From 1ef0b2e1a37878ebbc29b03fefb214b7501656a6 Mon Sep 17 00:00:00 2001 From: Cristian Toader Date: Mon, 2 Sep 2013 11:44:04 +0300 Subject: changed how sb getaddrinfo works such that it supports storing multiple results --- src/common/sandbox.c | 62 +++++++++++++++++++++++++++------------------------- src/common/sandbox.h | 18 +++++++++++++++ 2 files changed, 50 insertions(+), 30 deletions(-) (limited to 'src/common') diff --git a/src/common/sandbox.c b/src/common/sandbox.c index 748141cda..41c3b44d7 100644 --- a/src/common/sandbox.c +++ b/src/common/sandbox.c @@ -54,8 +54,7 @@ #include static sandbox_cfg_t *filter_dynamic = NULL; - -static struct addrinfo *sb_addr_info= NULL; +static sb_addr_info_t *sb_addr_info = NULL; /** Variable used for storing all syscall numbers that will be allowed with the * stage 1 general Tor sandbox. @@ -914,54 +913,57 @@ sandbox_cfg_allow_execve_array(sandbox_cfg_t **cfg, ...) int sandbox_getaddrinfo(const char *name, struct addrinfo **res) { - char hname[256]; + sb_addr_info_t *el; - if (!res) { - return -2; - } *res = NULL; - *res = (struct addrinfo *)malloc(sizeof(struct addrinfo)); - if (*res == NULL) { - return -2; - } - if (gethostname(hname, sizeof(hname)) < 0) { - return -1; - } + for (el = sb_addr_info; el; el = el->next) { + if(!strcmp(el->name, name)) { + *res = (struct addrinfo *)malloc(sizeof(struct addrinfo)); + if (!res) { + return -2; + } - if (strcmp(name, hname) || sb_addr_info == NULL) { - log_err(LD_BUG,"(Sandbox) failed for hname %s!", name); - return -1; + memcpy(*res, el->info, sizeof(struct addrinfo)); + + return 0; + } } - memcpy(*res, sb_addr_info, sizeof(struct addrinfo)); - return 0; + return -1; } -static int -init_addrinfo(void) +int +sandbox_add_addrinfo(const char* name) { int ret; struct addrinfo hints; - char hname[256]; + sb_addr_info_t *el = NULL; - sb_addr_info = NULL; - - if (gethostname(hname, sizeof(hname)) < 0) { - return -1; + el = (sb_addr_info_t*) malloc(sizeof(sb_addr_info_t)); + if(!el) { + log_err(LD_BUG,"(Sandbox) failed to allocate addr info!"); + ret = -2; + goto out; } memset(&hints, 0, sizeof(hints)); hints.ai_family = AF_INET; hints.ai_socktype = SOCK_STREAM; - ret = getaddrinfo(hname, NULL, &hints, &sb_addr_info); + ret = getaddrinfo(name, NULL, &hints, &(el->info)); if (ret) { - sb_addr_info = NULL; - return -2; + log_err(LD_BUG,"(Sandbox) failed to getaddrinfo"); + ret = -2; + goto out; } - return 0; + el->name = strdup(name); + el->next = sb_addr_info; + sb_addr_info = el; + + out: + return ret; } static int @@ -1151,7 +1153,7 @@ initialise_libseccomp_sandbox(sandbox_cfg_t* cfg) if (install_sigsys_debugging()) return -1; - if (init_addrinfo() || prot_strings(cfg)) { + if (prot_strings(cfg)) { return -4; } diff --git a/src/common/sandbox.h b/src/common/sandbox.h index 51449ca41..9a61749a3 100644 --- a/src/common/sandbox.h +++ b/src/common/sandbox.h @@ -62,6 +62,21 @@ struct pfd_elem { /** Typedef to structure used to manage a sandbox configuration. */ typedef struct pfd_elem sandbox_cfg_t; +/** + * Structure used for keeping a linked list of getaddrinfo pre-recorded + * results. + */ +struct sb_addr_info_el { + /** Name of the address info result. */ + char *name; + /** Pre-recorded getaddrinfo result. */ + struct addrinfo *info; + /** Next element in the list. */ + struct sb_addr_info_el *next; +}; +/** Typedef to structure used to manage an addrinfo list. */ +typedef struct sb_addr_info_el sb_addr_info_t; + /** Function pointer defining the prototype of a filter function.*/ typedef int (*sandbox_filter_func_t)(scmp_filter_ctx ctx, sandbox_cfg_t *filter); @@ -93,6 +108,9 @@ typedef struct { #endif // __linux__ +/** Pre-calls getaddrinfo in order to pre-record result. */ +int sandbox_add_addrinfo(const char *addr); + /** Replacement for getaddrinfo(), using pre-recorded results. */ int sandbox_getaddrinfo(const char *name, struct addrinfo **res); -- cgit v1.2.3