Modifying the debug information of llvm IR - llvm

I want to modify debug information of an llvm instruction so that the
modified debug info is subsequently passed to executable binary. So if I
use "addr2line" utility on the binary, it will return my modified debug
information.
I've tried to change by using the following code snippet:
MDNode *N = Inst->getMetadata("dbg");
DebugLoc Loc = DebugLoc::get(newLine, newCol, N);
Inst->setDebugLoc(Loc);
I read the DebugLoc back by using
const DebugLoc D = Inst->getDebugLoc();
unsigned Line = D.getLine();
outs() << Line <<"\n";
But I can't set the debug info correctly. How can I change the debug
info correctly through llvm pass?

Related

fopen_s returns error code 2 with system account and win 32 but works fine on winx64 (c++)

I have a cpp program that uses fopen_s to open and read a file created under the directory C:\Windows\System32\config\systemprofile\AppData\Roaming.
My program needs to be compatible with winx64 and win32.
When I run this program with a system account (run using PSTools\PSExec -i -s C:\windows\system32\cmd.exe) and the Win32 compiled version of the program, fopen_s() on any file inside "C:\Windows\System32\config\systemprofile\AppData\Roaming" returns an error code 2, even though the file is present.
However, when I run the x64 compiled version of the same program, it works fine and fopen_s() is able to find and open the same file.
I am sure there are no mistakes as far as passing a valid filename to fopen_s() and I have verified this.
I make sure that the int variable that stores the return value from fopen_s() is set to 0 every time before calling fopen_s(). I am calling fopen_s() in "r" mode.
Also, elsewhere in the same program I am able to create files under the same directory.
I am using VS2019 and cpp +11 to compile my program.
My system is running windows 10 (64-bit) on an x64 processor (Intel(R) Xeon(R) Gold 6136)
Why would a win32 application fail to read a file created under "C:\Windows\System32\config\systemprofile\AppData\Roaming" with a system account while the x64 version of the same application works fine?
Code snippet:
int FileOpenFunc(FILE ** ppFile, std::string sFilename, std::string sOpenMode)
{
int errOpen = 0;
#ifdef _WIN32
errOpen = fopen_s(ppFile, sFilename.c_str(), sOpenMode.c_str());
#else
*ppFile = fopen(sFilename.c_str(), sOpenMode.c_str());
errOpen = errno;
#endif
return errOpen;
}
void func()
{
std::string sFileName = "C:\\Windows\\System32\\config\\systemprofile\\AppData\\Roaming\\Check\\sample.txt";
int errFopenErrNo = 0;
FILE* fp = NULL;
errFopenErrNo = FileOpenFunc(&fp, sFileName, "r");
if (fp!= NULL)
{
//do something
}
else
{
//do something else
}
}

how to call a func with parameters from an executable using gdb

I need help running a program in an executable using GDB.
I have an executable file name vuln. I do not know the source code as I am doing a CTF. When I analyzed the executable, I found three exciting functions: main, vuln, and flag. Vuln func is vulnerable to BOF attack, but I do not want to go that way. What I am trying to do is run the executable in gdb, and I used print (void) flag(param1, param2) command to directly run flag func as this is supposed to give me a flag; however, it does not work as it says my parameters are incorrect which I am sure are not. I have also found out about the jump function, but I cannot pass any parameters.
So is there any way to run a function from executable with parameters properly or I would have to go through the pain of BOF.
GHIDRA disassembled code of FLAG and VULN Func are below.
void flag(int param_1, int param_2){
char local_50 [64];
FILE *local_10;
local_10 = fopen("flag.txt", "r");
if(local_10 != (FILE *)0x0){
fgets(local_50, 0x40, local_10);
if ((param_1 == -0x21524111) && (param_2 == -0x3f212ff3)){
printf(local_50);
}
return;
}
puts("Hurry up and try in on server side.");
exit(0);
}
void vuln(void)
{
char local_bc [180];
gets(local_bc);
puts(local_bc);
return;
}
print (void) flag(param1, param2)
Not sure what your values of param1 and param2 are, but this seems to work just fine for me:
echo "hello" > flag.txt
gdb -q ./a.out
(gdb) start
Temporary breakpoint 4 at 0x555555555307
Starting program: /tmp/a.out
Thread 1 "a.out" hit Temporary breakpoint 4, 0x0000555555555307 in main ()
(gdb) p (void)flag(-0x21524111, -0x3f212ff3)
hello
$2 = void
(gdb)

VLOG doesn't work for Google Logging Library (glog)

My purpose is simple: to somehow see the logs printed by VLOG(5), which is provided by the glog library.
I have the following code:
google::InitGoogleLogging(argv[0]);
google::ParseCommandLineFlags(&argc, &argv, true);
FLAGS_logtostderr = 1;
FLAGS_v = 10;
LOG(INFO) << "info"; // OK, I see it
LOG(WARNING) << "warning"; // OK
VLOG(5) << "vlog"; // Nothing :(
No matter I manually set the flags here (FLAGS_logtostderr and FLAGS_v) or I pass it through the command line (--v=10), I just never find the string "vlog" anywhere: neither stdout, stderr nor some log file under \tmp. I think I didn't change the output path though.
Do I miss anything here? Any idea how to enable VLOG?
Personally, I've never tried it with
FLAGS_logtostderr = 1;
FLAGS_v = 10;
The VLOG works fine for me if I set "GLOG_v=x" as an environmental variable on both linux and windows. E.g.
Alternatively, if you want to test it on the command line you can do the following:
Windows:
C:>set GLOG_v=5
C:>set GLOG_logtostderr=1
C:>YourProgramName
Linux:
$ GLOG_v=7 GLOG_logtostderr=1 ./YourProgramName

C++, debugging symbols and GDB

We developed a dynamic library L.so and an executable X which uses it. Both compiled with debugging info. While running gdb X:
Reading symbols from X...Segmentation fault (core dumped)
The X contains from 4 objects and I found out which one causes the crash. Lets say, if S.cpp is compiled, it crashes in gdb. S.cpp:
class Service {
private:
...
private:
...
LongTaskService longTaskService_; // Implementation is in L.so
If I remove this method from S.cpp, the crash disappears:
bool Service::downloadFile(const string &mapName, int &taskId) {
Properties dProps;
if(!config_.get("downloadService", dProps)) {
LOGG(Logger::ERROR) << "Failed to get config props for downloadService" << Logger::FLUSH;
return false;
}
string url = dProps.get("downloadUrl");
if(url == "") {
LOGG(Logger::ERROR) << "Failed to get url for downloadService" << Logger::FLUSH;
return false;
}
if(url[url.size()-1] != "/")
url += "/";
LOGG(Logger::DEBUG) << "Initializing download from "<< url << mapName << Logger::FLUSH;
URL dUrl(url+mapName);
vector<string> outPath = {workDir_, mapName};
URL outFile(FsUtil::makePath(outPath));
taskId = longTaskService_.submit(DownloadTask::run, dUrl, outFile); // This line causes problems
return true;
}
I wonder why is it like this and can I avoid the crash while debugging?
The usual thing to do here is run "gdb gdb" and then file a bug report with the stack trace.
Another possibility is that you could try updating to a newer version of gdb. That might help.
Anyway it is just a bug. Very new versions of gdb have a bit of protection against some crashes of this sort; but protecting against all crashes is hard.

"Access violation" Error on displaying string of simple Oracle Query (VS10 Exp C++)

I am struggling with an issue regarding running a SQL statement to an Oracle database through C++, using occi. My code is as follows:
#include <iostream>
#include "occi.h"
namespace oc = oracle::occi;
int main() {
std::cout << "Setting up environment...\n";
oc::Environment * env = oc::Environment::createEnvironment();
std::cout << "Setting up connection...\n";
oc::Connection * conn = env->createConnection("user","pass","server");
std::cout << "Creating statement...\n";
//Very simply query...
oc::Statement * stmt = conn->createStatement("SELECT '1' FROM dual");
std::cout << "Executing query...\n";
oc::ResultSet * rs = stmt->executeQuery();
while(rs->next()) {
std::cout << rs->getString(1) << std::endl; //Error is thrown at this line, but after printing since I can see '1' on the console.
}
stmt->closeResultSet(rs);
conn->terminateStatement(stmt);
env->terminateConnection(conn);
oc::Environment::terminateEnvironment(env);
return 0;
}
The error that is shown is:
Unhandled exception at 0x1048ad7a (msvcp100d.dll) in MyDatabaseApp.exe: 0xC0000005: Access violation reading location 0xccccccd0.
My program stops inside 'xstring' at the following line of code:
#if _ITERATOR_DEBUG_LEVEL == 0
....
#else /* _ITERATOR_DEBUG_LEVEL == 0 */
typedef typename _Alloc::template rebind<_Elem>::other _Alty;
_String_val(_Alty _Al = _Alty())
: _Alval(_Al)
{ // construct allocator from _Al
....
}
~_String_val()
{ // destroy the object
typename _Alloc::template rebind<_Container_proxy>::other
_Alproxy(_Alval);
this->_Orphan_all(); //<----------------------Code stops here
_Dest_val(_Alproxy, this->_Myproxy);
_Alproxy.deallocate(this->_Myproxy, 1);
this->_Myproxy = 0;
}
#endif /* _ITERATOR_DEBUG_LEVEL == 0 */
If I change my query to:
oc::Statement * stmt = conn->createStatement("SELECT 1 FROM dual");
and the loop statement to:
std::cout << rs->getInt(1) << std::endl;
It works fine with no errors. I think this is because getting an integer simply returns a primitive, but when an object is being returned it is blowing up (I think on a destructor, but I'm not sure why...)
I have been playing around with this for hours today, and I am pretty stuck.
Some information about my system:
OS - Windows XP
Oracle Version - 10g
IDE - Microsoft Visual Studio 2010 Express C++
My project properties are as follows:
C/C++ - General - Additional Include Directories = C:\oracle\product\10.2.0\client_1\oci\include;%(AdditionalIncludeDirectories)
C/C++ - Code Generation - Multi-threaded Debug DLL (/MDd)
Linker - General - Additional Library Directories = C:\oracle\product\10.2.0\client_1\oci\lib\msvc\vc8;%(AdditionalLibraryDirectories)
Linked - Input - Additional Dependencies = oraocci10.lib;oraocci10d.lib;%(AdditionalDependencies)
I hope I haven't been confusing with too much info... Any help or insight would be great, Thanks in advance!
EDIT If I rewrite my loop, storing the value in a local variable, the error is thrown at the end of the loop:
while(rs->next()) {
std::string s = rs->getString(1); //s is equal to "1" as expected
std::cout << s << std::endl; //This is executed successfully
} //Error is thrown here
Usually such kind of problems come from differences in build environments (IDE) of end user and provider.
Check this.
Related problems:
Unhandled exception at 0x523d14cf (msvcr100d.dll)?
Why does this program crash: passing of std::string between DLLs
First try to use correct lib and dll. If compiled in debug mode then all libs and dlls must be debug. Use VC++ Modules view to be sure that proper DLL loaded.
I was lucky with my application to have all libs compiled for MSVC2010. So I just check debug and release mode DLLs and got working application.
I revisited this issue about a month ago and I found that the MSVC2010 occi library was built for Oracle 11g. We are running Oracle 10g, so I had to use the MSVC2005 library. So I installed the outdated IDE and loaded the Debug library and it worked (for some reason the release version wouldn't work though).
EDIT
For anyone who is having the same problem I was, if downgrading the IDE from MSVC2010 to MSVC2005 with the appropriate libraries doesn't work, you could try upgrading the Oracle client from 10g to 11g and use the MSVC2010 library, as suggested by harvyS. In retrospect this would've probably been the better solution.