Esempio n. 1
0
static FILE *
open_status_file(pid_t pid)
{
	PROC_PID_FILE(fn, "/proc/%d/status", pid);
	/* Don't complain if we fail.  This would typically happen
	   when the process is about to terminate, and these files are
	   not available anymore.  This function is called from the
	   event loop, and we don't want to clutter the output just
	   because the process terminates.  */
	return fopen(fn, "r");
}
Esempio n. 2
0
int
process_get_entry(struct Process *proc,
		  arch_addr_t *entryp,
		  arch_addr_t *interp_biasp)
{
	PROC_PID_FILE(fn, "/proc/%d/auxv", proc->pid);
	int fd = open(fn, O_RDONLY);
	int ret = 0;
	if (fd == -1) {
	fail:
		fprintf(stderr, "couldn't read %s: %s", fn, strerror(errno));
		ret = -1;
	done:
		if (fd != -1)
			close(fd);
		return ret;
	}

	arch_addr_t at_entry = 0;
	arch_addr_t at_bias = 0;
	while (1) {
		Elf64_auxv_t entry = {};
		if (auxv_fetcher(proc)(fd, &entry) < 0)
			goto fail;

		switch (entry.a_type) {
		case AT_BASE:
			/* XXX The double cast should be removed when
			 * arch_addr_t becomes integral type.  */
			at_bias = (arch_addr_t)(uintptr_t)entry.a_un.a_val;
			continue;

		case AT_ENTRY:
			/* XXX The double cast should be removed when
			 * arch_addr_t becomes integral type.  */
			at_entry = (arch_addr_t)(uintptr_t)entry.a_un.a_val;
		default:
			continue;

		case AT_NULL:
			break;
		}
		break;
	}

	if (entryp != NULL)
		*entryp = at_entry;
	if (interp_biasp != NULL)
		*interp_biasp = at_bias;
	goto done;
}
Esempio n. 3
0
/*
 * Returns a (malloc'd) file name corresponding to a running pid
 */
char *
pid2name(pid_t pid) {
	if (!kill(pid, 0)) {
		int delay = 0;

		PROC_PID_FILE(proc_exe, "/proc/%d/exe", pid);

		while (delay < MAX_DELAY) {
			if (!access(proc_exe, F_OK)) {
				return strdup(proc_exe);
			}
			delay += 1000;	/* 1 milisecond */
		}
	}
	return NULL;
}
Esempio n. 4
0
int
process_tasks(pid_t pid, pid_t **ret_tasks, size_t *ret_n)
{
	PROC_PID_FILE(fn, "/proc/%d/task", pid);
	DIR * d = opendir(fn);
	if (d == NULL)
		return -1;

	pid_t *tasks = NULL;
	size_t n = 0;
	size_t alloc = 0;

	while (1) {
		struct dirent entry;
		struct dirent *result;
		if (readdir_r(d, &entry, &result) != 0) {
			free(tasks);
			return -1;
		}
		if (result == NULL)
			break;
		if (result->d_type == DT_DIR && all_digits(result->d_name)) {
			pid_t npid = atoi(result->d_name);
			if (n >= alloc) {
				alloc = alloc > 0 ? (2 * alloc) : 8;
				pid_t *ntasks = realloc(tasks,
							sizeof(*tasks) * alloc);
				if (ntasks == NULL) {
					free(tasks);
					return -1;
				}
				tasks = ntasks;
			}
			if (n >= alloc)
				abort();
			tasks[n++] = npid;
		}
	}

	closedir(d);

	*ret_tasks = tasks;
	*ret_n = n;
	return 0;
}