1 #include <signal.h> 2 #include <stdio.h> 3 #include <time.h> 4 #include <sys/resource.h> 5 #include <bpf/libbpf.h> 6 #include <time.h> 7 8 #include "commargv.h" 9 #include "commargv.skel.h" 10 11 #include <map> 12 #include <algorithm> 13 #include <tuple> 14 #include <string> 15 #include <set> 16 using namespace std; 17 18 19 20 // cpp code, to compile run `CC=g++ make commargv` 21 22 static struct ring_buffer *ring_buf = NULL; 23 static struct commargv_bpf *skel = NULL; 24 static int exiting = 0; 25 static void int_exit(int sig) { 26 exiting = 1; 27 if (ring_buf) { 28 ring_buffer__free(ring_buf); 29 ring_buf= NULL; 30 } 31 if (skel){ 32 commargv_bpf__destroy(skel); 33 skel = NULL; 34 } 35 } 36 37 using xtt = tuple<time_t, string, string>; 38 static map<int, xtt> pids; 39 static int event_handler(void *_ctx, void *data, size_t size) { 40 if (size != sizeof(struct comm_event)){ 41 printf("receive unmatch size %d\n", (int)size); 42 return 0; 43 } 44 struct comm_event* event = (struct comm_event*)data; 45 // printf("receive event from %d[%s]\n", event->pid, event->comm); 46 if (event->n==0) return 0; 47 int pid = event->pid, i; 48 time_t ctime = time(NULL); 49 if (pids.count(pid)==0 || ctime-get<0>(pids[pid]) > 1000) { 50 char b[128]; 51 char comm[128]; 52 char host[128]; 53 sprintf(b, "/proc/%d/comm", pid); 54 FILE* fp; 55 size_t i=0; 56 fp = fopen(b, "r"); if (fp) { 57 comm[0]=0; fgets(comm, sizeof(comm), fp); 58 while(i<sizeof(comm)&&comm[i]!=0&&comm[i]!='\n'&&comm[i]!='\r') i++; 59 comm[i]=0; 60 fclose(fp); 61 } 62 if (i<1) strcpy(comm, "unknown-command"); 63 sprintf(b, "/proc/%d/root/etc/hostname", pid); 64 i=0; fp = fopen(b, "r"); if (fp) { 65 host[0]=0; fgets(host, sizeof(host), fp); 66 while(i<sizeof(host)&&host[i]!=0&&host[i]!='\n'&&host[i]!='\r') i++; 67 host[i]=0; 68 fclose(fp); 69 } 70 if (i<1) strcpy(host, "unknown-host"); 71 pids[pid] = make_tuple(ctime, string(comm), string(host)); 72 } 73 printf("[%s@%s]: ", get<1>(pids[pid]).c_str(), get<2>(pids[pid]).c_str()); 74 for (i=0; i<event->n; i++) printf("%s ", event->argv[i]); 75 printf("\n"); 76 return 0; 77 } 78 79 int main(int argc, char *argv[]) { 80 int err; 81 signal(SIGINT, int_exit); 82 signal(SIGTERM, int_exit); 83 skel = commargv_bpf__open(); 84 if (!skel) { 85 fprintf(stderr, "Failed to open and load BPF skeleton\n"); 86 return 1; 87 } 88 err = commargv_bpf__load(skel); 89 if (err) { 90 fprintf(stderr, "Failed to load and verify BPF skeleton\n"); 91 goto cleanup; 92 } 93 err = commargv_bpf__attach(skel); 94 if (err) { 95 fprintf(stderr, "Failed to attach BPF skeleton\n"); 96 goto cleanup; 97 } 98 ring_buf = ring_buffer__new(bpf_map__fd(skel->maps.comms), event_handler, NULL, NULL); 99 if (!ring_buf) { 100 perror("Fail to alloc ring buf"); 101 goto cleanup; 102 } 103 while (!exiting) { 104 if(ring_buffer__poll(ring_buf, -1) < 0) break; 105 } 106 107 cleanup: 108 int_exit(0); 109 return 0; 110 } 111