Hi everyone, As a front-end developer, I'd like to add a language-specific information at a fixed location of each stack frame. The reason is that I want to retrieve this information when dynamically walking the stack. For example, X86 has the following stack layout for a function with two arguments and two locals: 12(%ebp) - second function parameter 8(%ebp) - first function parameter 4(%ebp) - old %EIP (the function's "return address") 0(%ebp) - old %EBP (previous function's base pointer) -4(%ebp) - first local variable -8(%ebp) - second local variable I'd like to generate this layout: 12(%ebp) - second function parameter 8(%ebp) - first function parameter 4(%ebp) - old %EIP (the function's "return address") 0(%ebp) - old %EBP (previous function's base pointer) -4(%ebp) - My language specific information -8(%ebp) - first local variable -12(%ebp) - second local variable Can I express this in LLVM without modifying llvm internals? I looked at writing a machine function pass, but I can't register one when JITting. Is the machine function pass the correct way of implementing this? Thanks, Nicolas
> I'd like to generate this layout: > > 12(%ebp) - second function parameter > 8(%ebp) - first function parameter > 4(%ebp) - old %EIP (the function's "return address") > 0(%ebp) - old %EBP (previous function's base pointer) > -4(%ebp) - My language specific information > -8(%ebp) - first local variable > -12(%ebp) - second local variable >Take a look at the register allocators, each of which is implemented as a MachineFunctionPass. These are responsible for assigning stack slots, and it shouldn't be too hard to modify them to reserve some stack slots. Also, I'd recommend that you consider the prevalence of this language specific information, and re-evaluate whether you want to modify the stack frame at all. Do you expect *every* function will need it, or *at most* every function will need it? Could this information also be encoded into a per-function local variable? Could your compiler generate code to maintain a separate stack for such information? Also, out of curiosity: are you working on something like Java security contexts? Or perhaps something like ProPolice canary values? -- Nick Johnson
Nick Johnson wrote (citing somebody else):>> I'd like to generate this layout: >> >> 12(%ebp) - second function parameter >> 8(%ebp) - first function parameter >> 4(%ebp) - old %EIP (the function's "return address") >> 0(%ebp) - old %EBP (previous function's base pointer) >> -4(%ebp) - My language specific information >> -8(%ebp) - first local variable >> -12(%ebp) - second local variable >> >> > > Take a look at the register allocators, each of which is implemented > as a MachineFunctionPass. These are responsible for assigning stack > slots, and it shouldn't be too hard to modify them to reserve some > stack slots. > > Also, I'd recommend that you consider the prevalence of this language > specific information, and re-evaluate whether you want to modify the > stack frame at all. Do you expect *every* function will need it, or > *at most* every function will need it?I don't know the motivation of the initial poster, but I do understand the wish to put some language specific information on the call stack. I even can think of several reasons to do that: 1. easy support of a precise garbage collector: you want each call frame to have, at some fixed offset, a pointer to some frame layout descriptor (used by your copying garbage collector) which tells what are the pointers in the call frame. Another way to do that is to have your GC use the return address to find out the routine and hence its frame layout (IIRC, the ocaml native compiler does that), but this is much harder to implement. 2. introspective/reflective facilities: your language is compiled but yet has the ability to inspect each of its call stack frame. There are many reasons to want that. 3. reification of continuations : your language implement continuations, and perhaps facilities to inspect them, or dump or serialize them, ... Happy New Year 2009 to everyone! Regards. -- Basile STARYNKEVITCH http://starynkevitch.net/Basile/ email: basile<at>starynkevitch<dot>net mobile: +33 6 8501 2359 8, rue de la Faiencerie, 92340 Bourg La Reine, France *** opinions {are only mines, sont seulement les miennes} *** membre de l'APRIL "promouvoir et défendre le logiciel libre" Rejoignez maitenant pplus de 3700 adhérents http://www.april.org
Hi Nick, Nick Johnson wrote:>> I'd like to generate this layout: >> >> 12(%ebp) - second function parameter >> 8(%ebp) - first function parameter >> 4(%ebp) - old %EIP (the function's "return address") >> 0(%ebp) - old %EBP (previous function's base pointer) >> -4(%ebp) - My language specific information >> -8(%ebp) - first local variable >> -12(%ebp) - second local variable >> >> > > Take a look at the register allocators, each of which is implemented > as a MachineFunctionPass. These are responsible for assigning stack > slots, and it shouldn't be too hard to modify them to reserve some > stack slots. > >Thanks, but I don't want to modify the register allocators. I'd like to write an llvm-external machine pass.> Also, I'd recommend that you consider the prevalence of this language > specific information, and re-evaluate whether you want to modify the > stack frame at all.Yes, I do :) There are some alternatives, but this looks like the most efficient. What I'm facing is engineering issues, since adding a new information in the stack frame is similar to adding the frame-pointer information.> Do you expect *every* function will need it, or > *at most* every function will need it?Every function that I compile with llvm.> Could this information also be > encoded into a per-function local variable?No, because then you wouldn't know where the information is stored when walking the stack.> Could your compiler > generate code to maintain a separate stack for such information? > >Sure, but it's much more expensive than a simple push and pop.> Also, out of curiosity: are you working on something like Java > security contexts? Or perhaps something like ProPolice canary values? > >I'm working on VMKit, which implements a JVM on top of LLVM. And an easy way to walk the stack is to have a methodID stored in each stack frame to locate which method the frame belongs to. Nicolas
On Dec 27, 2008, at 2:28 PM, Nicolas Geoffray wrote:> Hi everyone, > > As a front-end developer, I'd like to add a language-specific > information at a fixed location of each stack frame. The reason is > that > I want to retrieve this information when dynamically walking the > stack. > > For example, X86 has the following stack layout for a function with > two > arguments and two locals: > > 12(%ebp) - second function parameter > 8(%ebp) - first function parameter > 4(%ebp) - old %EIP (the function's "return address") > 0(%ebp) - old %EBP (previous function's base pointer) > -4(%ebp) - first local variable > -8(%ebp) - second local variable > > > I'd like to generate this layout: > > 12(%ebp) - second function parameter > 8(%ebp) - first function parameter > 4(%ebp) - old %EIP (the function's "return address") > 0(%ebp) - old %EBP (previous function's base pointer) > -4(%ebp) - My language specific information > -8(%ebp) - first local variable > -12(%ebp) - second local variable > > > Can I express this in LLVM without modifying llvm internals? I > looked at > writing a machine function pass, but I can't register one when > JITting. > Is the machine function pass the correct way of implementing this? >This might help. See how "stack protectors" is implemented here: lib/CodeGen/StackProtector.cpp It places a special value at a specific place on the stack. You can use the same trick to put your own information on a set stack position. There's more to the code than just that .cpp file. It's done with intrinsics. You'll also need to check out the PrologEpilogInserter.cpp code. -bw
Hi Bill, Bill Wendling wrote:> > This might help. See how "stack protectors" is implemented here: > > lib/CodeGen/StackProtector.cpp > > It places a special value at a specific place on the stack. You can > use the same trick to put your own information on a set stack > position. There's more to the code than just that .cpp file. It's done > with intrinsics. You'll also need to check out the > PrologEpilogInserter.cpp code. > >Thanks. I've already looked at what stack protector does, and indeed the need is similar. However, I'd like to add the functionality as a new machine pass, so that I don't need to add new intrinsics and modify the llvm code base. Do you think that's possible? Nicolas> -bw > _______________________________________________ > LLVM Developers mailing list > LLVMdev at cs.uiuc.edu http://llvm.cs.uiuc.edu > http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev >