Ejemplo n.º 1
0
static int
csops_task(SecTaskRef task, int ops, void *blob, size_t size)
{
	int rc;
    if (task->pid_self==-1) {
        pid_t pid;
        audit_token_to_au32(task->token, NULL, NULL, NULL, NULL, NULL, &pid, NULL, NULL);
        rc = csops_audittoken(pid, ops, blob, size, &task->token);
    }
    else
        rc = csops(task->pid_self, ops, blob, size);
	task->lastFailure = (rc == -1) ? errno : 0;
	return rc;
}
Ejemplo n.º 2
0
void InjectLibrary(int pid, int argc, const char *const argv[]) {
    auto cynject(LibraryFor(reinterpret_cast<void *>(&main)));
    auto slash(cynject.rfind('/'));
    _assert(slash != std::string::npos);
    cynject = cynject.substr(0, slash) + "/cynject";

    auto library(LibraryFor(reinterpret_cast<void *>(&MSmain0)));

#if defined(__APPLE__) && (defined(__i386__) || defined(__x86_64__))
    off_t offset;
    _assert(csops(pid, CS_OPS_PIDOFFSET, &offset, sizeof(offset)) != -1);

    // XXX: implement a safe version of this
    char path[4096];
    int writ(proc_pidpath(pid, path, sizeof(path)));
    _assert(writ != 0);

    auto fd(_syscall(open(path, O_RDONLY)));

    auto page(getpagesize());
    auto size(page * 4);
    auto map(_syscall(mmap(NULL, size, PROT_READ, MAP_SHARED, fd, offset)));

    _syscall(close(fd)); // XXX: _scope

    auto header(reinterpret_cast<mach_header *>(map));
    auto command(reinterpret_cast<load_command *>(header + 1));

    switch (header->magic) {
        case MH_MAGIC_64:
            command = shift(command, sizeof(uint32_t));
        case MH_MAGIC:
            break;
        default:
            _assert(false);
    }

    bool ios(false);
    for (decltype(header->ncmds) i(0); i != header->ncmds; ++i) {
        if (command->cmd == LC_VERSION_MIN_IPHONEOS)
            ios = true;
        command = shift(command, command->cmdsize);
    }

    _syscall(munmap(map, size)); // XXX: _scope

    auto length(library.size());
    _assert(length >= 6);
    length -= 6;

    _assert(library.substr(length) == ".dylib");
    library = library.substr(0, length);
    library += ios ? "-sim" : "-sys";
    library += ".dylib";
#endif

    std::ostringstream inject;
    inject << cynject << " " << std::dec << pid << " " << library;
    for (decltype(argc) i(0); i != argc; ++i)
        inject << " " << argv[i];

    _assert(system(inject.str().c_str()) == 0);
}
Ejemplo n.º 3
-7
int
main(int argc, const char * argv[])
{
    uint32_t status;
    int rcent;
    pid_t pid;
	
    pid = getpid();

    if (get_blob(pid, CS_OPS_ENTITLEMENTS_BLOB))
        errx(1, "failed to get entitlements");

    if (get_blob(0, CS_OPS_ENTITLEMENTS_BLOB))
        errx(1, "failed to get entitlements");

    if (get_blob(pid, CS_OPS_BLOB))
        errx(1, "failed to get blob");

    if (get_blob(0, CS_OPS_BLOB))
        errx(1, "failed to get blob");

    if (get_blob(pid, CS_OPS_IDENTITY))
        errx(1, "failed to get identity");

    if (get_blob(0, CS_OPS_IDENTITY))
        errx(1, "failed to get identity");

    rcent = csops(pid, CS_OPS_SET_STATUS, &status, sizeof(status) - 1);
    if (rcent == 0)
        err(1, "passed when passed in too short status buffer");

    status = htonl(CS_RESTRICT);
    rcent = csops(pid, CS_OPS_SET_STATUS, &status, sizeof(status));
    if (rcent != 0)
        errx(1, "failed to mark proc RESTRICTED");

    rcent = csops(pid, CS_OPS_MARKINVALID, NULL, 0);
    if (rcent != 0)
        errx(1, "failed to mark proc invalid");
    
    status = htonl(CS_VALID);
    rcent = csops(pid, CS_OPS_SET_STATUS, &status, sizeof(status));
    if (rcent == 0)
        errx(1, "managed set flags on an INVALID proc");

    if (!get_blob(pid, CS_OPS_ENTITLEMENTS_BLOB))
        errx(1, "got entitlements while invalid");

    if (!get_blob(pid, CS_OPS_IDENTITY))
        errx(1, "got identity");

    if (!get_blob(0, CS_OPS_IDENTITY))
        errx(1, "got identity");

    if (!get_blob(pid, CS_OPS_BLOB))
        errx(1, "got blob");

    return 0;
}
Ejemplo n.º 4
-15
int
get_blob(pid_t pid, int op)
{
    uint8_t header[8];
    unsigned int cnt;
    int rcent;

    for (cnt = 0; cnt < sizeof(header); cnt++) {
	rcent = csops(pid, op, header, 1);
	if (rcent != -1 && errno != ERANGE)
	    err(1, "errno != ERANGE for short header");
    }

    rcent = csops(pid, op, header, sizeof(header));
    if (rcent == -1 && errno == ERANGE) {
	uint32_t len, bufferlen, bufferlen2;
	    
	memcpy(&len, &header[4], 4);
	bufferlen = ntohl(len);
	if (bufferlen > 1024 * 1024)
	    errx(1, "invalid length on blob from kernel");
	else if (bufferlen == 0)
	    errx(1, "bufferlen == 0");
	else if (bufferlen < 8)
	    errx(1, "bufferlen <8 0");
	    
	uint8_t buffer[bufferlen + 1];
	    
	rcent = csops(pid, op, buffer, bufferlen - 1);
	if (rcent != -1 && errno != ERANGE)
	    errx(1, "csops with full buffer - 1 failed");

	rcent = csops(pid, op, buffer, bufferlen);
	if (rcent != 0)
	    errx(1, "csops with full buffer failed");
	    
	memcpy(&len, &buffer[4], 4);
	bufferlen2 = ntohl(len);

	if (op == CS_OPS_BLOB) {
		if (bufferlen2 > bufferlen)
			errx(1, "buffer larger on second try");
		if (bufferlen2 != bufferlen)
			warnx("buffer shrunk since codesign can't tell the right size to codesign_allocate");
	} else {
		if (bufferlen2 != bufferlen)
			errx(1, "buffer sizes different");
	}

	rcent = csops(pid, op, buffer, bufferlen + 1);
	if (rcent != 0)
	    errx(1, "csops with full buffer + 1 didn't pass");

	return 0;

    } else if (rcent == 0) {
        return 0;
    } else {
	return 1;
    }
}