3 This file is part of gldbg
4 Copyright © 2009, 2011 Mikko Rasa, Mikkosoft Productions
5 Distributed under the GPL
13 #include <sys/ptrace.h>
16 #include "strformat.h"
20 Process::Process(const vector<string> &a):
26 void Process::setenv(const string &key, const string &value)
31 void Process::launch()
34 throw logic_error("Program is already running");
39 for(map<string, string>::const_iterator i=env.begin(); i!=env.end(); ++i)
40 ::setenv(i->first.c_str(), i->second.c_str(), true);
41 std::vector<char *> argv(args.size()+1);
42 for(unsigned i=0; i<args.size(); ++i)
43 argv[i] = strdup(args[i].c_str());
44 argv[args.size()] = 0;
45 ::ptrace(PTRACE_TRACEME, 0, 0, 0);
46 execvp(argv[0], &argv[0]);
52 throw runtime_error(strformat("Could not launch process: %s", strerror(errno)));
58 int ret = waitpid(pid, &status, WNOHANG);
63 int code = WEXITSTATUS(status);
67 else if(WIFSIGNALED(status))
70 return 0x200|WTERMSIG(status);
72 else if(WIFSTOPPED(status))
74 int sig = WSTOPSIG(status);
75 if(sig==SIGTRAP && state==STARTING)
77 ptrace(PTRACE_CONT, 0, 0);
91 void Process::resume(int sig)
94 throw logic_error("Program is not stopped");
95 ptrace(PTRACE_CONT, 0, (void *)sig);
102 throw logic_error("Program is not running");
103 ptrace(PTRACE_KILL, 0, 0);
104 // Make the debugger wait() for us
108 long Process::ptrace(int req, void *addr, void *data)
110 int ret = ::ptrace((__ptrace_request)req, pid, addr, data);
111 if(ret==-1 && ((req!=PTRACE_PEEKTEXT && req!=PTRACE_PEEKDATA && req!=PTRACE_PEEKUSER) || errno))
112 throw runtime_error(strformat("ptrace error: %s", strerror(errno)));