summaryrefslogtreecommitdiff
path: root/src/lib
diff options
context:
space:
mode:
authorSander Vrijders <[email protected]>2016-07-05 09:06:20 +0200
committerSander Vrijders <[email protected]>2016-07-05 09:06:20 +0200
commit96acaa2b5732a7685725b5c46045eda3375a3839 (patch)
tree9a73dfc68725eccf2bb491e367705926dcc50214 /src/lib
parentaca5db11a73e66377b8566e69c1baabb1df803ab (diff)
parent66fd022a705cf65cbe37c446dbd87919a43a7fd3 (diff)
downloadouroboros-96acaa2b5732a7685725b5c46045eda3375a3839.tar.gz
ouroboros-96acaa2b5732a7685725b5c46045eda3375a3839.zip
Merged in dstaesse/ouroboros/be-path-check (pull request #152)
lib: irm: search for ap using PATH variable
Diffstat (limited to 'src/lib')
-rw-r--r--src/lib/irm.c96
1 files changed, 90 insertions, 6 deletions
diff --git a/src/lib/irm.c b/src/lib/irm.c
index 93963eb1..68ffdf03 100644
--- a/src/lib/irm.c
+++ b/src/lib/irm.c
@@ -27,7 +27,9 @@
#include <ouroboros/common.h>
#include <ouroboros/logs.h>
#include <ouroboros/sockets.h>
+#include <ouroboros/utils.h>
+#include <string.h>
#include <stdlib.h>
#include <sys/stat.h>
@@ -238,6 +240,84 @@ int irm_enroll_ipcp(pid_t api,
return ret;
}
+static int check_ap(char * ap_name)
+{
+ struct stat s;
+
+ if (stat(ap_name, &s) != 0)
+ return -ENOENT;
+
+ if (!(s.st_mode & S_IXUSR))
+ return -EPERM;
+
+ return 0;
+}
+
+static int check_ap_path(char ** ap_name)
+{
+ char * path = getenv("PATH");
+ char * path_end = path + strlen(path) + 1;
+ char * pstart;
+ char * pstop = path;
+ char * tmp;
+ char * tstop;
+ char * tstart;
+ bool perm = true;
+ int ret = 0;
+
+ if (*ap_name == NULL || path == NULL)
+ return -EINVAL;
+
+ if (!strlen(path) || strchr(*ap_name, '/') == NULL)
+ if ((ret = check_ap(*ap_name)) < 0)
+ return ret;
+
+ tmp = malloc(strlen(path) + strlen(*ap_name) + 2);
+ if (tmp == NULL)
+ return -ENOMEM;
+
+ tstop = tmp + strlen(path) + 1;
+ strcpy(tstop--, *ap_name);
+
+ while (pstop < path_end) {
+ ret = 0;
+ pstart = pstop;
+ if (*pstart != '/') {
+ free(tmp);
+ return -EINVAL;
+ }
+
+ while (*pstop != '\0' && *pstop != ':')
+ pstop++;
+
+ *pstop = '\0';
+ tstart = tstop - (pstop++ - pstart);
+ strcpy(tstart, pstart);
+ *tstop = '/';
+
+ if ((ret = check_ap(tstart)) < 0) {
+ if (ret == -EPERM)
+ perm = false;
+ continue;
+ }
+
+ free(*ap_name);
+ *ap_name = strdup(tstart);
+ free(tmp);
+
+ if (*ap_name == NULL)
+ return -ENOMEM;
+
+ return 0;
+ }
+
+ free(tmp);
+ if (!perm)
+ return -EPERM;
+
+ return -ENOENT;
+}
+
int irm_bind(char * name,
char * ap_name,
uint16_t opts,
@@ -247,20 +327,23 @@ int irm_bind(char * name,
irm_msg_t msg = IRM_MSG__INIT;
irm_msg_t * recv_msg = NULL;
int ret = -1;
- struct stat s;
+ char * full_ap_name;
if (name == NULL || ap_name == NULL)
return -EINVAL;
- if (stat(ap_name, &s) != 0)
- return -ENOENT;
+ full_ap_name = strdup(ap_name);
+ if (full_ap_name == NULL)
+ return -ENOMEM;
- if (!(s.st_mode & S_IXUSR))
- return -EPERM;
+ if ((ret = check_ap_path(&full_ap_name)) < 0) {
+ free(full_ap_name);
+ return ret;
+ }
msg.code = IRM_MSG_CODE__IRM_BIND;
msg.dst_name = name;
- msg.ap_name = ap_name;
+ msg.ap_name = full_ap_name;
if (argv != NULL) {
msg.n_args = argc;
@@ -282,6 +365,7 @@ int irm_bind(char * name,
ret = recv_msg->result;
irm_msg__free_unpacked(recv_msg, NULL);
+ free(full_ap_name);
return ret;
}