I got a situation on ARM controller, where in the underlying OS layer, an exception is reported by calling osException(). The caller of this function also passes the pc(program counter). I have set a breakpoint on osException() and can print the value of pc on trace32 AREA. Further, I would like to focus the Trace32 view to the source code where this program counter is pointing to. How can I do it using a trace32 scripts ?
I think the command you are searching for is
List Var.VALUE(pc)
The command List [<address>] opens a windows showing the target application a the given address. If you omit the parameter , the window will focus on the address, where the current program counter is pointing to. (The current program counter point of course somewhere inside osException())
The function Var.VALUE(<HllExpr>) returns the value of the given high-level-language expression. So if you have a variable pc it return the value of this variable for all TRACE32 commands not starting with Var.
Related
I'm new to c++ debugging and LLDB. I'm using VSCode with its c++ adapter, LLDB as the debugger, and bazel as the build system. My application deals with manipulating images. The application runs quickly but debugging it is very slow. That's because once I've loaded the images into memory, it takes about 20 seconds to a minute to step through each line. My assumption is that the raw images are too much for the debugger. If I use a small image, then I'm able to step through the code quickly inside the debugger
My question is: is there a way to tell the debugger to ignore the image loaded variables? Or perhaps to lazy-load the image variable data? I'm more interested in the other variables such as the matrices.
The underlying debugger, lldb, doesn't fetch any variables unless explicitly asked. It's always the UI that requests variable values.
In Xcode, if you close the Locals View, Xcode won't ask lldb to fetch variables. That does speed up stepping in frames with big local variables.
Then if you need to keep an eye on one or two of the variables while stepping you can use tooltips or the debugger console to print them on demand. You can also set up target stop-hooks in the lldb Console and use them to auto-print the variables you are tracking.
Some UI's also separate the "Locals" view from the "Watched Expression" view, so you can close the former and put the variables you need to see in the latter.
I don't know if VSCode allows you to close the Locals view, but if it does that might be a way to handle this problem.
I am dealing with a large code base with tons of globals. Under some peculiar set of data it produces the wrong result. I wanted to automatically run few scenarios with gdb in automatic step-by-step execution and periodical dumping
of some values and recording the tracing in some file. Doing it manually will ruin my sight and my brain. I speculate that there is some globals mess-up. How to do this automatically? Use some scripting. All this is in RH linux.
Thanks in advance.
tried to do this manually using conditional breaks, but gave up after a while
I wanted to automatically run few scenarios with gdb in automatic step-by-step execution and periodical dumping of some values and recording the tracing in some file.
It may be significantly more effective to run the program under reverse debugger (such as rr), and trace the wrong result back to its source.
How to do this automatically?
You can't do automatically what you can't express as an algorithm, and you haven't described an algorithm you want to use. If it's something like "stop every 100 times foo is called and print the values of these 500 globals", than that's trivially automatable with GDB.
More complicated algorithms are possible with the use of embedded Python.
In the .gdbinit file in your home folder add
add-auto-load-safe-path /path_to_the_folder_containing_your_executable/
Now you can create another .gdbinit file in the same folder where your executable is that will be loaded when you start gdb from there (the .gdbinit file in your home that is also read - useful if you have nice stuff there such as loading pretty printers).
In this .gdbinit file, add the code below
file your_executable_name
start
# Optional
set args "<any command line parameters you program might need>"
# xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
# Add gdb commands below to set breakpoints, print variable values, etc
# xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
run
Gdb is very powerful and I'll list a few things that might help this automation.
You can set breakpoints with b filename.ext:line_number or b function_name
You can use commands breakpoint_number (see here) and then list commands that should be run after this breakpoint is hit. Use end to finish the commands
You know the breakpoint number, since they are created sequencially (note that the start will count as a breakpoint and thus the first one you add will be breakpoint 2)
You can use convenience variables to store useful things such as the address of an important object
The python api is very powerful
One idea is that you can save the address of the important global variables (if they are not always accessible) using convenience variables. For instance, add a breakpoint where this global variable is and then add to this breakpoint the command to save the address of this variable to a convenience variable followed by continue (with continue you will not see gdb stopping there).
set $var1 = &myglobal
continue
You might want to also delete this breakpoint with delete breakpoint_number before continue to avoid stopping at this breakpoint again.
Then as long is the object exists you can inspect it using p $var1 or p $var1->something when the program is stopped at a different breakpoint where myglobal might not be directly accessible.
In the commands that you add to be run when a breakpoint is hit you can do things such as echo message explaining where you are, p some_var to see the values of variables or even python some_complicated_python_code.
In the case you want to use python for more power it is worth reading the section about it in the manual. Let-me give you one example. Suppose one of your global variables was stored in a convenience variable called "$myvar". Then you can pass it to the python interpreter with
python myvar = gdb.parse_and_eval("$myvar")
You can also pass any variable in the current scope to parse_and_eval.
Now, suppose this global variable stores an object of a class with a "n_elem" attribute you want to check. You can print it with
python print(myvar["n_elem"])
You can also create a python file in the same folder and use
python from my_python_file import *
to import functions defined there.
With these gdb features you can pretty much automate whatever you might need.
I need to set a local environment variable for current user and it shoukd be visible to other processes like a new command prompt. I need it for windows. I have tried options like putenv and editing the registry from C++ code but the new cmd prompt see the old values. Primarily i need to edit PATH variable along with few custom env variables. Will appreciate if i can get a working sample code.
Please note that the environment variable need to persist past program execution.
My requirement is for windows. I even tried running setx from C++ code and it works fine but for PATH variable it trims it down to 1024 character and i lose the update. Is there a workaround to this?
IF my wording looks confusing about the requirement. I need exactly same behavior as if i am using setx.
Thanks in advance.
If you start Cmd.exe from your process you can control its environment. The environment variables are inherited from the parent process. They can also be overridden when you call CreateProcess.
If you change the users/system environment configuration in the registry(HKCU\Environment/HKLM\SYSTEM\CurrentControlSet\Control\Session Manager\Environment) and log off/reboot then the first process will use these new defaults.
If you update the registry you can tell other applications to refresh their environments without logging off by broadcasting a message:
BroadcastSystemMessage(0, 0, WM_SETTINGCHANGE, 0, (LPARAM)TEXT("Environment"));
In reality it is only Explorer.exe that reacts to this message but that is enough to affect new applications started from the taskbar/start menu.
The setx command is actually an executable that sets values in the registry. If you are looking to simulate the behavior where you can set an environment variable that will last longer than the current process you will need to write it to the HKCU\Environment key. The HKCU is for the the current user and can be written to without elevated permissions.
Use RegEdit.exe or reg.exe query HKCU\Environment to view the current settings. From C/C++ you can use the Registry functions. If you can, I recommend using the ATL CRegKey class as it follows RAII and ensures handles are properly cleaned up.
I have 2 cpp GUI applications P1 and P2. P1 can be opened by two ways.
Through directly double clicking or using command line
Using P2's GUI, implemented using the CreateProcess function (https://msdn.microsoft.com/en-us/library/windows/desktop/ms682425(v=vs.85).aspx), using default flags.
P1 has a file selection box, which is implemented using SHBrowseForFolder (https://msdn.microsoft.com/en-us/library/windows/desktop/bb762115(v=vs.85).aspx), using default flags.
In windows 8.1 the file selection box shows several shortcuts under 'This PC' dropdown (Desktop, Pictures, Downloads etc).
If I use method 1 to open P1 these shortcuts expand fine.
But if I use method 2, while expanding these shortcuts it shows the following error in a dialogue box.
C:\Windows\system32\config\systemprofile\Desktop refers to a location that is unavailable. It could be on a hard drive on this computer or on a network. Check to make sure that the disk is properly inserted, or that you are connected to the Internet or your network, then try again. If it still cannot be located, the information might have been moved to a different location
Please help guys. Stuck in this for last two days.
EDIT: Just found out the following.
Process P2 is opened by a system level process in the start up. If I close P2 and reopens it as a user, error is gone ,the file selection works fine.
Found out the issue. I was creating processes using CreateProcess function with default flags. One of the argument is environmental block, for which I passed NULL. So the new process will be created with parent processes environmental variable. So in the startup P2 is created by a system level process with environmental variables of system. Ans P2 will create P1 with same environmental variables. So when expanding shortcuts P1 will look for the USERPROFILE variable in the environmental block, which will be systemprofile.
When I open P2 as a user environmental variables are set correctly and shortcuts expands properly.
May this be helpful for someone in future.
I would like to write a program that sets an environment variable in an instance of the shell (cmd.exe) it was called from. The idea is that I could store some state in this variable and then use it again on a subsequent call.
I know there are commands like SetEnvironmentVariable, but my understanding is that those only change the variable for the current process and won't modify the calling shell's variables.
Specifically what I would like to be able to do is create a command that can bounce between two directories. Pushd/Popd can go to a directory and back, but don't have a way of returning a 2nd time to the originally pushed directory.
MSDN states the following:
Calling SetEnvironmentVariable has no
effect on the system environment
variables. To programmatically add or
modify system environment variables,
add them to the
HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session
Manager\Environment registry key, then
broadcast a WM_SETTINGCHANGE message
with lParam set to the string
"Environment". This allows
applications, such as the shell, to
pick up your updates. Note that the
values of the environment variables
listed in this key are limited to 1024
characters.
Considering that there are two levels of environment - System and Process - changing those in the shell would constitute changing the environment of another process. I don't believe that this is possible.
A common techniques is the write an env file, that is then "call"ed from the script.
del env.var
foo.exe ## writes to env.var
call env.var
In Windows when one process creates another, it can simply let the child inherit the current environment strings, or it can give the new child process a modified, or even completely new environment.
See the full info for the CreateProccess() win32 API
There is no supported way for a child process to reach back to the parent process and change the parent's environment.
That being said, with CMD scripts and PowerShell, the parent command shell can take output from the child process and update its own environment. This is a common technique.
personly, I don't like any kind of complex CMD scripts - they are a bitch to write an debug. You may want to do this in PowerShell - there is a learning curve to be sure, but it is much richer.
There is a way...
Just inject your code into parent process and call SetEnvironmentVariableA inside
cmd's process memory. After injecting just free the allocated memory.