Пример #1
0
int main(int argc, char **argv)
{
    struct hp_options opts = { 0 };
    hotpatch_t *hp = NULL;
	int rc = 0;
	/* parse all arguments first */
    if ((rc = parse_arguments(argc, argv, &opts)) != 0) {
        return rc;
    }
    print_options(&opts);
	/* break from execution whenever a step fails */
	do {
		uintptr_t ptr = 0;
		hp = hotpatch_create(opts.pid, opts.verbose);
		if (!hp) {
			fprintf(stderr, "[%s:%d] Unable to create hotpatch for PID %d\n",
					__func__, __LINE__, opts.pid);
			rc = -1;
			break;
		}
		if (opts.dryrun)
			break;
		if (opts.dll) {
			uintptr_t dlres = 0;
			uintptr_t symres = 0;
			rc = hotpatch_inject_library(hp, opts.dll, opts.symbol, NULL, 0,
										 &dlres, &symres);
			if (rc >=0) {
				printf("Dll was injected at %p\n", (void *)dlres);
				printf("Invocation of %s() returned %p\n",
						(opts.symbol ? opts.symbol : "_init"),
						(void *)symres);
			}
		} else {
			/* handles the stripped apps as well */
			if (opts.is__start) {
				ptr = hotpatch_get_entry_point(hp);
			} else {
				ptr = hotpatch_read_symbol(hp, opts.symbol, NULL, NULL);
			}
			if (!ptr) {
				printf("Symbol %s not found. Cannot proceed\n", opts.symbol);
				break;
			}
			printf("Setting execution pointer to %s at 0x"LX"\n", opts.symbol, ptr);
			rc = hotpatch_attach(hp);
			if (rc < 0) {
				printf("Failed to attach to process. Cannot proceed\n");
				break;
			}

			rc = hotpatch_exec_symbol(hp, ptr, opts.verbose);
			if (rc < 0) {
			  printf("Failed to execute the symbol in 0x"LX"\n", ptr);
			  rc = hotpatch_detach(hp);
			  break;
			}

			rc = hotpatch_detach(hp);
		}
	} while (0);
	hotpatch_destroy(hp);
	hp = NULL;
	if (opts.symbol)
		free(opts.symbol);
	opts.symbol = NULL;
	if (opts.dll)
		free(opts.dll);
	opts.dll = NULL;
    return rc;
}
Пример #2
0
hotpatch_t *hotpatch_create(pid_t pid, int verbose)
{
	int rc = 0;
	hotpatch_t *hp = NULL;
	do {
		char filename[OS_MAX_BUFFER];
		if (pid <= 0) {
			LOG_ERROR_INVALID_PID(pid);
			break;
		}
		memset(filename, 0, sizeof(filename));
		snprintf(filename, sizeof(filename), "/proc/%d/exe", pid);
		if (verbose > 3)
			fprintf(stderr, "[%s:%d] Exe symlink for pid %d : %s\n", __func__,
					__LINE__, pid, filename);
		hp = malloc(sizeof(*hp));
		if (!hp) {
			LOG_ERROR_OUT_OF_MEMORY;
			rc = -1;
			break;
		}
		memset(hp, 0, sizeof(*hp));
		hp->verbose = verbose;
		hp->pid = pid;
		hp->is64 = HOTPATCH_EXE_IS_NEITHER;
		hp->exe_symbols = exe_load_symbols(filename, hp->verbose,
				&hp->exe_symbols_num,
				&hp->exe_entry_point,
				&hp->exe_interp,
				&hp->is64);
		if (!hp->exe_symbols) {
			fprintf(stderr, "[%s:%d] Unable to find any symbols in exe.\n",
					__func__, __LINE__);
			rc = -1;
			break;
		}
		if (hp->exe_entry_point == 0) {
			fprintf(stderr, "[%s:%d] Entry point is 0. Invalid.\n",
					__func__, __LINE__);
			rc = -1;
			break;
		}
		LOG_INFO_HEADERS_LOADED(verbose);
		hp->ld_maps = ld_load_maps(hp->pid, hp->verbose, &hp->ld_maps_num);
		if (!hp->ld_maps) {
			fprintf(stderr, "[%s:%d] Unable to load data in "
					"/proc/%d/maps.\n", __func__, __LINE__, pid);
			rc = -1;
			break;
		}
		if (verbose > 2)
			fprintf(stderr, "[%s:%d] /proc/%d/maps loaded.\n",
					__func__, __LINE__, pid);
		if (hp->exe_symbols && hp->exe_symbols_num > 0) {
			qsort(hp->exe_symbols, hp->exe_symbols_num,
					sizeof(*hp->exe_symbols), elf_symbol_cmpqsort);
		}
		if (hotpatch_gather_functions(hp) < 0) {
			fprintf(stderr, "[%s:%d] Unable to find all the functions"
					" needed. Cannot proceed.\n", __func__, __LINE__);
			rc = -1;
			break;
		}
		if (rc < 0) {
			hotpatch_destroy(hp);
			hp = NULL;
		}
	} while (0);
	return hp;
}