Electrical FireExamples |
|
The following are examples of Electrical Fire at work.
The Java function fed to Electrical Fire is a seive function:
public static void sieve(int a[])
{
int k1 = 1;
int i2 = 0;
int j2 = 0;
int an[] = a;
j2++;
an[0] = 1;
an[1] = 2;
k1 = 2;
for (int i1 = 3; i1 < 2048; i1++)
{
boolean flag1;
i2 = 1;
for (flag1 = true; i2 < k1 && flag1; i2++)
if (an[i2] > 0 && an[i2] <= i1 / 2 && i1 % an[i2] == 0)
flag1 = false;
if (flag1)
{
k1++;
an[k1 - 1] = i1;
}
}
}
The equivalent bytecode of the given source code:
0000: 04 iconst_1 0001: 3C istore_1 0002: 03 iconst_0 0003: 3D istore_2 0004: 03 iconst_0 0005: 3E istore_3 0006: 2A aload_0 0007: 3A 04 astore 4 0009: 84 03 01 iinc 3,1 000C: 19 04 aload 4 000E: 03 iconst_0 000F: 04 iconst_1 0010: 4F iastore 0011: 19 04 aload 4 0013: 04 iconst_1 0014: 05 iconst_2 0015: 4F iastore 0016: 05 iconst_2 0017: 3C istore_1 0018: 06 iconst_3 0019: 36 05 istore 5 001B: A7 004A goto 0x0065 001E: 04 iconst_1 001F: 3D istore_2 0020: 04 iconst_1 0021: 36 06 istore 6 0023: A7 0025 goto 0x0048 0026: 19 04 aload 4 0028: 1C iload_2 0029: 2E iaload 002A: 9E 001B ifle 0x0045 002D: 19 04 aload 4 002F: 1C iload_2 0030: 2E iaload 0031: 15 05 iload 5 0033: 05 iconst_2 0034: 6C idiv 0035: A3 0010 if_icmpgt 0x0045 0038: 15 05 iload 5 003A: 19 04 aload 4 003C: 1C iload_2 003D: 2E iaload 003E: 70 irem 003F: 9A 0006 ifne 0x0045 0042: 03 iconst_0 0043: 36 06 istore 6 0045: 84 02 01 iinc 2,1 0048: 1C iload_2 0049: 1B iload_1 004A: A2 0008 if_icmpge 0x0052 004D: 15 06 iload 6 004F: 9A FFD7 ifne 0x0026 0052: 15 06 iload 6 0054: 99 000E ifeq 0x0062 0057: 84 01 01 iinc 1,1 005A: 19 04 aload 4 005C: 1B iload_1 005D: 04 iconst_1 005E: 64 isub 005F: 15 05 iload 5 0061: 4F iastore 0062: 84 05 01 iinc 5,1 0065: 15 05 iload 5 0067: 11 0800 sipush 2048 006A: A1 FFB4 if_icmplt 0x001E 006D: B1 return
After reading in the bytecodes, a bytecode graph is generated:
The bytecode graph has 15 bytecode blocks:
B0 (00DB7508): 1 predecessors
0000: 04 iconst_1
0001: 3C istore_1
0002: 03 iconst_0
0003: 3D istore_2
0004: 03 iconst_0
0005: 3E istore_3
0006: 2A aload_0
0007: 3A 04 astore 4
0009: 84 03 01 iinc 3,1
000C: 19 04 aload 4
000E: 03 iconst_0
000F: 04 iconst_1
0010: 4F iastore
0011: 19 04 aload 4
0013: 04 iconst_1
0014: 05 iconst_2
0015: 4F iastore
0016: 05 iconst_2
0017: 3C istore_1
0018: 06 iconst_3
0019: 36 05 istore 5
001B: A7 004A goto 0x0065
Successors: B1
B1 (00DB7560): 2 predecessors
0065: 15 05 iload 5
0067: 11 0800 sipush 2048
006A: A1 FFB4 if_icmplt 0x001E
Successors: B13, B2
B2 (00DB75B8): 1 predecessors
001E: 04 iconst_1
001F: 3D istore_2
0020: 04 iconst_1
0021: 36 06 istore 6
0023: A7 0025 goto 0x0048
Successors: B3
B3 (00DB7610): 2 predecessors
0048: 1C iload_2
0049: 1B iload_1
004A: A2 0008 if_icmpge 0x0052
Successors: B4, B10
B4 (00DB7878): 1 predecessors
004D: 15 06 iload 6
004F: 9A FFD7 ifne 0x0026
Successors: B10, B5
B5 (00DB7668): 1 predecessors
0026: 19 04 aload 4
0028: 1C iload_2
0029: 2E iaload
002A: 9E 001B ifle 0x0045
Successors: B6, B9
B6 (00DB7718): 1 predecessors
002D: 19 04 aload 4
002F: 1C iload_2
0030: 2E iaload
0031: 15 05 iload 5
0033: 05 iconst_2
0034: 6C idiv
0035: A3 0010 if_icmpgt 0x0045
Successors: B7, B9
B7 (00DB7770): 1 predecessors
0038: 15 05 iload 5
003A: 19 04 aload 4
003C: 1C iload_2
003D: 2E iaload
003E: 70 irem
003F: 9A 0006 ifne 0x0045
Successors: B8, B9
B8 (00DB77C8): 1 predecessors
0042: 03 iconst_0
0043: 36 06 istore 6
Successors: B9
B9 (00DB76C0): 4 predecessors
0045: 84 02 01 iinc 2,1
Successors: B3
B10 (00DB7820): 2 predecessors
0052: 15 06 iload 6
0054: 99 000E ifeq 0x0062
Successors: B11, B12
B11 (00DB7928): 1 predecessors
0057: 84 01 01 iinc 1,1
005A: 19 04 aload 4
005C: 1B iload_1
005D: 04 iconst_1
005E: 64 isub
005F: 15 05 iload 5
0061: 4F iastore
Successors: B12
B12 (00DB78D0): 2 predecessors
0062: 84 05 01 iinc 5,1
Successors: B1
B13 (00DB7980): 1 predecessors
006D: B1 return
Successors: B14
B14 (00DB74B0): 1 predecessors
End block
Primitive Graph Representation:
Here is a contextual representation of the primitive graph with some optimizations performed:
Begin Node N0 (013E03F4):
Predecessors:
Primitives:
wm1 := Arg_M argMEM
va2 := Arg_A arg0
Successors: N1
Exc Node N1 (013E0658):
Predecessors: N0
Primitives:
Exc ChkNull va2
Successors: N2, N30
Exc Node N2 (013E0760):
Predecessors: N1
Primitives:
va4 := AddI_A va2, 4
vi5 := LdC_I va4
Exc LimitR 0, vi5
Successors: N3, N30
Exc Node N3 (013E09A0):
Predecessors: N2
Primitives:
va6 := AddI_A va2, 8
wm7 := StI_I wm1, va6, 1
Exc ChkNull va2
Successors: N4, N30
Exc Node N4 (013E0BD8):
Predecessors: N3
Primitives:
va8 := AddI_A va2, 4
vi9 := LdC_I va8
Exc LimitR 1, vi9
Successors: N5, N30
Block Node N5 (013E0E18):
Predecessors: N4
Primitives:
va10 := AddI_A va2, 12
wm11 := StI_I wm7, va10, 2
wi12 := Const_I 3
wi13 := Const_I 2
Successors: N6
AExc Node N6 (013E1070):
Predecessors: N5, N28
Phi nodes:
vi14 := Phi_I wi12, vi65
vi15 := Phi_I wi13, vi64
va16 := Phi_A va2, va24
vm17 := Phi_M wm11, vm63
Successors: N7, N30
If Node N7 (013E1128):
Predecessors: N6
Primitives:
vc18 := CmpI_I vi14, 2048
IfLt vc18
Successors: N29, N8
Block Node N8 (013E13C0):
Predecessors: N7
Primitives:
wi19 := Const_I 1
wi20 := Const_I 1
Successors: N9
AExc Node N9 (013E1458):
Predecessors: N8, N23
Phi nodes:
vi21 := Phi_I vi15, vi21
vi22 := Phi_I wi19, vi54
vi23 := Phi_I wi20, vi53
va24 := Phi_A va16, va24
vm25 := Phi_M vm17, vm25
vi26 := Phi_I vi14, vi26
Successors: N10, N30
If Node N10 (013E1510):
Predecessors: N9
Primitives:
vc27 := Cmp_I vi22, vi21
IfGe vc27
Successors: N11, N24
If Node N11 (013E1950):
Predecessors: N10
Primitives:
vc28 := CmpI_I vi23, 0
IfNe vc28
Successors: N24, N12
Exc Node N12 (013E1BE8):
Predecessors: N11
Primitives:
Exc ChkNull va24
Successors: N13, N30
Exc Node N13 (013E1E20):
Predecessors: N12
Primitives:
va29 := AddI_A va24, 4
vi30 := LdC_I va29
Exc Limit vi22, vi30
Successors: N14, N30
If Node N14 (013E2060):
Predecessors: N13
Primitives:
vi31 := ShlI_I vi22, 2
va32 := Add_A va24, vi31
va33 := AddI_A va32, 8
vi34 := Ld_I vm25, va33
vc35 := CmpI_I vi34, 0
IfLe vc35
Successors: N15, N23
Exc Node N15 (013E4600):
Predecessors: N14
Primitives:
Exc ChkNull va24
Successors: N16, N30
Exc Node N16 (013E4708):
Predecessors: N15
Primitives:
va36 := AddI_A va24, 4
vi37 := LdC_I va36
Exc Limit vi22, vi37
Successors: N17, N30
If Node N17 (013E4948):
Predecessors: N16
Primitives:
vi38 := ShlI_I vi22, 2
va39 := Add_A va24, vi38
va40 := AddI_A va39, 8
vi41 := Ld_I vm25, va40
vi42 := DivI_I vi26, 2
vc43 := Cmp_I vi41, vi42
IfGt vc43
Successors: N18, N23
Exc Node N18 (013E4E40):
Predecessors: N17
Primitives:
Exc ChkNull va24
Successors: N19, N30
Exc Node N19 (013E4F48):
Predecessors: N18
Primitives:
va44 := AddI_A va24, 4
vi45 := LdC_I va44
Exc Limit vi22, vi45
Successors: N20, N30
Exc Node N20 (013E5188):
Predecessors: N19
Primitives:
vi46 := ShlI_I vi22, 2
va47 := Add_A va24, vi46
va48 := AddI_A va47, 8
vi49 := Ld_I vm25, va48
Exc vi50 := ModE_I vi26, vi49
Successors: N21, N30
If Node N21 (013E5518):
Predecessors: N20
Primitives:
vc51 := CmpI_I vi50, 0
IfNe vc51
Successors: N22, N23
Block Node N22 (013E56A0):
Predecessors: N21
Primitives:
vi52 := Const_I 0
Successors: N23
Block Node N23 (013E5738):
Predecessors: N14, N17, N21, N22
Phi nodes:
vi53 := Phi_I vi23, vi23, vi23, vi52
Primitives:
vi54 := AddI_I vi22, 1
Successors: N9
If Node N24 (013E59B0):
Predecessors: N10, N11
Primitives:
vc55 := CmpI_I vi23, 0
IfEq vc55
Successors: N25, N28
Exc Node N25 (013E5B38):
Predecessors: N24
Primitives:
vi56 := AddI_I vi21, 1
Exc ChkNull va24
Successors: N26, N30
Exc Node N26 (013E5CD0):
Predecessors: N25
Primitives:
va57 := AddI_A va24, 4
vi58 := LdC_I va57
Exc Limit vi21, vi58
Successors: N27, N30
Block Node N27 (013E5F10):
Predecessors: N26
Primitives:
vi59 := ShlI_I vi21, 2
va60 := Add_A va24, vi59
va61 := AddI_A va60, 8
wm62 := St_I vm25, va61, vi26
Successors: N28
Block Node N28 (013E61F8):
Predecessors: N24, N27
Phi nodes:
vm63 := Phi_M vm25, wm62
vi64 := Phi_I vi21, vi56
Primitives:
vi65 := AddI_I vi26, 1
Successors: N6
Return Node N29 (013E6490):
Predecessors: N7
Successors: N30
End Node N30 (013E04F8):
Predecessors: N1, N2, N3, N4, N6, N9, N12, N13, N15, N16, N18, N19, N20, N25, N26, N29
Phi nodes:
vm3 := Phi_M wm1, wm1, wm7, wm7, vm17, vm25, vm25, vm25, vm25, vm25, vm25, vm25, vm25, vm25, vm25, vm17
Primitives:
resMEM := Result_M vm3
Successors:
After generating the primitive graph, native instructions are generated.
The following is an example of generating x86 instructions:
014269B0: push ebp 014269B1: mov ebp,esp 014269B3: sub esp,0000C 014269B6: push edi 014269B7: push esi 014269B8: push ebx 014269B9: cmp dword ptr [ecx+ 4],00000 014269BD: jle 6 014269C3: mov dword ptr [ecx+ 8], 1 014269CA: cmp dword ptr [ecx+ 4],00001 014269CE: jle 6 014269D4: mov dword ptr [ecx+ C], 2 014269DB: mov dword ptr [ebp- 4], 3 014269E2: mov edi, 2 014269E7: jmp 8D 014269EC: mov ebx, 1 014269F1: mov esi, 1 014269F6: jmp 4E 014269FB: cmp ebx,[ecx+ 4] 014269FE: jge 6 01426A04: cmp dword ptr [ecx+ebx*4+ 8],00000 01426A09: jle 3A 01426A0F: cmp ebx,[ecx+ 4] 01426A12: jge 6 01426A18: mov eax,[ebp- 4] 01426A1B: sar eax,01 01426A1E: cmp [ecx+ebx*4+ 8],eax 01426A22: jg 21 01426A28: cmp ebx,[ecx+ 4] 01426A2B: jge 6 01426A31: mov eax,[ebp- 4] 01426A34: cwd 01426A35: idiv dword ptr [ecx+ebx*4+ 8] 01426A39: test edx,edx 01426A3B: jnz 8 01426A41: xor esi,esi 01426A43: inc ebx 01426A44: cmp ebx,edi 01426A46: jge E 01426A4C: test esi,esi 01426A4E: jnz FFFFFFAD 01426A54: test esi,esi 01426A56: jz 1B 01426A5C: mov ebx,edi 01426A5E: inc ebx 01426A5F: cmp edi,[ecx+ 4] 01426A62: jge 6 01426A68: mov eax,[ebp- 4] 01426A6B: mov [ecx+edi*4+ 8],eax 01426A6F: mov edi,ebx 01426A71: inc dword ptr [ebp- 4] 01426A74: cmp dword ptr [ebp- 4], 800 01426A7B: jl FFFFFF71 01426A81: pop ebx 01426A82: pop esi 01426A83: pop edi 01426A84: mov esp,ebp 01426A86: pop ebp 01426A87: ret C
The following is an example of generating HPPA instructions:
sieve:
bl sieve_entry,%rp
nop
ldw -18(%sr0,%sp),%rp
ldsid (%sr0,%rp),%r1
mtsp %r1,%sr0
be,n 0(%sr0,%rp)
sieve_entry:
copy %arg0,%r22
comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
comibf,<=,n 0,%r19,N30
nop
ldi 1,%r19
stw %r19,8(0,%r22)
comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
comibf,<=,n 1,%r19,N30
nop
ldi 2,%r19
stw %r19,12(0,%r22)
ldi 3,%arg0
ldi 2,%arg2
bl,n N6,0
nop
N8: ldi 1,%r21
ldi 1,%arg3
bl,n N9,0
nop
N12: comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
combf,<,n %r21,%r19,N30
nop
sh2addl %r21,%r22,%r19
ldw 8(0,%r19),%r19
comibf,<=,n 0,%r19,N23
nop
comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
combf,<,n %r21,%r19,N30
nop
sh2addl %r21,%r22,%r19
ldw 8(0,%r19),%r20
extru %arg0,0,1,%r19
addl %arg0,%r19,%r19
extrs %r19,30,31,%r19
combf,<=,n %r20,%r19,N23
nop
comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
combf,<,n %r21,%r19,N30
nop
sh2addl %r21,%r22,%r19
ldw 8(0,%r19),%arg1
bl,n HPPAremI,%r31
comibf,=,n 0,%ret1,N23
nop
copy 0,%arg3
N23: ldo 1(%r21),%r21
N9: combf,<,n %r21,%arg2,N24
nop
comibf,=,n 0,%arg3,N12
nop
N24: comibt,=,n 0,%arg3,N28
nop
ldo 1(%arg2),%r20
comibt,=,n 0,%r22,N30
nop
ldw 4(0,%r22),%r19
combf,<,n %arg2,%r19,N30
nop
sh2addl %arg2,%r22,%r19
stw %arg0,8(0,%r19)
copy %r20,%arg2
N28: ldo 1(%arg0),%arg0
N6: ldi 2048,%r19
combt,<,n %arg0,%r19,N8
nop
N30: bv 0(%rp)
HPPAremI:
addit,= 0,%arg1,%r0
add,>= %r0,%arg0,%ret1
sub %r0,%ret1,%ret1
sub %r0,%arg1,%r1
ds %r0,%r1,%r0
copy %r0,%r1
add %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
ds %r1,%arg1,%r1
addc %ret1,%ret1,%ret1
movb,>=,n %r1,%ret1,L5
add,< %arg1,%r0,%r0
add,tr %r1,%arg1,%ret1
sub %r1,%arg1,%ret1
L5: add,>= %arg0,%r0,%r0
sub %r0,%ret1,%ret1
bv %r0(%r31)
nop
Using Quantify, it is possible to compute the time it takes EF to translate bytecodes. Here are the following functions that were timed: Basic block division, Primitive Graph generation, Optimization, and Code generation.
Given: A function with 1045 bytecodes to translate.
| Basic Blocks | 00.25 ms |
| Primitive Graph | 02.86 ms |
| Optimization | 00.13 ms |
| Code Generation | 20.50 ms |
| Total | 23.74 ms |