]> git.saurik.com Git - cycript.git/blame - Inject.cpp
Remove everything obsoleted by just using cynject.
[cycript.git] / Inject.cpp
CommitLineData
b3378a02 1/* Cycript - Optimizing JavaScript Compiler/Runtime
f95d2598 2 * Copyright (C) 2009-2014 Jay Freeman (saurik)
e91fbe93
JF
3*/
4
f95d2598 5/* GNU Affero General Public License, Version 3 {{{ */
e91fbe93 6/*
f95d2598
JF
7 * This program is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU Affero General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
c15969fd 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
f95d2598
JF
15 * GNU Affero General Public License for more details.
16
17 * You should have received a copy of the GNU Affero General Public License
18 * along with this program. If not, see <http://www.gnu.org/licenses/>.
b3378a02 19**/
e91fbe93
JF
20/* }}} */
21
f8d45a20 22#include <sstream>
7cfc264c 23#include <string>
56fc2692 24
3615a2f7 25#include <dlfcn.h>
b6961e53 26
b6961e53
JF
27#include "Exception.hpp"
28#include "Pooling.hpp"
b6961e53 29
7cfc264c
JF
30#if defined(__APPLE__) && (defined(__i386__) || defined(__x86_64__))
31#include <sys/fcntl.h>
32#include <sys/mman.h>
6342b70c 33
7cfc264c 34#include <mach-o/loader.h>
3615a2f7 35
7cfc264c 36#define CS_OPS_PIDOFFSET 6
3370d0c0 37
7cfc264c
JF
38extern "C" int csops(pid_t pid, unsigned int ops, void *useraddr, size_t usersize);
39extern "C" int proc_pidpath(int pid, void *buffer, uint32_t buffersize);
3615a2f7 40#endif
b6961e53 41
7cfc264c
JF
42int main(int argc, char * const argv[], char const * const envp[]);
43extern "C" char *MSmain0(int argc, char *argv[]);
b6961e53 44
7cfc264c
JF
45static std::string LibraryFor(void *address) {
46 Dl_info info;
47 _assert(dladdr(address, &info) != 0);
48 return info.dli_fname;
49}
3615a2f7 50
7cfc264c
JF
51template <typename Type_>
52Type_ *shift(Type_ *data, size_t size) {
53 return reinterpret_cast<Type_ *>(reinterpret_cast<uint8_t *>(data) + size);
54}
3615a2f7 55
f8d45a20 56void InjectLibrary(int pid, int argc, const char *argv[]) {
7cfc264c
JF
57 auto cynject(LibraryFor(reinterpret_cast<void *>(&main)));
58 auto slash(cynject.rfind('/'));
59 _assert(slash != std::string::npos);
60 cynject = cynject.substr(0, slash) + "/cynject";
3615a2f7 61
7cfc264c 62 auto library(LibraryFor(reinterpret_cast<void *>(&MSmain0)));
3615a2f7 63
7cfc264c
JF
64#if defined(__APPLE__) && (defined(__i386__) || defined(__x86_64__))
65 off_t offset;
66 _assert(csops(pid, CS_OPS_PIDOFFSET, &offset, sizeof(offset)) != -1);
3615a2f7 67
7cfc264c 68 char path[PATH_MAX];
e4b4d8c7 69 int writ(proc_pidpath(pid, path, sizeof(path)));
7cfc264c 70 _assert(writ != 0);
b6961e53 71
7cfc264c 72 auto fd(_syscall(open(path, O_RDONLY)));
b6961e53 73
7cfc264c
JF
74 auto page(getpagesize());
75 auto size(page * 4);
76 auto map(_syscall(mmap(NULL, size, PROT_READ, MAP_SHARED, fd, offset)));
3615a2f7 77
7cfc264c 78 _syscall(close(fd)); // XXX: _scope
3615a2f7 79
7cfc264c
JF
80 auto header(reinterpret_cast<mach_header *>(map));
81 auto command(reinterpret_cast<load_command *>(header + 1));
3615a2f7 82
7cfc264c
JF
83 switch (header->magic) {
84 case MH_MAGIC_64:
85 command = shift(command, sizeof(uint32_t));
86 case MH_MAGIC:
3615a2f7
JF
87 break;
88 default:
89 _assert(false);
90 }
3db8ce8e 91
7cfc264c
JF
92 bool ios(false);
93 for (decltype(header->ncmds) i(0); i != header->ncmds; ++i) {
94 if (command->cmd == LC_VERSION_MIN_IPHONEOS)
95 ios = true;
96 command = shift(command, command->cmdsize);
3615a2f7 97 }
9d79cefc 98
7cfc264c 99 _syscall(munmap(map, size)); // XXX: _scope
9d79cefc 100
7cfc264c
JF
101 auto length(library.size());
102 _assert(length >= 6);
103 length -= 6;
9d79cefc 104
7cfc264c
JF
105 _assert(library.substr(length) == ".dylib");
106 library = library.substr(0, length);
107 library += ios ? "-sim" : "-sys";
108 library += ".dylib";
b6961e53
JF
109#endif
110
f8d45a20
JF
111 std::ostringstream inject;
112 inject << cynject << " " << std::dec << pid << " " << library;
113 for (decltype(argc) i(0); i != argc; ++i)
114 inject << " " << argv[i];
115
116 _assert(system(inject.str().c_str()) == 0);
b6961e53 117}