aboutsummaryrefslogtreecommitdiffstats
path: root/src/libtracelog
diff options
context:
space:
mode:
Diffstat (limited to 'src/libtracelog')
-rw-r--r--src/libtracelog/Makefile.in26
-rw-r--r--src/libtracelog/libtracelog.c704
2 files changed, 0 insertions, 730 deletions
diff --git a/src/libtracelog/Makefile.in b/src/libtracelog/Makefile.in
deleted file mode 100644
index 3927c762a..000000000
--- a/src/libtracelog/Makefile.in
+++ /dev/null
@@ -1,26 +0,0 @@
1CC=@CC@
2PREFIX=@prefix@
3VERSION=@PACKAGE_VERSION@
4NAME=@PACKAGE_NAME@
5HAVE_FATAL_WARNINGS=@HAVE_FATAL_WARNINGS@
6
7H_FILE_LIST = $(sort $(wildcard *.[h]))
8C_FILE_LIST = $(sort $(wildcard *.c))
9OBJS = $(C_FILE_LIST:.c=.o)
10BINOBJS = $(foreach file, $(OBJS), $file)
11CFLAGS += -ggdb $(HAVE_FATAL_WARNINGS) -O2 -DVERSION='"$(VERSION)"' -fstack-protector-all -D_FORTIFY_SOURCE=2 -fPIC -Wformat -Wformat-security
12LDFLAGS += -pie -Wl,-z,relro -Wl,-z,now
13
14all: libtracelog.so
15
16%.o : %.c $(H_FILE_LIST)
17 $(CC) $(CFLAGS) $(INCLUDE) -c $< -o $@
18
19libtracelog.so: $(OBJS)
20 $(CC) $(LDFLAGS) -shared -fPIC -z relro -o $@ $(OBJS) -ldl
21
22
23clean:; rm -f $(OBJS) libtracelog.so
24
25distclean: clean
26 rm -fr Makefile
diff --git a/src/libtracelog/libtracelog.c b/src/libtracelog/libtracelog.c
deleted file mode 100644
index 0f8d5a00d..000000000
--- a/src/libtracelog/libtracelog.c
+++ /dev/null
@@ -1,704 +0,0 @@
1/*
2 * Copyright (C) 2014-2018 Firejail Authors
3 *
4 * This file is part of firejail project
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19*/
20#define _GNU_SOURCE
21#include <stdio.h>
22#include <stdlib.h>
23#include <string.h>
24#include <dlfcn.h>
25#include <sys/types.h>
26#include <unistd.h>
27#include <sys/socket.h>
28#include <netinet/in.h>
29#include <arpa/inet.h>
30#include <sys/un.h>
31#include <sys/stat.h>
32#include <syslog.h>
33#include <dirent.h>
34#include <limits.h>
35
36//#define DEBUG
37
38// break recursivity on fopen call
39typedef FILE *(*orig_fopen_t)(const char *pathname, const char *mode);
40static orig_fopen_t orig_fopen = NULL;
41typedef FILE *(*orig_fopen64_t)(const char *pathname, const char *mode);
42static orig_fopen64_t orig_fopen64 = NULL;
43
44//
45// blacklist storage
46//
47typedef struct list_elem_t {
48 struct list_elem_t *next;
49 char *path;
50} ListElem;
51
52#define HMASK 0x0ff
53ListElem *storage[HMASK + 1];
54
55// djb2
56static inline uint32_t hash(const char *str) {
57 uint32_t hash = 5381;
58 int c;
59
60 while ((c = *str++) != '\0')
61 hash = ((hash << 5) + hash) + c; // hash * 33 + c; another variant would be hash * 33 ^ c
62
63 return hash & HMASK;
64}
65
66static void storage_add(const char *str) {
67 if (!str) {
68#ifdef DEBUG
69 printf("null pointer passed to storage_add\n");
70#endif
71 return;
72 }
73
74#ifdef DEBUG
75 printf("add %s\n", str);
76#endif
77
78 ListElem *ptr = malloc(sizeof(ListElem));
79 if (!ptr) {
80 fprintf(stderr, "Error: cannot allocate memory\n");
81 return;
82 }
83 ptr->path = strdup(str);
84 if (!ptr->path) {
85 fprintf(stderr, "Error: cannot allocate memory\n");
86 free(ptr);
87 return;
88 }
89
90 // insert it into the hash table
91 uint32_t h = hash(ptr->path);
92 ptr->next = storage[h];
93 storage[h] = ptr;
94}
95
96// global variable to keep current working directory
97static char* cwd = NULL;
98
99static char *storage_find(const char *str) {
100 if (!str) {
101#ifdef DEBUG
102 printf("null pointer passed to storage_find\n");
103#endif
104 return NULL;
105 }
106
107#ifdef DEBUG
108 printf("storage find %s\n", str);
109#endif
110
111 const char *tofind = str;
112 int allocated = 0;
113
114 if (strstr(str, "..") || strstr(str, "/./") || strstr(str, "//") || str[0] != '/') {
115 if (cwd != NULL && str[0] != '/') {
116 char *fullpath=malloc(PATH_MAX);
117 if (!fullpath) {
118 fprintf(stderr, "Error: cannot allocate memory\n");
119 return NULL;
120 }
121 if (snprintf(fullpath, PATH_MAX, "%s/%s", cwd, str)<3) {
122 fprintf(stderr, "Error: snprintf failed\n");
123 free(fullpath);
124 return NULL;
125 }
126 tofind = realpath(fullpath, NULL);
127 free(fullpath);
128 } else {
129 tofind = realpath(str, NULL);
130 }
131 if (!tofind) {
132#ifdef DEBUG
133 printf("realpath failed\n");
134#endif
135 return NULL;
136 }
137 allocated = 1;
138 }
139
140 uint32_t h = hash(tofind);
141 ListElem *ptr = storage[h];
142 while (ptr) {
143 if (strcmp(tofind, ptr->path) == 0) {
144 if (allocated)
145 free((char *) tofind);
146#ifdef DEBUG
147 printf("storage found\n");
148#endif
149 return ptr->path;
150 }
151 ptr = ptr->next;
152 }
153
154 if (allocated)
155 free((char *) tofind);
156#ifdef DEBUG
157 printf("storage not found\n");
158#endif
159 return NULL;
160}
161
162
163//
164// load blacklist form /run/firejail/mnt/fslogger
165//
166#define RUN_FSLOGGER_FILE "/run/firejail/mnt/fslogger"
167#define MAXBUF 4096
168static int blacklist_loaded = 0;
169static char *sandbox_pid_str = NULL;
170static char *sandbox_name_str = NULL;
171static void load_blacklist(void) {
172 if (blacklist_loaded)
173 return;
174
175 // open filesystem log
176 if (!orig_fopen)
177 orig_fopen = (orig_fopen_t)dlsym(RTLD_NEXT, "fopen");
178 FILE *fp = orig_fopen(RUN_FSLOGGER_FILE, "r");
179 if (!fp)
180 return;
181
182 // extract blacklists
183 char buf[MAXBUF];
184 int cnt = 0;
185 while (fgets(buf, MAXBUF, fp)) {
186 if (strncmp(buf, "sandbox pid: ", 13) == 0) {
187 char *ptr = strchr(buf, '\n');
188 if (ptr)
189 *ptr = '\0';
190 if (sandbox_pid_str == NULL)
191 sandbox_pid_str = strdup(buf + 13);
192 }
193 else if (strncmp(buf, "sandbox name: ", 14) == 0) {
194 char *ptr = strchr(buf, '\n');
195 if (ptr)
196 *ptr = '\0';
197 if (sandbox_name_str == NULL)
198 sandbox_name_str = strdup(buf + 14);
199 }
200 else if (strncmp(buf, "blacklist ", 10) == 0) {
201 char *ptr = strchr(buf, '\n');
202 if (ptr)
203 *ptr = '\0';
204 storage_add(buf + 10);
205 cnt++;
206 }
207 }
208 fclose(fp);
209 blacklist_loaded = 1;
210#ifdef DEBUG
211 printf("Monitoring %d blacklists\n", cnt);
212 {
213 int i;
214 for (i = 0; i <= HMASK; i++) {
215 int cnt = 0;
216 ListElem *ptr = storage[i];
217 while (ptr) {
218 cnt++;
219 ptr = ptr->next;
220 }
221
222 if ((i % 16) == 0)
223 printf("\n");
224 printf("%02d ", cnt);
225 }
226 printf("\n");
227 }
228#endif
229}
230
231
232static void sendlog(const char *name, const char *call, const char *path) {
233 if (!name || !call || !path) {
234#ifdef DEBUG
235 printf("null pointer passed to sendlog\n");
236#endif
237 return;
238 }
239
240 openlog ("firejail", LOG_CONS | LOG_PID | LOG_NDELAY, LOG_LOCAL1);
241 if (sandbox_pid_str && sandbox_name_str)
242 syslog (LOG_INFO, "blacklist violation - sandbox %s, name %s, exe %s, syscall %s, path %s",
243 sandbox_pid_str, sandbox_name_str, name, call, path);
244 else if (sandbox_pid_str)
245 syslog (LOG_INFO, "blacklist violation - sandbox %s, exe %s, syscall %s, path %s",
246 sandbox_pid_str, name, call, path);
247 else
248 syslog (LOG_INFO, "blacklist violation - exe %s, syscall %s, path %s",
249 name, call, path);
250 closelog ();
251}
252
253
254//
255// pid
256//
257static pid_t mypid = 0;
258static inline pid_t pid(void) {
259 if (!mypid)
260 mypid = getpid();
261 return mypid;
262}
263
264//
265// process name
266//
267#define MAXNAME 16
268static char myname[MAXNAME];
269static int nameinit = 0;
270static char *name(void) {
271 if (!nameinit) {
272
273 // initialize the name of the process based on /proc/PID/comm
274 memset(myname, 0, MAXNAME);
275
276 pid_t p = pid();
277 char *fname;
278 if (asprintf(&fname, "/proc/%u/comm", p) == -1)
279 return "unknown";
280
281 // read file
282 if (!orig_fopen)
283 orig_fopen = (orig_fopen_t)dlsym(RTLD_NEXT, "fopen");
284 FILE *fp = orig_fopen(fname, "r");
285 if (!fp)
286 return "unknown";
287 if (fgets(myname, MAXNAME, fp) == NULL) {
288 fclose(fp);
289 free(fname);
290 return "unknown";
291 }
292
293 // clean '\n'
294 char *ptr = strchr(myname, '\n');
295 if (ptr)
296 *ptr = '\0';
297
298 fclose(fp);
299 free(fname);
300 nameinit = 1;
301 }
302
303 return myname;
304}
305
306//
307// syscalls
308//
309
310// open
311typedef int (*orig_open_t)(const char *pathname, int flags, mode_t mode);
312static orig_open_t orig_open = NULL;
313int open(const char *pathname, int flags, mode_t mode) {
314#ifdef DEBUG
315 printf("%s %s\n", __FUNCTION__, pathname);
316#endif
317 if (!orig_open)
318 orig_open = (orig_open_t)dlsym(RTLD_NEXT, "open");
319
320 if (!blacklist_loaded)
321 load_blacklist();
322
323 if (storage_find(pathname))
324 sendlog(name(), __FUNCTION__, pathname);
325 int rv = orig_open(pathname, flags, mode);
326 return rv;
327}
328
329
330
331
332//#if 0 - todo: fix problems on google-chrome and opera - seems to be crashing when open64 is called
333typedef int (*orig_open64_t)(const char *pathname, int flags, mode_t mode);
334static orig_open64_t orig_open64 = NULL;
335int open64(const char *pathname, int flags, mode_t mode) {
336#ifdef DEBUG
337 printf("%s %s\n", __FUNCTION__, pathname);
338#endif
339 if (!orig_open64)
340 orig_open64 = (orig_open64_t)dlsym(RTLD_NEXT, "open64");
341 if (!blacklist_loaded)
342 load_blacklist();
343
344 if (storage_find(pathname))
345 sendlog(name(), __FUNCTION__, pathname);
346 int rv = orig_open64(pathname, flags, mode);
347 return rv;
348}
349//#endif
350
351
352// openat
353typedef int (*orig_openat_t)(int dirfd, const char *pathname, int flags, mode_t mode);
354static orig_openat_t orig_openat = NULL;
355int openat(int dirfd, const char *pathname, int flags, mode_t mode) {
356#ifdef DEBUG
357 printf("%s %s\n", __FUNCTION__, pathname);
358#endif
359 if (!orig_openat)
360 orig_openat = (orig_openat_t)dlsym(RTLD_NEXT, "openat");
361 if (!blacklist_loaded)
362 load_blacklist();
363
364 if (storage_find(pathname))
365 sendlog(name(), __FUNCTION__, pathname);
366 int rv = orig_openat(dirfd, pathname, flags, mode);
367 return rv;
368}
369
370typedef int (*orig_openat64_t)(int dirfd, const char *pathname, int flags, mode_t mode);
371static orig_openat64_t orig_openat64 = NULL;
372int openat64(int dirfd, const char *pathname, int flags, mode_t mode) {
373#ifdef DEBUG
374 printf("%s %s\n", __FUNCTION__, pathname);
375#endif
376 if (!orig_openat64)
377 orig_openat64 = (orig_openat64_t)dlsym(RTLD_NEXT, "openat64");
378 if (!blacklist_loaded)
379 load_blacklist();
380
381 if (storage_find(pathname))
382 sendlog(name(), __FUNCTION__, pathname);
383 int rv = orig_openat64(dirfd, pathname, flags, mode);
384 return rv;
385}
386
387
388// fopen
389FILE *fopen(const char *pathname, const char *mode) {
390#ifdef DEBUG
391 printf("%s %s\n", __FUNCTION__, pathname);
392#endif
393 if (!orig_fopen)
394 orig_fopen = (orig_fopen_t)dlsym(RTLD_NEXT, "fopen");
395 if (!blacklist_loaded)
396 load_blacklist();
397
398 if (storage_find(pathname))
399 sendlog(name(), __FUNCTION__, pathname);
400 FILE *rv = orig_fopen(pathname, mode);
401 return rv;
402}
403
404#ifdef __GLIBC__
405FILE *fopen64(const char *pathname, const char *mode) {
406#ifdef DEBUG
407 printf("%s %s\n", __FUNCTION__, pathname);
408#endif
409 if (!orig_fopen64)
410 orig_fopen64 = (orig_fopen_t)dlsym(RTLD_NEXT, "fopen64");
411 if (!blacklist_loaded)
412 load_blacklist();
413
414 if (storage_find(pathname))
415 sendlog(name(), __FUNCTION__, pathname);
416 FILE *rv = orig_fopen64(pathname, mode);
417 return rv;
418}
419#endif /* __GLIBC__ */
420
421
422// freopen
423typedef FILE *(*orig_freopen_t)(const char *pathname, const char *mode, FILE *stream);
424static orig_freopen_t orig_freopen = NULL;
425FILE *freopen(const char *pathname, const char *mode, FILE *stream) {
426#ifdef DEBUG
427 printf("%s %s\n", __FUNCTION__, pathname);
428#endif
429 if (!orig_freopen)
430 orig_freopen = (orig_freopen_t)dlsym(RTLD_NEXT, "freopen");
431 if (!blacklist_loaded)
432 load_blacklist();
433
434 if (storage_find(pathname))
435 sendlog(name(), __FUNCTION__, pathname);
436 FILE *rv = orig_freopen(pathname, mode, stream);
437 return rv;
438}
439
440#ifdef __GLIBC__
441typedef FILE *(*orig_freopen64_t)(const char *pathname, const char *mode, FILE *stream);
442static orig_freopen64_t orig_freopen64 = NULL;
443FILE *freopen64(const char *pathname, const char *mode, FILE *stream) {
444#ifdef DEBUG
445 printf("%s %s\n", __FUNCTION__, pathname);
446#endif
447 if (!orig_freopen64)
448 orig_freopen64 = (orig_freopen64_t)dlsym(RTLD_NEXT, "freopen64");
449 if (!blacklist_loaded)
450 load_blacklist();
451
452 if (storage_find(pathname))
453 sendlog(name(), __FUNCTION__, pathname);
454 FILE *rv = orig_freopen64(pathname, mode, stream);
455 return rv;
456}
457#endif /* __GLIBC__ */
458
459// unlink
460typedef int (*orig_unlink_t)(const char *pathname);
461static orig_unlink_t orig_unlink = NULL;
462int unlink(const char *pathname) {
463#ifdef DEBUG
464 printf("%s %s\n", __FUNCTION__, pathname);
465#endif
466 if (!orig_unlink)
467 orig_unlink = (orig_unlink_t)dlsym(RTLD_NEXT, "unlink");
468 if (!blacklist_loaded)
469 load_blacklist();
470
471 if (storage_find(pathname))
472 sendlog(name(), __FUNCTION__, pathname);
473 int rv = orig_unlink(pathname);
474 return rv;
475}
476
477typedef int (*orig_unlinkat_t)(int dirfd, const char *pathname, int flags);
478static orig_unlinkat_t orig_unlinkat = NULL;
479int unlinkat(int dirfd, const char *pathname, int flags) {
480#ifdef DEBUG
481 printf("%s %s\n", __FUNCTION__, pathname);
482#endif
483 if (!orig_unlinkat)
484 orig_unlinkat = (orig_unlinkat_t)dlsym(RTLD_NEXT, "unlinkat");
485 if (!blacklist_loaded)
486 load_blacklist();
487
488 if (storage_find(pathname))
489 sendlog(name(), __FUNCTION__, pathname);
490 int rv = orig_unlinkat(dirfd, pathname, flags);
491 return rv;
492}
493
494// mkdir/mkdirat/rmdir
495typedef int (*orig_mkdir_t)(const char *pathname, mode_t mode);
496static orig_mkdir_t orig_mkdir = NULL;
497int mkdir(const char *pathname, mode_t mode) {
498#ifdef DEBUG
499 printf("%s %s\n", __FUNCTION__, pathname);
500#endif
501 if (!orig_mkdir)
502 orig_mkdir = (orig_mkdir_t)dlsym(RTLD_NEXT, "mkdir");
503 if (!blacklist_loaded)
504 load_blacklist();
505
506 if (storage_find(pathname))
507 sendlog(name(), __FUNCTION__, pathname);
508 int rv = orig_mkdir(pathname, mode);
509 return rv;
510}
511
512typedef int (*orig_mkdirat_t)(int dirfd, const char *pathname, mode_t mode);
513static orig_mkdirat_t orig_mkdirat = NULL;
514int mkdirat(int dirfd, const char *pathname, mode_t mode) {
515#ifdef DEBUG
516 printf("%s %s\n", __FUNCTION__, pathname);
517#endif
518 if (!orig_mkdirat)
519 orig_mkdirat = (orig_mkdirat_t)dlsym(RTLD_NEXT, "mkdirat");
520 if (!blacklist_loaded)
521 load_blacklist();
522
523 if (storage_find(pathname))
524 sendlog(name(), __FUNCTION__, pathname);
525 int rv = orig_mkdirat(dirfd, pathname, mode);
526 return rv;
527}
528
529typedef int (*orig_rmdir_t)(const char *pathname);
530static orig_rmdir_t orig_rmdir = NULL;
531int rmdir(const char *pathname) {
532#ifdef DEBUG
533 printf("%s %s\n", __FUNCTION__, pathname);
534#endif
535 if (!orig_rmdir)
536 orig_rmdir = (orig_rmdir_t)dlsym(RTLD_NEXT, "rmdir");
537 if (!blacklist_loaded)
538 load_blacklist();
539
540 if (storage_find(pathname))
541 sendlog(name(), __FUNCTION__, pathname);
542 int rv = orig_rmdir(pathname);
543 return rv;
544}
545
546// stat
547typedef int (*orig_stat_t)(const char *pathname, struct stat *buf);
548static orig_stat_t orig_stat = NULL;
549int stat(const char *pathname, struct stat *buf) {
550#ifdef DEBUG
551 printf("%s %s\n", __FUNCTION__, pathname);
552#endif
553 if (!orig_stat)
554 orig_stat = (orig_stat_t)dlsym(RTLD_NEXT, "stat");
555 if (!blacklist_loaded)
556 load_blacklist();
557
558 if (storage_find(pathname))
559 sendlog(name(), __FUNCTION__, pathname);
560 int rv = orig_stat(pathname, buf);
561 return rv;
562}
563
564#ifdef __GLIBC__
565typedef int (*orig_stat64_t)(const char *pathname, struct stat64 *buf);
566static orig_stat64_t orig_stat64 = NULL;
567int stat64(const char *pathname, struct stat64 *buf) {
568#ifdef DEBUG
569 printf("%s %s\n", __FUNCTION__, pathname);
570#endif
571 if (!orig_stat64)
572 orig_stat64 = (orig_stat64_t)dlsym(RTLD_NEXT, "stat64");
573 if (!blacklist_loaded)
574 load_blacklist();
575
576 if (storage_find(pathname))
577 sendlog(name(), __FUNCTION__, pathname);
578 int rv = orig_stat64(pathname, buf);
579 return rv;
580}
581#endif /* __GLIBC__ */
582
583typedef int (*orig_lstat_t)(const char *pathname, struct stat *buf);
584static orig_lstat_t orig_lstat = NULL;
585int lstat(const char *pathname, struct stat *buf) {
586#ifdef DEBUG
587 printf("%s %s\n", __FUNCTION__, pathname);
588#endif
589 if (!orig_lstat)
590 orig_lstat = (orig_lstat_t)dlsym(RTLD_NEXT, "lstat");
591 if (!blacklist_loaded)
592 load_blacklist();
593
594 if (storage_find(pathname))
595 sendlog(name(), __FUNCTION__, pathname);
596 int rv = orig_lstat(pathname, buf);
597 return rv;
598}
599
600#ifdef __GLIBC__
601typedef int (*orig_lstat64_t)(const char *pathname, struct stat64 *buf);
602static orig_lstat64_t orig_lstat64 = NULL;
603int lstat64(const char *pathname, struct stat64 *buf) {
604#ifdef DEBUG
605 printf("%s %s\n", __FUNCTION__, pathname);
606#endif
607 if (!orig_lstat64)
608 orig_lstat64 = (orig_lstat64_t)dlsym(RTLD_NEXT, "lstat64");
609 if (!blacklist_loaded)
610 load_blacklist();
611
612 if (storage_find(pathname))
613 sendlog(name(), __FUNCTION__, pathname);
614 int rv = orig_lstat64(pathname, buf);
615 return rv;
616}
617#endif /* __GLIBC__ */
618
619// access
620typedef int (*orig_access_t)(const char *pathname, int mode);
621static orig_access_t orig_access = NULL;
622int access(const char *pathname, int mode) {
623#ifdef DEBUG
624 printf("%s, %s\n", __FUNCTION__, pathname);
625#endif
626 if (!orig_access)
627 orig_access = (orig_access_t)dlsym(RTLD_NEXT, "access");
628 if (!blacklist_loaded)
629 load_blacklist();
630
631 if (storage_find(pathname))
632 sendlog(name(), __FUNCTION__, pathname);
633 int rv = orig_access(pathname, mode);
634 return rv;
635}
636
637// opendir
638typedef DIR *(*orig_opendir_t)(const char *pathname);
639static orig_opendir_t orig_opendir = NULL;
640DIR *opendir(const char *pathname) {
641#ifdef DEBUG
642 printf("%s %s\n", __FUNCTION__, pathname);
643#endif
644 if (!orig_opendir)
645 orig_opendir = (orig_opendir_t)dlsym(RTLD_NEXT, "opendir");
646 if (!blacklist_loaded)
647 load_blacklist();
648
649 if (storage_find(pathname))
650 sendlog(name(), __FUNCTION__, pathname);
651 DIR *rv = orig_opendir(pathname);
652 return rv;
653}
654
655// chdir
656typedef int (*orig_chdir_t)(const char *pathname);
657static orig_chdir_t orig_chdir = NULL;
658int chdir(const char *pathname) {
659#ifdef DEBUG
660 printf("%s %s\n", __FUNCTION__, pathname);
661#endif
662 if (!orig_chdir)
663 orig_chdir = (orig_chdir_t)dlsym(RTLD_NEXT, "chdir");
664 if (!blacklist_loaded)
665 load_blacklist();
666
667 if (storage_find(pathname))
668 sendlog(name(), __FUNCTION__, pathname);
669
670 free(cwd);
671 cwd = strdup(pathname);
672
673 int rv = orig_chdir(pathname);
674 return rv;
675}
676
677// fchdir
678typedef int (*orig_fchdir_t)(int fd);
679static orig_fchdir_t orig_fchdir = NULL;
680int fchdir(int fd) {
681#ifdef DEBUG
682 printf("%s %d\n", __FUNCTION__, fd);
683#endif
684 if (!orig_fchdir)
685 orig_fchdir = (orig_fchdir_t)dlsym(RTLD_NEXT, "fchdir");
686
687 free(cwd);
688 char *pathname=malloc(PATH_MAX);
689 if (pathname) {
690 if (snprintf(pathname,PATH_MAX,"/proc/self/fd/%d", fd)>0) {
691 cwd = realpath(pathname, NULL);
692 } else {
693 cwd = NULL;
694 fprintf(stderr, "Error: snprintf failed\n");
695 }
696 free(pathname);
697 } else {
698 fprintf(stderr, "Error: cannot allocate memory\n");
699 cwd = NULL;
700 }
701
702 int rv = orig_fchdir(fd);
703 return rv;
704}