X-Git-Url: https://git.saurik.com/cycript.git/blobdiff_plain/9185d5ef70289d99e212f2dd04457b05716e222e..032e971ea180d9e7f9df03887bedd233c8d5c537:/Console.cpp diff --git a/Console.cpp b/Console.cpp index 503a3e8..77e9759 100644 --- a/Console.cpp +++ b/Console.cpp @@ -62,6 +62,9 @@ #include #include #include +#include + +#include static volatile enum { Working, @@ -110,11 +113,11 @@ void Setup(CYOutput &out, CYDriver &driver) { driver.program_->Replace(context); } -void Run(int socket, const char *data, size_t size, FILE *fout = NULL, bool expand = false) { +void Run(int client, const char *data, size_t size, FILE *fout = NULL, bool expand = false) { CYPool pool; const char *json; - if (socket == -1) { + if (client == -1) { mode_ = Running; #ifdef CY_EXECUTE json = CYExecute(pool, data); @@ -126,15 +129,15 @@ void Run(int socket, const char *data, size_t size, FILE *fout = NULL, bool expa size = strlen(json); } else { mode_ = Sending; - CYSendAll(socket, &size, sizeof(size)); - CYSendAll(socket, data, size); + CYSendAll(client, &size, sizeof(size)); + CYSendAll(client, data, size); mode_ = Waiting; - CYRecvAll(socket, &size, sizeof(size)); + CYRecvAll(client, &size, sizeof(size)); if (size == _not(size_t)) json = NULL; else { char *temp(new(pool) char[size + 1]); - CYRecvAll(socket, temp, size); + CYRecvAll(client, temp, size); temp[size] = '\0'; json = temp; } @@ -167,11 +170,24 @@ void Run(int socket, const char *data, size_t size, FILE *fout = NULL, bool expa } } -void Run(int socket, std::string &code, FILE *fout = NULL, bool expand = false) { - Run(socket, code.c_str(), code.size(), fout, expand); +void Run(int client, std::string &code, FILE *fout = NULL, bool expand = false) { + Run(client, code.c_str(), code.size(), fout, expand); } -static void Console(int socket) { +static void Console(apr_pool_t *pool, int client) { + passwd *passwd; + if (const char *username = getenv("LOGNAME")) + passwd = getpwnam(username); + else + passwd = getpwuid(getuid()); + + const char *basedir(apr_psprintf(pool, "%s/.cycript", passwd->pw_dir)); + const char *histfile(apr_psprintf(pool, "%s/history", basedir)); + size_t histlines(0); + + mkdir(basedir, 0700); + read_history(histfile); + bool bypass(false); bool debug(false); bool expand(false); @@ -225,6 +241,7 @@ static void Console(int socket) { fflush(fout); } add_history(line); + ++histlines; goto restart; } } @@ -278,6 +295,7 @@ static void Console(int socket) { std::cerr << error->message_ << std::endl; add_history(command.c_str()); + ++histlines; goto restart; } } @@ -292,7 +310,7 @@ static void Console(int socket) { if (driver.program_ == NULL) goto restart; - if (socket != -1) + if (client != -1) code = command; else { std::ostringstream str; @@ -304,13 +322,17 @@ static void Console(int socket) { } add_history(command.c_str()); + ++histlines; if (debug) std::cout << code << std::endl; - Run(socket, code, fout, expand); + Run(client, code, fout, expand); } + _syscall(close(_syscall(open(histfile, O_CREAT | O_WRONLY, 0600)))); + append_history(histlines, histfile); + fputs("\n", fout); fflush(fout); } @@ -332,7 +354,9 @@ static void *Map(const char *path, size_t *psize) { return base; } -int main(int argc, char *argv[]) { +void InjectLibrary(pid_t pid); + +int Main(int argc, char const * const argv[], char const * const envp[]) { bool tty(isatty(STDIN_FILENO)); bool compile(false); @@ -340,70 +364,128 @@ int main(int argc, char *argv[]) { pid_t pid(_not(pid_t)); #endif - for (;;) switch (getopt(argc, argv, - "cg:n:" + CYPool pool; + apr_getopt_t *state; + _aprcall(apr_getopt_init(&state, pool, argc, argv)); + + for (;;) { + char opt; + const char *arg; + + apr_status_t status(apr_getopt(state, + "cg:n:" #ifdef CY_ATTACH - "p:" + "p:" #endif - "s" - )) { - case -1: - goto getopt; - case '?': - fprintf(stderr, "usage: cycript [-c]" + "s" + , &opt, &arg)); + + switch (status) { + case APR_EOF: + goto getopt; + case APR_BADCH: + case APR_BADARG: + fprintf(stderr, + "usage: cycript [-c]" #ifdef CY_ATTACH - " [-p ]" + " [-p ]" #endif - " [