I sent a long message yesterday describing a problem I thought had to do with
the JIT stubs.
After further investigating, the problem seems to be in the code generation.
The following basic block seems to have an error in it's code generation:
__exp.exit: ; preds = %codeRepl258, %__exp_bb_bb.exit
phi double [ 1.000000e+00, %codeRepl258 ], [ %.reload.reload.i,
%__exp_bb_bb.exit ] ; <double>:30 [#uses=2]
%castPointerToLong10 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic11 = add long %castPointerToLong10, 0 ;
<long> [#uses=1]
%castPointerToLong9 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic10 = add long %castPointerToLong9, 40 ;
<long> [#uses=1]
%castLongToGV11 = cast long %pointerArithmetic10 to double*
; <double*> [#uses=1]
store double 7.000000e+00, double* %castLongToGV11
%castPointerToLong12 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic13 = add long %castPointerToLong12, 16
; <long> [#uses=1]
%tmp2.loc = alloca int ; <int*> [#uses=2]
%castLongToGV14 = cast long %pointerArithmetic13 to double*
; <double*> [#uses=1]
store double 2.000000e+00, double* %castLongToGV14
cast int %x to double ; <double>:31 [#uses=1]
frem double %31, 1.000000e+02 ; <double>:32 [#uses=2]
%castPointerToLong15 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic16 = add long %castPointerToLong15, 24
; <long> [#uses=1]
%castLongToGV17 = cast long %pointerArithmetic16 to double*
; <double*> [#uses=1]
store double %32, double* %castLongToGV17
%castPointerToLong18 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic19 = add long %castPointerToLong18, 24
; <long> [#uses=1]
%castLongToGV20 = cast long %pointerArithmetic19 to double*
; <double*> [#uses=1]
load double* %castLongToGV20 ; <double>:33 [#uses=1]
%castPointerToLong21 = cast [10 x double]* %DataStore to long
; <long> [#uses=1]
%pointerArithmetic22 = add long %castPointerToLong21, 16
; <long> [#uses=1]
%castLongToGV23 = cast long %pointerArithmetic22 to double*
; <double*> [#uses=1]
load double* %castLongToGV23 ; <double>:34 [#uses=1]
cast double %34 to int ; <int>:9 [#uses=2]
seteq int %9, 0 ; <bool>:7 [#uses=1]
br bool %7, label %entry.bb19_crit_edge.i270, label %bb.preheader.i271
It gets converted to the following MachineBasicBlock
__exp.exit (0x8c58628, LLVM BB @0x8c1c558, ID#21):
Predecessors according to CFG: 0x8c53a90 0x8c55b50
MOV32mi %EBP, 1, %NOREG, -224, <ga:DataStore>
%EAX = MOV32rm %EBP, 1, %NOREG, -224
%EAX = ADD32ri8 %EAX, 40
MOV32mi %EAX, 1, %NOREG, 0, 0
MOV32mi %EAX, 1, %NOREG, 4, 1075576832
%ESP = SUB32ri %ESP, 16
%XMM0 = CVTSI2SDrr %EDI
MOVSDmr %ESP, 1, %NOREG, 0, %XMM0
MOV32mr %EBP, 1, %NOREG, -268, %ESP
ADD32mi8 %EBP, 1, %NOREG, -268, 4294967288
%ESP = MOV32rm %EBP, 1, %NOREG, -268
%ESI = MOV32rm %EBP, 1, %NOREG, -224
%ESI = ADD32ri8 %ESI, 16
MOV32mi %ESI, 1, %NOREG, 0, 0
MOV32mi %ESI, 1, %NOREG, 4, 1073741824
MOV32mi %ESP, 1, %NOREG, 12, 1079574528
MOV32mi %ESP, 1, %NOREG, 8, 0
CALLpcrel32 <es:fmod>
%ESP = ADD32ri8 %ESP, 16
FSTP64m %EBP, 1, %NOREG, -160
%EAX = MOV32rm %EBP, 1, %NOREG, -224
%EAX = ADD32ri8 %EAX, 24
%XMM0 = MOVSDrm %EBP, 1, %NOREG, -160
MOVSDmr %EBP, 1, %NOREG, -232, %XMM0
MOVSDmr %EAX, 1, %NOREG, 0, %XMM0
%EAX = CVTTSD2SIrm %ESI, 1, %NOREG, 0
%ECX = MOV32r0
TEST32rr %EAX, %EAX
JNE mbb<bb.preheader.i271,0x8c55330>
Successors according to CFG: 0x8c55330 0x8c573b0
The gdb disassembler gives me the following lines for that basic block
__exp.exit:
0xf5f6f317: movl $0xa542b70,0xffffff20(%ebp)
0xf5f6f321: mov 0xffffff20(%ebp),%eax
0xf5f6f327: add $0x28,%eax
0xf5f6f32a: movl $0x0,(%eax)
0xf5f6f330: movl $0x401c0000,0x4(%eax)
0xf5f6f337: sub $0x10,%esp
0xf5f6f33d: cvtsi2sd %edi,%xmm0
0xf5f6f341: movsd %xmm0,(%esp)
0xf5f6f346: mov %esp,0xfffffef4(%ebp)
0xf5f6f34c: addl $0xfffffff8,0xfffffef4(%ebp)
0xf5f6f353: mov 0xfffffef4(%ebp),%esp
0xf5f6f359: mov 0xffffff20(%ebp),%esi
0xf5f6f35f: add $0x10,%esi
0xf5f6f362: movl $0x0,(%esi)
0xf5f6f368: movl $0x40000000,0x4(%esi)
0xf5f6f36f: movl $0x40590000,0xc(%esp)
0xf5f6f377: movl $0x0,0x8(%esp)
0xf5f6f37f: call 0xf5f6effb
0xf5f6f384: add $0x10,%esp
0xf5f6f387: fstpl 0xffffff60(%ebp)
0xf5f6f38d: mov 0xffffff20(%ebp),%eax
0xf5f6f393: add $0x18,%eax
0xf5f6f396: movsd 0xffffff60(%ebp),%xmm0
0xf5f6f39e: movsd %xmm0,0xffffff18(%ebp)
0xf5f6f3a6: movsd %xmm0,(%eax)
0xf5f6f3aa: cvttsd2si (%esi),%eax
0xf5f6f3ae: xor %ecx,%ecx
0xf5f6f3b0: test %eax,%eax
0xf5f6f3b2: jne 0xf5f6f3c5
The problem I'm seeing is that the generated code for the "%tmp2.loc =
alloca int" instruction seems to get placed in the middle of
the generated code for the "frem double %31, 1.000000e+02"
instruction. The generated code for the frem call subtracts 16 from the stack
to
prepare for the insertion of arguments onto the stack. However, before it
insert the arguments on the stack, it allocates space for tmp2.loc.
Therefore the stack essentially gets subtracted by 10 more. Then the arguments
are placed on, the call is made, and upon return, 16 is added to
the stack. Basically, after the call, the stack doesn't go back to the
state it was in before the call because the alloca snuck in between
the instructions. Now, tmp2.loc is sitting in memory past the stack pointer
which can potentially be overwritten by a future call and in the example
I sent yesterday, it does get overwritten.
Thanks,
Ben Mayne
x245
-------------- next part --------------
An HTML attachment was scrubbed...
URL:
<http://lists.llvm.org/pipermail/llvm-dev/attachments/20071220/a2102e29/attachment.html>
llvm 1.9 is fairly old. Please move to top of tree and try to reproduce the problem if possible. Then please file a bugzilla report with reproducible test case and information about system configuration. Thanks, Evan On Dec 20, 2007, at 12:54 PM, Ben Mayne wrote:> I sent a long message yesterday describing a problem I thought had > to do with the JIT stubs. > After further investigating, the problem seems to be in the code > generation. > > The following basic block seems to have an error in it's code > generation: > > __exp.exit: ; preds = %codeRepl258, %__exp_bb_bb.exit > phi double [ 1.000000e+00, %codeRepl258 ], > [ %.reload.reload.i, %__exp_bb_bb.exit ] ; <double>:30 > [#uses=2] > %castPointerToLong10 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic11 = add long %castPointerToLong10, > 0 ; <long> [#uses=1] > %castPointerToLong9 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic10 = add long %castPointerToLong9, > 40 ; <long> [#uses=1] > %castLongToGV11 = cast long %pointerArithmetic10 to > double* ; <double*> [#uses=1] > store double 7.000000e+00, double* %castLongToGV11 > %castPointerToLong12 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic13 = add long %castPointerToLong12, > 16 ; <long> [#uses=1] > %tmp2.loc = alloca int ; <int*> [#uses=2] > %castLongToGV14 = cast long %pointerArithmetic13 to > double* ; <double*> [#uses=1] > store double 2.000000e+00, double* %castLongToGV14 > cast int %x to double ; <double>:31 [#uses=1] > frem double %31, 1.000000e+02 ; <double>:32 > [#uses=2] > %castPointerToLong15 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic16 = add long %castPointerToLong15, > 24 ; <long> [#uses=1] > %castLongToGV17 = cast long %pointerArithmetic16 to > double* ; <double*> [#uses=1] > store double %32, double* %castLongToGV17 > %castPointerToLong18 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic19 = add long %castPointerToLong18, > 24 ; <long> [#uses=1] > %castLongToGV20 = cast long %pointerArithmetic19 to > double* ; <double*> [#uses=1] > load double* %castLongToGV20 ; <double>:33 > [#uses=1] > %castPointerToLong21 = cast [10 x double]* %DataStore to > long ; <long> [#uses=1] > %pointerArithmetic22 = add long %castPointerToLong21, > 16 ; <long> [#uses=1] > %castLongToGV23 = cast long %pointerArithmetic22 to > double* ; <double*> [#uses=1] > load double* %castLongToGV23 ; <double>:34 > [#uses=1] > cast double %34 to int ; <int>:9 [#uses=2] > seteq int %9, 0 ; <bool>:7 [#uses=1] > br bool %7, label %entry.bb19_crit_edge.i270, label > %bb.preheader.i271 > > It gets converted to the following MachineBasicBlock > __exp.exit (0x8c58628, LLVM BB @0x8c1c558, ID#21): > Predecessors according to CFG: 0x8c53a90 0x8c55b50 > MOV32mi %EBP, 1, %NOREG, -224, <ga:DataStore> > %EAX = MOV32rm %EBP, 1, %NOREG, -224 > %EAX = ADD32ri8 %EAX, 40 > MOV32mi %EAX, 1, %NOREG, 0, 0 > MOV32mi %EAX, 1, %NOREG, 4, 1075576832 > %ESP = SUB32ri %ESP, 16 > %XMM0 = CVTSI2SDrr %EDI > MOVSDmr %ESP, 1, %NOREG, 0, %XMM0 > MOV32mr %EBP, 1, %NOREG, -268, %ESP > ADD32mi8 %EBP, 1, %NOREG, -268, 4294967288 > %ESP = MOV32rm %EBP, 1, %NOREG, -268 > %ESI = MOV32rm %EBP, 1, %NOREG, -224 > %ESI = ADD32ri8 %ESI, 16 > MOV32mi %ESI, 1, %NOREG, 0, 0 > MOV32mi %ESI, 1, %NOREG, 4, 1073741824 > MOV32mi %ESP, 1, %NOREG, 12, 1079574528 > MOV32mi %ESP, 1, %NOREG, 8, 0 > CALLpcrel32 <es:fmod> > %ESP = ADD32ri8 %ESP, 16 > FSTP64m %EBP, 1, %NOREG, -160 > %EAX = MOV32rm %EBP, 1, %NOREG, -224 > %EAX = ADD32ri8 %EAX, 24 > %XMM0 = MOVSDrm %EBP, 1, %NOREG, -160 > MOVSDmr %EBP, 1, %NOREG, -232, %XMM0 > MOVSDmr %EAX, 1, %NOREG, 0, %XMM0 > %EAX = CVTTSD2SIrm %ESI, 1, %NOREG, 0 > %ECX = MOV32r0 > TEST32rr %EAX, %EAX > JNE mbb<bb.preheader.i271,0x8c55330> > Successors according to CFG: 0x8c55330 0x8c573b0 > > The gdb disassembler gives me the following lines for that basic block > > __exp.exit: > 0xf5f6f317: movl $0xa542b70,0xffffff20(%ebp) > 0xf5f6f321: mov 0xffffff20(%ebp),%eax > 0xf5f6f327: add $0x28,%eax > 0xf5f6f32a: movl $0x0,(%eax) > 0xf5f6f330: movl $0x401c0000,0x4(%eax) > 0xf5f6f337: sub $0x10,%esp > 0xf5f6f33d: cvtsi2sd %edi,%xmm0 > 0xf5f6f341: movsd %xmm0,(%esp) > 0xf5f6f346: mov %esp,0xfffffef4(%ebp) > 0xf5f6f34c: addl $0xfffffff8,0xfffffef4(%ebp) > 0xf5f6f353: mov 0xfffffef4(%ebp),%esp > 0xf5f6f359: mov 0xffffff20(%ebp),%esi > 0xf5f6f35f: add $0x10,%esi > 0xf5f6f362: movl $0x0,(%esi) > 0xf5f6f368: movl $0x40000000,0x4(%esi) > 0xf5f6f36f: movl $0x40590000,0xc(%esp) > 0xf5f6f377: movl $0x0,0x8(%esp) > 0xf5f6f37f: call 0xf5f6effb > 0xf5f6f384: add $0x10,%esp > 0xf5f6f387: fstpl 0xffffff60(%ebp) > 0xf5f6f38d: mov 0xffffff20(%ebp),%eax > 0xf5f6f393: add $0x18,%eax > 0xf5f6f396: movsd 0xffffff60(%ebp),%xmm0 > 0xf5f6f39e: movsd %xmm0,0xffffff18(%ebp) > 0xf5f6f3a6: movsd %xmm0,(%eax) > 0xf5f6f3aa: cvttsd2si (%esi),%eax > 0xf5f6f3ae: xor %ecx,%ecx > 0xf5f6f3b0: test %eax,%eax > 0xf5f6f3b2: jne 0xf5f6f3c5 > > > The problem I'm seeing is that the generated code for the "%tmp2.loc > = alloca int" instruction seems to get placed in the middle of > the generated code for the "frem double %31, 1.000000e+02" > instruction. The generated code for the frem call subtracts 16 from > the stack to > prepare for the insertion of arguments onto the stack. However, > before it insert the arguments on the stack, it allocates space for > tmp2.loc. > Therefore the stack essentially gets subtracted by 10 more. Then > the arguments are placed on, the call is made, and upon return, 16 > is added to > the stack. Basically, after the call, the stack doesn't go back to > the state it was in before the call because the alloca snuck in > between > the instructions. Now, tmp2.loc is sitting in memory past the stack > pointer which can potentially be overwritten by a future call and in > the example > I sent yesterday, it does get overwritten. > > Thanks, > > Ben Mayne > x245 > > > _______________________________________________ > LLVM Developers mailing list > LLVMdev at cs.uiuc.edu http://llvm.cs.uiuc.edu > http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev-------------- next part -------------- An HTML attachment was scrubbed... URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20071220/2e7ce979/attachment.html>
Maybe Matching Threads
- [LLVMdev] JIT Stub Problem
- [newbie] trouble with global variables and CreateLoad/Store in JIT
- [newbie] trouble with global variables and CreateLoad/Store in JIT
- [newbie] trouble with global variables and CreateLoad/Store in JIT
- [newbie] trouble with global variables and CreateLoad/Store in JIT