Difficulties with using gdb and u-boot efi payload - gdb

I've been sinking days into getting this working with no results. I want to use gdb to debug u-boot on qemu. I am using the 64 bit efi payload of u-boot (in which u-boot is placed in the payload of an efi stub application), and a x86-64 qemu with ovmf firmware. I have two elf files for the debug symbols: u-boot and u-boot-payload. It seems that u-boot contains the symbols for u-boot itself, while u-boot-payload contains symbols for the stub application.
I have been following several guides on how to do this:
https://www.haiku-os.org/blog/kallisti5/2021-01-17_debugging_riscv-64_bootloader_in_qemu/
https://wiki.osdev.org/Debugging_UEFI_applications_with_GDB
My problem is that gdb is never able to hit the breakpoints. I believe the problem is that I can't find the offset I need to load the symbols to. All of these guides mention relocation, and I have tried using the same formula they suggest (<MAXMEM> - SYS_MONITOR_LEN), with no luck. I've tried the addresses that u-boot outputs:
SYS_TEXT = 01110000
UBOOT = 7e36f200
SIZE = 0005cdcf
But none of these worked. I've tried breaking in functions in the stub and u-boot itself, but nothing ever works. I've been going at this for so long its honestly hard for me to recall everything I've tried accurately, but I've run out of ideas.
Is there some underlying assumption I've made that's tripping me up, or is it really just that I'm using the wrong offset? I've read that u-boot relocates, but what I don't understand is what address it relocates to and when. Does the stub relocate, or does relocation happen before the stub runs? These are all things I haven't found any clarification on.
Anything feedback helps, it's hard for me to ask a more specific question because I'm not sure what I'm doing wrong.

Figured it out! The required argument for add-symbol-file comes from common/board_f.c after the setup_reloc function runs, the value of gd->relocaddr will contain the value you need for add-symbol-file.
The other problem I was having is that you need to use hbreak instead of break in gdb. This is a "hardware assisted" breakpoint, and for some reason all of the guides online I saw fail to mention this. I hope someone else finds this useful

Related

get c++ function name from !DllRegisterServer+0x3ebfa notation to solve 'endless wait in critical section' puzzle

I'm new in debugging with symbols (when no access to the testing machine is possible).
I already provided the client with Debug build with .pdb file but for some reason the dump file I get contains no entries specific to my .dll (although the customer insists the problem occurs there, in particular, the app hangs). The debug build was made with VC++ 2008 x86 (I also tried older VC++ 6.0 with no difference).
The stack trace customer provides looks like
ChildEBP RetAddr
01ece854 773f8e44 ntdll!NtWaitForSingleObject+0x15
01ece8b8 773f8d28 ntdll!RtlpWaitOnCriticalSection+0x13e
01ece8e0 02a92003 ntdll!RtlEnterCriticalSection+0x150
WARNING: Stack unwind information not available. Following frames may be wrong.
01ece8f0 02a8b4fa MyDllName!DllRegisterServer+0xbd2dc
01ece920 02a8b49e MyDllName!DllRegisterServer+0xb67d3
01ece930 02a8746c MyDllName!DllRegisterServer+0xb6777
01ece93c 029dc5ca MyDllName!DllRegisterServer+0xb2745
01ece99c 02a819e4 MyDllName!DllRegisterServer+0x78a3
01ecea80 02a09776 MyDllName!DllRegisterServer+0xaccbd
01eceb00 02a32506 MyDllName!DllRegisterServer+0x34a4f
01eceb58 029f44bf MyDllName!DllRegisterServer+0x5d7df
01ececdc 029f5e20 MyDllName!DllRegisterServer+0x1f798
01eceda0 029f76da MyDllName!DllRegisterServer+0x210f9
01ecedf4 291fe0ce MyDllName!DllRegisterServer+0x229b3
01ecee98 29365243 ClientAppName!Class.Method2+0x262
01eceeb8 293378d9 ClientAppName!Class.Method1+0x37
But I'm not sure what all of this exactly means. Does DllRegisterServer+0x229b3 mean "function which has address +229b3 to the address of DllRegisterServer in map file"?
In map file, I have something like
0002:0006d720 _DllRegisterServer#0 10137720 f DllName.obj
But when I sum 229b3 and 6d720, I don't have any match in the map file for the resulting value.
And why the stack trace shows DllRegisterServer as an address base? It's not the first address in the map file. There are many function before it, should they have negative offset then (seems meaningless)?
I guess I understand reading debugging things wrong, but can't figure out what exactly is wrong..
If I could find out the function names, this would let me move further.
Things get even more complicated as I don't think my .DLL has no critical sections but the customer insists it's my dll which causes entering a critical section and never getting out. For now, I don't yet know how to prove him wrong (or maybe find out that it's indeed my lib which somehow, indirectly, does this, maybe, Windows sockets or DNS resolve name to an IP address somewhere behind the scenes are using critical sections).
This recent blog post by Raymond Chen is exactly the answer you're looking for: Restoring symbols to a stack trace originally generated without symbols.
For some reason, the debugger (or whatever is producing that stack trace) is failing to find the debug symbols for your module, so it's doing the best it can with only the DLL's export table. To paraphrase Raymond:
Ugh. A stack trace taken without working symbols. (There's no way
that DllRegisterServer is a deeply recursive 750 KB function. Just by
casual inspection, you know that the symbols are wrong.)
To see how to fix this, you just have to understand what the debugger
does when it has no symbols to work from: It uses the symbols from the
exported function table. For every address it wants to resolve, it
looks for the nearest exported function whose address is less than or
equal to the target value.
Assuming you have the correct, matching symbols file (.pdb) for the version of the DLL that generated the stack trace, you can trick the debugger into loading the DLL as if it were a process dump, and then you can load the symbols for it:
C:> ntsd -z MyDllName.dll
NTSD is the Microsoft NT Symbolic Debugger, which is installed by default on all modern Windows versions. You can also use WinDbg, but I'm not sure if there's a way to use Visual Studio with this technique.
Once you've got the DLL loaded into the debugger with symbols, you can then let the debugger do the heavy lifting to decode the stack trace. See the blog post for more detailed examples of that.
I'd guess that your DLL is badly behaved and you're deadlocking on the loader lock.
See "Another reason not to do anything scary in your DllMain: Inadvertent deadlock" here

Generic log for application crash C++/MFC

We have a problem for which I am looking for a direction. We have an old MFC based application, and due to various reasons, the application is crashing sometimes intermittently in some weird scenarios. And even the customers who are using our application and getting these crashes are finding difficulty in identifying the pattern of crash. So, I had a thought that, if we can have a mechanism by which we can generate a log whenever the application crashes. Like for example, the call stack or any other information in that log. I know,, we can use the crash dump in this case, but then I feel like having a log is a better option. So any help or information in this regard would be really helpful.
Thank you.
You can find a good implementation of crash reporter in the link here.
When you compile your release build, make sure that both DEBUG and /MAP are enabled. Store your binaries together with your .map files and let your customer run this version until a crash is produced. In the Event Viewer you will then find a crash log with a crash offset. Then debug step into your code (F10) and use the crash offset together with some nifty tricks and tricks to jump (set the EIP register to... well, you have to google this a bit) to the location where the crash occurred. You should now be able to find the error!

mysql++ connections always returning 0 rows ever since reboot

this might be something obvious but i cannot for the life of me figure it out. Ever since we did a server reboot, a C++ program using mysql++ to connect to our database has just returned 0 rows for all queries instantly. My first thought was that my.cnf might not have been loaded correctly but it appears that it was, after checking show variables and comparing.
any suggestions? is it possible that some directory setting is failing to find some .so needed for mysqlpp that I don't know about?
any advice appreciated.
any suggestions?
Sure:
Ensure that you're checking all error code returns if you've disabled exceptions.
If you haven't disabled exceptions, check that each catch block that could be involved isn't just quietly eating the error.
The MySQL C API library (and therefore MySQL++) is probably trying to tell you what went wrong, and you're suppressing it or ignoring it somehow.
Build and run the examples. If they fail in the same way as your program, it means the problem is broad in nature. The examples have good diagnostics, so they may guide you to the problem.
If the examples work fine, then the problem is specific to your program or its data. So, separate the cases:
Does the program work on a different machine against a DB with the same structure as the problem machine, but different contents?
If so, does it still work on that machine when you load a copy of the problem DB into the second machine?
And if that still works, does it work when you access the remote machine's DB directly from the system that does work? (Be careful with this one. You want to have SSL set up on the MySQL DB connection itself, or have some kind of secure channel to it, like a VPN or SSH tunnel.)
If you run that gauntlet successfully, it means the problem is with the program itself on the original machine, or with the program's environment. Libraries or permissions, as you've speculated, are one possibility.
Run your program under a debugger.
Try gdb first, because what we're interested in is whether the debugger sees any exceptions or signals thrown. Maybe the program is core dumping, for example.
If gdb gives the program a clean bill of health, try valgrind. If Valgrind complains about your program, chances are good that it's complaining about something legitimate; maybe harmless, but legitimate. If you get complaints, and you found above that the problem is specific to one machine, I recommend re-trying the Valgrind run on the system where the program runs successfully. Fix those problems, or at least rule out the harmless warnings before continuing debugging on the original problem machine.
is it possible that some directory setting is failing to find some .so needed for mysqlpp that I don't know about?
It's easy to check:
$ ldd myprogram
You should get a report listing all the shared libraries your program is linking to, including their full paths. Any that are missing or unreadable by the user running ldd will be indicated.

Getting PEB from remote process in Win 7

Specs: Windows 7 x64, Visual C++
Objective: I'm trying to get the remote PEB from a sample program (calc.exe e.g.). I've found the proc ID and I've opened a handle to the process with all the good rights. I've now moved on to writing a class to retrieve the location of the PEB from the process using PROCESS_BASIC_INFORMATION.
Problem: I've found several posts elsewhere that seem to indicate that the NtQueryInformationProcess turned to shit at MS. One post suggests a method of dynamic-runtime-linking NtQueryInformationProcess out of ntdll.dll. However, I think this would be unstable in the long-run (MS could remove NtQueryInformationProcess tomorrow) without extensive error handling.
This idea is realized later in this thread, and it is then suggested by Mike2343 that one should "use other methods."
Questions: What would be another method to locate the PEB of a remote process that doesn't involve NtQueryInformationProcess?
Thanks to anyone who spends any time looking at this.
Method I ended up using:
I stole pretty much all of this code and fixed it up for 64-bit. I spent a ton of time wrapping my head around various documents related to all of the different headers and structs. I also ran into an issue regarding the PE32+ format, where jcopenha was kind enough to enlighten me on a few problems I might be facing. After accounting for these problems I had a functioning program that is capable of obtaining a list of all the DLL's and their respective functions loaded in by an executable along with their relative addresses.
In retrospect, I don't think I had a good handle on what I was attempting to do. I think that I thought I was going to read in a process out of memory and find the PEB related structs or something (Later I found out that image headers and the like account for the information in the PEB). Albeit that may be possible, but what I have now is an offline example that reads in exe files and works for me.

How can I debug a program when debugger fails

I am debugging an Iphone program with the simulator in xCode and I have one last issue to resolve but I need help resolving it for the following reason: when it happens the program goes into debugging mode but no errors appear (no BAD ACCESS appears) and it does not show where the code fails. Putting some variables as global helps me to see their values to start pin pointing where the bug is but before I go into this fully I would like to know what techniques/tools you guys use to debug these situations.
If it helps Im debugging the following: I merged some code into the SpeakHere demo. The code was added in the C++ modules of the program (AQRecorder.h and .mm). I seem to have pinpointed the problem code in a function I wrote.
My favourite is always to add debugging code and log it to a file. This allows me so report any and all information I need to resolve the issue if the debugger is not working properly.
I normally control the debugging code by use of a flag which I can manipulate at run time or by the command line.
If the error is (and it probably is) a memory management issue, printing log entries is really not going to help.
I would reccomend learning how to use Instruments, and use its tools to track down the memory leak when it occurs rather than waiting until the application crashes later on.