forked from lastpass/lastpass-cli
-
Notifications
You must be signed in to change notification settings - Fork 0
/
process.c
129 lines (110 loc) · 2.81 KB
/
process.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
/*
* Copyright (c) 2014-2015 LastPass.
*/
#include "process.h"
#include "util.h"
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <sys/resource.h>
#include <limits.h>
#if defined(__linux__)
#include <sys/prctl.h>
#define USE_PRCTL
#elif defined(__APPLE__) && defined(__MACH__)
#include <libproc.h>
#include <sys/ptrace.h>
#define USE_PTRACE
#elif defined(__OpenBSD__)
#include <sys/param.h>
#include <sys/proc.h>
#include <sys/sysctl.h>
#include <kvm.h>
#endif
#ifndef USE_PRCTL
#undef PR_SET_DUMPABLE
#define PR_SET_DUMPABLE 0
#define PR_SET_NAME 0
static void prctl(__attribute__((unused)) int x,
__attribute__((unused)) int y) {}
#endif
#ifndef USE_PTRACE
#undef PT_DENY_ATTACH
#define PT_DENY_ATTACH 0
static void ptrace(__attribute__((unused)) int x,
__attribute__((unused)) int y,
__attribute__((unused)) int z,
__attribute__((unused)) int w) {}
#endif
#if defined(__linux__) || defined(__CYGWIN__) || defined(__NetBSD__)
#define DEVPROC_NAME "exe"
#elif defined(__FreeBSD__) || defined(__DragonFly__)
#define DEVPROC_NAME "file"
#endif
#ifdef DEVPROC_NAME
static int pid_to_cmd(pid_t pid, char *cmd, size_t cmd_size)
{
_cleanup_free_ char *proc;
xasprintf(&proc, "/proc/%lu/" DEVPROC_NAME, (unsigned long)pid);
return readlink(proc, cmd, cmd_size - 1);
}
#elif defined(__APPLE__) && defined(__MACH__)
static int pid_to_cmd(pid_t pid, char *cmd, size_t cmd_size)
{
int result;
result = proc_pidpath(pid, cmd, cmd_size);
return (result <= 0) ? -1 : 0;
}
#elif defined(__OpenBSD__)
static int pid_to_cmd(pid_t pid, char *cmd, size_t cmd_size)
{
int cnt, ret;
kvm_t *kd;
struct kinfo_proc *kp;
ret = -1;
if ((kd = kvm_openfiles(NULL, NULL, NULL, KVM_NO_FILES, NULL)) == NULL)
return ret;
if ((kp = kvm_getprocs(kd, KERN_PROC_PID, (int)pid, sizeof(*kp), &cnt)) == NULL)
goto out;
if ((kp->p_flag & P_SYSTEM) != 0)
goto out;
if (cnt != 1)
goto out;
if (strlcpy(cmd, kp[0].p_comm, cmd_size) >= cmd_size)
goto out;
ret = 0;
out:
kvm_close(kd);
return ret;
}
#else
#error "Please provide a pid_to_cmd for your platform"
#endif
void process_set_name(const char *name)
{
size_t argslen = 0;
prctl(PR_SET_NAME, name);
if (!ARGC || !ARGV)
return;
for (int i = 0; i < ARGC; ++i) {
argslen += strlen(ARGV[i]) + 1;
for (char *p = ARGV[i]; *p; ++p)
*p = '\0';
}
strlcpy(ARGV[0], name, argslen);
}
bool process_is_same_executable(pid_t pid)
{
char resolved_them[PATH_MAX + 1] = { 0 }, resolved_me[PATH_MAX + 1] = { 0 };
if (pid_to_cmd(pid, resolved_them, sizeof(resolved_them)) < 0 ||
pid_to_cmd(getpid(), resolved_me, sizeof(resolved_me)) < 0)
return false;
return strcmp(resolved_them, resolved_me) == 0;
}
void process_disable_ptrace(void)
{
prctl(PR_SET_DUMPABLE, 0);
ptrace(PT_DENY_ATTACH, 0, 0, 0);
struct rlimit limit = { 0, 0 };
setrlimit(RLIMIT_CORE, &limit);
}