comparison cinst/nssstore_linux.c @ 383:5eb7ee4ee819

Look up executable name based on /proc/self/exe
author Andre Heinecke <andre.heinecke@intevation.de>
date Tue, 15 Apr 2014 17:47:07 +0200
parents 824ef90a6721
children 638db75f0fdf
comparison
equal deleted inserted replaced
382:124f08a85532 383:5eb7ee4ee819
9 #include <unistd.h> 9 #include <unistd.h>
10 #include <sys/types.h> 10 #include <sys/types.h>
11 #include <sys/wait.h> 11 #include <sys/wait.h>
12 #include <string.h> 12 #include <string.h>
13 #include <stdlib.h> 13 #include <stdlib.h>
14 #include <limits.h>
14 15
15 #include "nssstore.h" 16 #include "nssstore.h"
16 #include "logging.h" 17 #include "logging.h"
17 #include "strhelp.h" 18 #include "strhelp.h"
19
20 #define NSS_PROCESS_NAME "mozilla"
21
22 /**@brief get the current path of the executable
23 *
24 * Looks up the current executables directory. The caller
25 * has to free the return value.
26 *
27 * The returned value includes the last /
28 *
29 * @returns the absolute directory of the currently executed executable or NULL
30 */
31 char *
32 get_exe_dir()
33 {
34 char *retval = NULL,
35 *p = NULL,
36 buf[PATH_MAX];
37 ssize_t ret;
38 size_t path_len = 0;
39
40 ret = readlink ("/proc/self/exe", buf, PATH_MAX);
41 if (ret <= 0)
42 {
43 ERRORPRINTF ("readlink failed\n");
44 return NULL;
45 }
46
47 buf[ret] = '\0';
48
49 /* cut off the filename */
50 p = strrchr (buf, '/');
51 if (p == NULL)
52 {
53 ERRORPRINTF ("No filename found.\n");
54 return NULL;
55 }
56 *(p + 1) = '\0';
57
58 path_len = strlen (buf);
59 retval = xmalloc (path_len + 1);
60 strncpy (retval, buf, path_len);
61
62 return retval;
63 }
18 64
19 /**@brief Start the process to install / remove 65 /**@brief Start the process to install / remove
20 * 66 *
21 * This forks the process and executes the NSS installation 67 * This forks the process and executes the NSS installation
22 * process. It also writes the Instructions to that process. 68 * process. It also writes the Instructions to that process.
33 start_procces_for_user (char **to_install, char **to_remove, 79 start_procces_for_user (char **to_install, char **to_remove,
34 uid_t uid, gid_t gid, char *homedir) 80 uid_t uid, gid_t gid, char *homedir)
35 { 81 {
36 int pipe_fd[2]; 82 int pipe_fd[2];
37 pid_t pid = 0; 83 pid_t pid = 0;
38 char *argv[] = {"mozilla", NULL}, 84 char *argv[2] = {NULL, NULL},
39 *envp[2]; 85 *envp[2] = {NULL, NULL},
40 size_t homedir_len = 0; 86 *inst_dir = NULL;
87 size_t homedir_len = 0,
88 exe_path_len = 0;
41 int ret = -1, 89 int ret = -1,
42 i = 0; 90 i = 0;
43 FILE *stream = NULL; 91 FILE *stream = NULL;
44 bool success = false; 92 bool success = false;
45 93
62 ERRORPRINTF ("Error setting home env variable.\n"); 110 ERRORPRINTF ("Error setting home env variable.\n");
63 xfree (envp[0]); 111 xfree (envp[0]);
64 return -1; 112 return -1;
65 } 113 }
66 114
67 DEBUGPRINTF ("Home: %s \n", envp[0]); 115 /* Set up the file name of the installer process */
116 inst_dir = get_exe_dir();
117 if (inst_dir == NULL)
118 {
119 ERRORPRINTF ("Failed to find installation directory.\n");
120 xfree (envp[0]);
121 return -1;
122 }
123
124 exe_path_len = strlen(inst_dir) + strlen(NSS_PROCESS_NAME);
125 argv[0] = xmalloc (exe_path_len + 1);
126
127 ret = snprintf(argv[0], exe_path_len + 1, "%s%s", inst_dir, NSS_PROCESS_NAME);
128 if (ret < 0 || (size_t) ret != exe_path_len)
129 {
130 ERRORPRINTF ("Error setting executable variable.\n");
131 xfree (argv[0]);
132 return -1;
133 }
68 134
69 if (pipe (pipe_fd)) 135 if (pipe (pipe_fd))
70 { 136 {
71 ERRORPRINTF ("Failed to create pipe.\n"); 137 ERRORPRINTF ("Failed to create pipe.\n");
72 return -1; 138 return -1;
90 156
91 close (pipe_fd[1]); 157 close (pipe_fd[1]);
92 dup2 (pipe_fd[0], 0); 158 dup2 (pipe_fd[0], 0);
93 close (pipe_fd[0]); 159 close (pipe_fd[0]);
94 /* TODO find path based on current executable */ 160 /* TODO find path based on current executable */
95 execve ("mozilla", argv, envp); 161 execve (argv[0], argv, envp);
96 exit (127); 162 exit (127);
97 } 163 }
98 164
99 close (pipe_fd[0]); 165 close (pipe_fd[0]);
100 stream = fdopen(pipe_fd[1], "w"); 166 stream = fdopen(pipe_fd[1], "w");
127 193
128 done: 194 done:
129 if (stream) { 195 if (stream) {
130 fclose (stream); 196 fclose (stream);
131 } 197 }
198 xfree (argv[0]);
132 xfree (envp[0]); 199 xfree (envp[0]);
133 close(pipe_fd[0]); 200 close (pipe_fd[0]);
134 close(pipe_fd[1]); 201 close (pipe_fd[1]);
135 202
136 if (success) 203 if (success)
137 { 204 {
138 return pid; 205 return pid;
139 } 206 }
169 if (childprocess == -1 || !WIFEXITED(status)) 236 if (childprocess == -1 || !WIFEXITED(status))
170 { 237 {
171 ERRORPRINTF ("Waitpid failed.\n"); 238 ERRORPRINTF ("Waitpid failed.\n");
172 return -1; 239 return -1;
173 } 240 }
174 DEBUGPRINTF ("Child returned status: %i\n", WEXITSTATUS(status));
175 241
176 return 0; 242 return 0;
177 } 243 }
178 printf ("Installation as root is not yet implemented\n"); 244 printf ("Installation as root is not yet implemented\n");
179 /* TODO root parse /etc/passwd for users with a home directory */ 245 /* TODO root parse /etc/passwd for users with a home directory */

http://wald.intevation.org/projects/trustbridge/