Hi, Is it normal for these two threads to differ?
exe_ctx = m_interpreter.GetExecutionContext(); * * *exe_ctx.thread: 0x107900610, exe_ctx.process->GetThreadList().GetSelectedThread(): 0x0* Also, if we only have one thread, shouldn't that thread always be selected? Somehow the ThreadList.m_selected_thread is being set to LLDB_INVALID_THREADID right after I run my command. Regards, Filipe On Wed, Jul 27, 2011 at 10:27, Filipe Cabecinhas <[email protected]>wrote: > Hi, > > I did that, and tried watching the thread list, to see when it changed… > Couldn't find anything. I'll continue searching the code and debugging to > see where the selected thread may be changing. Or is it something that > shouldn't happen? > > I will also try this with a Cocoa program, to check the objective-c returns > and if having more threads change anything. > > Regards, > > Filipe Cabecinhas > > > On Tue, Jul 26, 2011 at 17:36, Enrico Granata <[email protected]> wrote: > >> Hi Filipe, >> thanks for all the hard work you are doing on LLDB. >> >> While I have not really delved into your patch, I think a good way to find >> out why you get this persistent error on stepping-over after your new >> command would be to set a breakpoint in >> CommandObjectThreadStepWithTypeAndScope::Execute >> >> The way I usually do this is creating an instance of LLDB debugging my >> inferior process (a test program in your case), and then in another Terminal >> window, opening a second LLDB and attaching it to the first instance (you >> can use the process attach -p command to do so). >> Then start to play with the first LLDB, and when you get to the point >> where you would type thread step-over and get in trouble, just set a >> breakpoint into the CommandObjectThreadStepWithTypeAndScope::Execute call >> in the second LLDB instance. >> >> Now, you can step through the command's code and check where it's failing >> exactly (and hopefully figure out why). >> >> Sincerely, >> *Enrico Granata* >> ✆ 408.974.5572 | ✉ egranata@.com >> >> On Jul 26, 2011, at 5:29 PM, Filipe Cabecinhas wrote: >> >> Hi all, >> >> Multi-level returns were not working as intended, as I would write to the >> frame's RegisterContext (yielding an error), instead of writing to the live >> RegisterContext. I have fixed that and created another test-case for it. >> >> I still have the problem of not rebuilding the StackFrameList, and the >> first "thread step-over" command right after a "frame return" is yielding an >> error. Subsequent commands work fine. >> >> Regards, >> >> Filipe >> >> On Mon, Jul 25, 2011 at 15:08, Filipe Cabecinhas < >> [email protected]> wrote: >> >>> Hi all, >>> >>> I've refactored the code to put most of the work on the StackFrameList >>> class, but I still have one problem: >>> The state of execution isn't being updated. >>> >>> - If I try to print the pc register after returning, it will just give me >>> the old value (still in the function). >>> - The first thread step-over command after returning from a function >>> isn't working, too. But that may have to do with: >>> - I can't update the stackframe list. thread backtrace always puts me >>> inside the function. >>> >>> These three problems may be interconnected. I'll try to debug further. >>> >>> I also can't do what Jim suggested. I got the Block reference, from the >>> frame. I can see if it's inlined and its size, but can't tell where it >>> starts/ends. >>> >>> I'll send two patches: They're the same except for the implemented >>> command. >>> >>> In one, the command is "thread return", in the other it is "frame >>> return". >>> >>> My problem is… Except for "frame select", the frame commands only work on >>> the current frame (not on other frames), so I would see "frame return" as >>> return only from the current frame. While "thread return" could return from >>> any frame (defaulting for the current thread). What do you think? >>> >>> I'm also sending a test directory, using the "thread return" variation. >>> >>> Regards, >>> >>> Filipe Cabecinhas >>> >>> >>> On Fri, Jul 22, 2011 at 16:25, Filipe Cabecinhas < >>> [email protected]> wrote: >>> >>>> Thanks for the help and advice. I will ping back the list with more >>>> stuff when I'm done. >>>> >>>> Regards, >>>> >>>> Filipe >>>> >>>> >>>> On Fri, Jul 22, 2011 at 16:23, Jim Ingham <[email protected]> wrote: >>>> >>>>> >>>>> On Jul 22, 2011, at 3:46 PM, Filipe Cabecinhas wrote: >>>>> >>>>> > >>>>> > >>>>> > On Fri, Jul 22, 2011 at 15:18, Jim Ingham <[email protected]> wrote: >>>>> > Filipe, >>>>> > >>>>> > Thanks for working on this. >>>>> > >>>>> > Note, gdb's "return" command doesn't do anything to attempt to clean >>>>> up local objects. It just pops the frames off the stack & returns the >>>>> value. This, like moving the PC by hand, is one of those commands that >>>>> you >>>>> just shouldn't use if you don't know what could go wrong... Anyway, >>>>> people >>>>> mostly use this to hack system routines to do something else, in which >>>>> case >>>>> you stop at the very beginning and return directly - you haven't gotten >>>>> far >>>>> enough to need to do any cleanup. >>>>> > >>>>> > Seems to me that the sensible thing to do about the return expression >>>>> is take whatever the user gives you and cast it to the return type of the >>>>> function you are returning from, if you know it. If you don't then just >>>>> write it as whatever they have given you, and the user will have to get it >>>>> right when they write the expression. That's the best you can do in this >>>>> case. >>>>> > >>>>> > OK. >>>>> > >>>>> > It also seems to me that much more of this could be generic. The >>>>> algorithm gdb uses is to get the register context one frame up on the >>>>> stack, >>>>> and write that to the real registers, and then throw away the cached stack >>>>> and remake it from the changed registers. That can all be done >>>>> generically. >>>>> Mind there are target specific bits but they are all hidden under the >>>>> register code. It is the unwinder's job to know what the register state >>>>> of >>>>> the functions up on the stack are, you should rely on that. >>>>> > >>>>> > The only ABI specific bit is that you need to ask the ABI where to >>>>> store the return value. For things smaller than a register that is easy. >>>>> For struct returns it can be hard, because the compiler usually passes >>>>> in a >>>>> pointer to the save location, but you would have to track the history of >>>>> that value to know where it is stored at the point you are trying to >>>>> return >>>>> from, and that's not trivial. Again, if you are at the beginning of the >>>>> function you're returning from, this is easy to do. >>>>> > >>>>> > Ok. You're suggesting taking the code out of the ABI and putting it >>>>> on the command (or maybe the StackFrame)? I initially wrote the code >>>>> thinking calling conventions could vary a lot but, for the returns, they >>>>> don't vary that much (and lldb allows us to abstract most of what varies). >>>>> Or would it be preferred to just contain the code in the command object? >>>>> >>>>> Yes. This functionality seems generally useful, so the code to do this >>>>> should go somewhere in the core. Then the command would just be a thin >>>>> wrapper. StackFrame doesn't seem right to me, since you are operating on >>>>> the list of frames more than the individual frame. So either >>>>> StackFrameList, or its owner Thread, seem good places. >>>>> >>>>> > >>>>> > I suppose the command should also be changed to the "frame" command, >>>>> to mimic gdb (it returns from the current frame, not the bottom-most). >>>>> > >>>>> >>>>> Yes, that makes sense, you would either return from the currently >>>>> selected frame, or from a frame given explicitly in the command. Note in >>>>> general in lldb we try to avoid positional arguments, so I would do: >>>>> >>>>> frame return --frame <FRAME NUMBER> <expression> >>>>> >>>>> BTW, you can also make LLDB commands "RAW" commands, which means that >>>>> everything after the options is passed unparsed to the command. That's >>>>> very >>>>> convenient for commands that take an expression as their argument, since >>>>> then you don't end up having to backslash yourself to death. See the >>>>> "expression" command for an example of this. >>>>> >>>>> Oh, yeah, another thing, though very trivial, since you defined your >>>>> command with: >>>>> >>>>> eFlagProcessMustBeLaunched | >>>>> eFlagProcessMustBePaused >>>>> >>>>> you don't have to check whether the process & target are valid, the >>>>> command interpreter shouldn't call you if they are not. >>>>> >>>>> Again, thanks for working on this! >>>>> >>>>> Jim >>>>> >>>>> >>>>> > You can also check whether the block you are in is inlined, and if it >>>>> is, then all you do is move the PC to the end of the block. You can't >>>>> really do anything about the return value then, because you can't really >>>>> tell where it is going, but at least you can return properly from the >>>>> inlined function. >>>>> > >>>>> > Hope that helps... >>>>> > I will try that one too, thanks. >>>>> > >>>>> > Regards, >>>>> > >>>>> > Filipe >>>>> > >>>>> > >>>>> > Jim >>>>> > >>>>> > On Jul 22, 2011, at 12:35 PM, Filipe Cabecinhas wrote: >>>>> > >>>>> > > >>>>> > > >>>>> > > On Mon, Jul 18, 2011 at 18:05, Greg Clayton <[email protected]> >>>>> wrote: >>>>> > > On Jul 18, 2011, at 5:23 PM, Filipe Cabecinhas wrote: >>>>> > > >>>>> > > > Hi, >>>>> > > > >>>>> > > > Is there a way to mimic gdb's "return <expr>" command? >>>>> > > >>>>> > > Not if you want to change the return value. >>>>> > > >>>>> > > If you don't want to change the return value you can use "thread >>>>> step-out". "thread step-out" (which is aliased to "finish"), is context >>>>> sensitive to the frame you are currently in, so if you run and stop in a >>>>> frame and then do a "frame select 12", and then to a "thread step-out", >>>>> you >>>>> will return to frame 13. >>>>> > > >>>>> > > Yes, that command will run until the frame returns (like gdb's >>>>> finish command), but what if we want to return immediately? >>>>> > > >>>>> > > > (gdb) help return >>>>> > > > Make selected stack frame return to its caller. >>>>> > > > Control remains in the debugger, but when you continue >>>>> > > > execution will resume in the frame above the one now selected. >>>>> > > > If an argument is given, it is an expression for the value to >>>>> return. >>>>> > > > >>>>> > > > >>>>> > > > I've been looking at the StackFrame class, but it doesn't look >>>>> like it can do that. >>>>> > > > If I wanted to implement it, where should I look first? I can get >>>>> the return address >>>>> (StackFrame.GetRegisterContext().get().GetReturnAddress(), I think) write >>>>> it >>>>> to the PC (StackFrame.ChangePC()), but I have no idea how to get the >>>>> expression's result into the return registers/memory. >>>>> > > >>>>> > > LLDB currently doesn't have any real idea of where the return >>>>> address goes, we currently let the compiler handle all ABI issues by the >>>>> way >>>>> we make expressions. >>>>> > > >>>>> > > There is another issue where if a function isn't external, the >>>>> compiler can make a call to this function and how the function returns the >>>>> value, violate the ABI. In most cases you won't get affected by this, but >>>>> it >>>>> would be nice if we knew for sure from the compiler or debug info where >>>>> the >>>>> return value is. The old ARM compiler used to inject artificial >>>>> DW_TAG_variable debug information entries into the DWARF that would tell >>>>> you >>>>> the result of functions which has a location that describes the returned >>>>> value and where it is. >>>>> > > >>>>> > > >>>>> > > > ClangExpression isn't a big help there, since the result comes to >>>>> debugger-land. >>>>> > > >>>>> > > Yep, and even so there is the issue that internal functions can >>>>> violate the ABI... >>>>> > > >>>>> > > FYI: anything ABI related is currently in the ABI plug-ins: >>>>> > > >>>>> > > lldb/source/Plugins/ABI/* >>>>> > > >>>>> > > The ABI function: >>>>> > > >>>>> > > virtual bool >>>>> > > ABI::GetReturnValue (Thread &thread, >>>>> > > Value &value) const = 0; >>>>> > > >>>>> > > Take a look a the ABIMacOSX_i386 and ABIMacOSX_x86_64 versions of >>>>> this function and see if this does close to what you want. You can also >>>>> fill >>>>> in more functionality inside these for types you want it to support. >>>>> Currently we fill the "value" argument with the result, but we don't fill >>>>> in >>>>> the context (See the "void Value::SetContext (ContextType context_type, >>>>> void >>>>> *p)" function for details, but the ABI::GetReturnValue functions can be >>>>> modified to fill in the register context for return values that are >>>>> returned >>>>> in registers, and the address (See the "Value::SetValueType (...)" >>>>> function) >>>>> if needed. >>>>> > > >>>>> > > These functions currently will attempt to extract the return value >>>>> for a function according to the ABI rules for simple pointer size or less >>>>> types only (no structs, floats, complex etc). So this might help you for >>>>> the >>>>> simple cases. If you were to implement this command you would want to add >>>>> a >>>>> new "return" subcommand in the "thread" multi-word command. In the >>>>> "Execute" >>>>> function of the new "return" command you would want to evaluate an >>>>> expression an store the result, set a breakpoint at the return address, >>>>> install a breakpoint callback and run and hit the breakpoint, then try and >>>>> instert the expression result into the appropriate location (you would >>>>> need >>>>> to modify the "ABI::GetReturnValue(...)" to fill in the "value" param more >>>>> completely with the location of the return type. >>>>> > > >>>>> > > Greg Clayton >>>>> > > >>>>> > > >>>>> > > I implemented a thread return command, which works (right now) for >>>>> integers and pointers, for i386 and x86-64. The command has some caveats >>>>> (like the ones discussed here), but it works (at least) for a few simple >>>>> examples in C. >>>>> > > >>>>> > > "thread return <expr>" returns the result of evaluating that >>>>> expression. I'm not casting the expression, so there may be some problems >>>>> (especially when returning floating point types is implemented). >>>>> > > >>>>> > > But… >>>>> > > We have no idea if the compiler generated a stackframe for this >>>>> function or not. We may be returning from two functions, and not one. >>>>> > > We have no ideia if the compiler changed the calling conventions >>>>> for this code. >>>>> > > We don't know about the callee-saved registers (I suppose there >>>>> isn't a way to find out the epilogue of the function… Especially since it >>>>> may be mixed with "regular code") >>>>> > > >>>>> > > There are a lot more issues for C++ code (e.g: calling dtors). >>>>> > > >>>>> > > I also have some problems updating the state lldb thinks the thread >>>>> is in. >>>>> > > >>>>> > > "register read pc" won't read the real value >>>>> > > "thread backtrace" doesn't get updated. >>>>> > > >>>>> > > How can I fix that? I am also looking for comments on stuff to >>>>> fix/improve. >>>>> > > >>>>> > > I also have some tests (a directory to put in lldb/test/). >>>>> > > >>>>> > > Regards, >>>>> > > >>>>> > > Filipe Cabecinhas >>>>> > > >>>>> > > P.S: Converting between a ValueObject object and >>>>> > > >>>>> <thread-return.patch><thread_return.zip>_______________________________________________ >>>>> > > lldb-dev mailing list >>>>> > > [email protected] >>>>> > > http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev >>>>> > >>>>> > >>>>> >>>>> >>>> >>> >> <frame_return.zip><frame-return.patch> >> _______________________________________________ >> >> lldb-dev mailing list >> [email protected] >> http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev >> >> >> *Enrico Granata* >> ✆ 408.974.5572 | ✉ egranata@.com >> >> >> >> >> >
_______________________________________________ lldb-dev mailing list [email protected] http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev
