dragoran escribió:
Hello,Since the fedora-extras review for initng started work has started to add selinux support for initng. I started by porting the sysvinit patches to initng. This made it possible that selinux loads its policy at all.But then we run into an other problem:The selinux policy does not allow initng to do what it should do (=> does not work in enforcing mode).This is whats still missing until today. There is a bugreport in redhats bugzilla about this issue: https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=179761 One of the problems is that there are some fd leaks in initng.When a daemon or a script gets started in its own selinux domain it picks up one of the still open fds but they are not in its domain which causes problems (not allowed to use them; does not work correctly).I have no idea how to fix this thats why I am asking here... Any ideas how to get rid of the fd leaks issue?When this is solved we can see what avs are remaining and if they are fixable inside initng or not. If not we can modificy the policy to work with this.
The attached patch _may_ fix the fd-leaking issue. But be careful, it's untested.
Index: plugins/bash_launcher/initng_bash_launcher.c
===================================================================
--- plugins/bash_launcher/initng_bash_launcher.c (revision 4826)
+++ plugins/bash_launcher/initng_bash_launcher.c (working copy)
@@ -48,6 +48,7 @@
#include <initng_env_variable.h>
#include <initng_static_event_types.h>
#include <initng_event_hook.h>
+#include <initng_fd.h>
INITNG_PLUGIN_MACRO;
@@ -168,13 +169,10 @@
if ((pid_fork = initng_fork(s, process_to_exec)) == 0)
{
- int i;
-
/* run afterfork hooks from other plugins */
initng_fork_aforkhooks(s, process_to_exec);
- for (i = 3; i < 1024; i++)
- close(i);
+ initng_fd_close_all_afork();
/* execute code */
bash_this(script, s, args);
Index: plugins/simple_launcher/initng_simple_launcher.c
===================================================================
--- plugins/simple_launcher/initng_simple_launcher.c (revision 4826)
+++ plugins/simple_launcher/initng_simple_launcher.c (working copy)
@@ -45,6 +45,7 @@
#include <initng_env_variable.h>
#include <initng_static_event_types.h>
#include <initng_event_hook.h>
+#include <initng_fd.h>
INITNG_PLUGIN_MACRO;
@@ -183,11 +184,8 @@
/* run g.AFTER_FORK from other plugins */
initng_fork_aforkhooks(s, process_to_exec);
- int i;
+ initng_fd_close_all_afork();
- for (i = 3; i < 1024; i++)
- close(i);
-
#ifdef DEBUG
D_("FROM_FORK simple_exec(%i,%s, ...);\n", argc, argv[0]);
/*D_argv("simple_exec: ", argv); */
@@ -323,7 +321,7 @@
argv[0] = exec;
ret=simple_exec_fork(process, service, argc, argv);
-
+
// Do some cleanup
if(exec_args)
fix_free(exec_args, exec_args_unfixed);
@@ -431,7 +429,7 @@
fix_free(exec_fixed, exec);
return (FALSE);
}
-
+
free(argv[0]);
argv[0] = argv0; // Check this before freeing!
}
@@ -441,21 +439,21 @@
result = simple_exec_fork(process, service, argc, argv);
/* clean up */
-
+
// First free the fixed argv0 if its not a plain link to argv[0]
if (argv0 && argv0 != argv[0])
{
free(argv0);
}
argv0 = NULL;
-
+
// Later free the big argv array
- split_delim_free(argv);
+ split_delim_free(argv);
argv = NULL;
-
+
// then free this one.
fix_free(exec_fixed, exec);
-
+
/* return result */
if (result == FAIL)
return (FALSE);
Index: src/initng_fd.c
===================================================================
--- src/initng_fd.c (revision 4826)
+++ src/initng_fd.c (working copy)
@@ -25,6 +25,8 @@
#include <errno.h>
#include <string.h>
#include <fcntl.h> /*
fcntl() */
+#include <sys/types.h>
+#include <dirent.h>
#include "initng.h"
#include "initng_global.h"
@@ -271,7 +273,7 @@
pi->buffer_len = 9000; /* shortened by
1000 chars */
pi->buffer[9000] = '\0'; /* shortened by
1000 chars */
}
-
+
D_("function done...");
}
@@ -543,3 +545,27 @@
return;
}
+
+void initng_fd_close_all_afork(void)
+{
+ DIR * dir;
+ struct dirent * entry;
+ int fd;
+
+ dir = opendir("/proc/self/fd");
+ if (!dir)
+ {
+ W_("Can not open /proc/self/fd!\n");
+
+ for (fd = 3; fd < 1024; fd++)
+ close(fd);
+ return;
+ }
+
+ while ((entry = readdir(dir)))
+ {
+ fd = atoi(entry->d_name);
+ if (fd > 2)
+ close(fd);
+ }
+}
Index: src/initng_fd.h
===================================================================
--- src/initng_fd.h (revision 4826)
+++ src/initng_fd.h (working copy)
@@ -19,12 +19,15 @@
#ifndef INITNG_FD_H
#define INITNG_FD_H
+#include "initng_active_db.h"
+#include "initng_process_db.h"
#define STILL_OPEN(fd) (fcntl(fd, F_GETFD)>=0)
-void initng_fd_process_read_input(active_db_h * service, process_h * p,
- pipe_h *
pipe);
+void initng_fd_process_read_input(active_db_h * service, process_h * p, pipe_h
* pipe);
void initng_fd_close_all(void);
void initng_fd_plugin_poll(int timeout);
+void initng_fd_close_all_afork(void);
+
#endif
Index: src/main.c
===================================================================
--- src/main.c (revision 4843)
+++ src/main.c (working copy)
@@ -413,7 +413,10 @@
/* if this is real init */
if (g.i_am == I_AM_INIT)
{
- /*load selinux policy and rexec*/
+ /* mount /proc */
+ mount("proc", "/proc", "proc", 0, NULL);
+
+ /* load selinux policy and rexec */
#ifdef SELINUX
if ((fopen("/selinux/enforce", "r")) != NULL) goto BOOT;
int enforce = -1;
signature.asc
Description: OpenPGP digital signature
-- _______________________________________________ Initng mailing list [email protected] http://jw.dyndns.org/mailman/listinfo/initng
