Commit 9ba8130c by Serge Hallyn Committed by Daniel Lezcano

switch all sprintfs which can overrun to snprintfs

and check return values Signed-off-by: 's avatarSerge Hallyn <serge.hallyn@ubuntu.com> Signed-off-by: 's avatarDaniel Lezcano <dlezcano@fr.ibm.com>
parent a0a2066d
......@@ -261,13 +261,18 @@ static int lxc_one_cgroup_attach(const char *name,
char tasks[MAXPATHLEN], initcgroup[MAXPATHLEN];
char *cgmnt = mntent->mnt_dir;
int flags, ret = 0;
int rc;
flags = get_cgroup_flags(mntent);
snprintf(tasks, MAXPATHLEN, "%s%s%s/%s/tasks", cgmnt,
rc = snprintf(tasks, MAXPATHLEN, "%s%s%s/%s/tasks", cgmnt,
get_init_cgroup(NULL, mntent, initcgroup),
(flags & CGROUP_NS_CGROUP) ? "" : "/lxc",
name);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("pathname too long");
return -1;
}
f = fopen(tasks, "w");
if (!f) {
......@@ -500,6 +505,7 @@ int recursive_rmdir(char *dirname)
while (!readdir_r(dir, &dirent, &direntp)) {
struct stat mystat;
int rc;
if (!direntp)
break;
......@@ -508,7 +514,11 @@ int recursive_rmdir(char *dirname)
!strcmp(direntp->d_name, ".."))
continue;
snprintf(pathname, MAXPATHLEN, "%s/%s", dirname, direntp->d_name);
rc = snprintf(pathname, MAXPATHLEN, "%s/%s", dirname, direntp->d_name);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("pathname too long");
continue;
}
ret = stat(pathname, &mystat);
if (ret)
continue;
......@@ -530,10 +540,15 @@ int lxc_one_cgroup_destroy(struct mntent *mntent, const char *name)
char cgname[MAXPATHLEN], initcgroup[MAXPATHLEN];
char *cgmnt = mntent->mnt_dir;
int flags = get_cgroup_flags(mntent);
int rc;
snprintf(cgname, MAXPATHLEN, "%s%s%s/%s", cgmnt,
rc = snprintf(cgname, MAXPATHLEN, "%s%s%s/%s", cgmnt,
get_init_cgroup(NULL, mntent, initcgroup),
(flags & CGROUP_NS_CGROUP) ? "" : "/lxc", name);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("name too long");
return -1;
}
DEBUG("destroying %s\n", cgname);
if (recursive_rmdir(cgname)) {
SYSERROR("failed to remove cgroup '%s'", cgname);
......@@ -583,11 +598,16 @@ int lxc_cgroup_path_get(char **path, const char *subsystem, const char *name)
{
static char buf[MAXPATHLEN];
static char retbuf[MAXPATHLEN];
int rc;
/* lxc_cgroup_set passes a state object for the subsystem,
* so trim it to just the subsystem part */
if (subsystem) {
snprintf(retbuf, MAXPATHLEN, "%s", subsystem);
rc = snprintf(retbuf, MAXPATHLEN, "%s", subsystem);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("subsystem name too long");
return -1;
}
char *s = index(retbuf, '.');
if (s)
*s = '\0';
......@@ -598,7 +618,11 @@ int lxc_cgroup_path_get(char **path, const char *subsystem, const char *name)
return -1;
}
snprintf(retbuf, MAXPATHLEN, "%s/%s", buf, name);
rc = snprintf(retbuf, MAXPATHLEN, "%s/%s", buf, name);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("name too long");
return -1;
}
DEBUG("%s: returning %s for subsystem %s", __func__, retbuf, subsystem);
......@@ -611,12 +635,17 @@ int lxc_cgroup_set(const char *name, const char *filename, const char *value)
int fd, ret;
char *dirpath;
char path[MAXPATHLEN];
int rc;
ret = lxc_cgroup_path_get(&dirpath, filename, name);
if (ret)
return -1;
snprintf(path, MAXPATHLEN, "%s/%s", dirpath, filename);
rc = snprintf(path, MAXPATHLEN, "%s/%s", dirpath, filename);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("pathname too long");
return -1;
}
fd = open(path, O_WRONLY);
if (fd < 0) {
......@@ -642,12 +671,17 @@ int lxc_cgroup_get(const char *name, const char *filename,
int fd, ret = -1;
char *dirpath;
char path[MAXPATHLEN];
int rc;
ret = lxc_cgroup_path_get(&dirpath, filename, name);
if (ret)
return -1;
snprintf(path, MAXPATHLEN, "%s/%s", dirpath, filename);
rc = snprintf(path, MAXPATHLEN, "%s/%s", dirpath, filename);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("pathname too long");
return -1;
}
fd = open(path, O_RDONLY);
if (fd < 0) {
......@@ -669,12 +703,17 @@ int lxc_cgroup_nrtasks(const char *name)
char path[MAXPATHLEN];
int pid, ret, count = 0;
FILE *file;
int rc;
ret = lxc_cgroup_path_get(&dpath, NULL, name);
if (ret)
return -1;
snprintf(path, MAXPATHLEN, "%s/tasks", dpath);
rc = snprintf(path, MAXPATHLEN, "%s/tasks", dpath);
if (rc < 0 || rc >= MAXPATHLEN) {
ERROR("pathname too long");
return -1;
}
file = fopen(path, "r");
if (!file) {
......
......@@ -75,8 +75,14 @@ static int __lxc_command(const char *name, struct lxc_command *command,
int sock, ret = -1;
char path[sizeof(((struct sockaddr_un *)0)->sun_path)] = { 0 };
char *offset = &path[1];
int rc, len;
sprintf(offset, abstractname, name);
len = sizeof(path)-1;
rc = snprintf(offset, len, abstractname, name);
if (rc < 0 || rc >= len) {
ERROR("Name too long");
return -1;
}
sock = lxc_af_unix_connect(path);
if (sock < 0 && errno == ECONNREFUSED) {
......@@ -266,8 +272,14 @@ extern int lxc_command_mainloop_add(const char *name,
int ret, fd;
char path[sizeof(((struct sockaddr_un *)0)->sun_path)] = { 0 };
char *offset = &path[1];
int rc, len;
sprintf(offset, abstractname, name);
len = sizeof(path)-1;
rc = snprintf(offset, len, abstractname, name);
if (rc < 0 || rc >= len) {
ERROR("Name too long");
return -1;
}
fd = lxc_af_unix_open(path, SOCK_STREAM, 0);
if (fd < 0) {
......
......@@ -241,11 +241,25 @@ static int run_script(const char *name, const char *section,
return -1;
}
ret = sprintf(buffer, "%s %s %s", script, name, section);
ret = snprintf(buffer, size, "%s %s %s", script, name, section);
if (ret < 0 || ret >= size) {
ERROR("Script name too long");
free(buffer);
return -1;
}
va_start(ap, script);
while ((p = va_arg(ap, char *)))
ret += sprintf(buffer + ret, " %s", p);
while ((p = va_arg(ap, char *))) {
int len = size-ret;
int rc;
rc = snprintf(buffer + ret, len, " %s", p);
if (rc < 0 || rc >= len) {
free(buffer);
ERROR("Script args too long");
return -1;
}
ret += rc;
}
va_end(ap);
f = popen(buffer, "r");
......@@ -391,7 +405,7 @@ static int mount_rootfs_file(const char *rootfs, const char *target)
{
struct dirent dirent, *direntp;
struct loop_info64 loinfo;
int ret = -1, fd = -1;
int ret = -1, fd = -1, rc;
DIR *dir;
char path[MAXPATHLEN];
......@@ -415,7 +429,10 @@ static int mount_rootfs_file(const char *rootfs, const char *target)
if (strncmp(direntp->d_name, "loop", 4))
continue;
sprintf(path, "/dev/%s", direntp->d_name);
rc = snprintf(path, MAXPATHLEN, "/dev/%s", direntp->d_name);
if (rc < 0 || rc >= MAXPATHLEN)
continue;
fd = open(path, O_RDWR);
if (fd < 0)
continue;
......@@ -577,7 +594,7 @@ static int setup_tty(const struct lxc_rootfs *rootfs,
}
if (ttydir) {
/* create dev/lxc/tty%d" */
snprintf(lxcpath, sizeof(lxcpath), "%s/dev/%s/tty%d",
ret = snprintf(lxcpath, sizeof(lxcpath), "%s/dev/%s/tty%d",
rootfs->mount, ttydir, i + 1);
if (ret >= sizeof(lxcpath)) {
ERROR("pathname too long for ttys");
......@@ -601,7 +618,11 @@ static int setup_tty(const struct lxc_rootfs *rootfs,
continue;
}
snprintf(lxcpath, sizeof(lxcpath), "%s/tty%d", ttydir, i+1);
ret = snprintf(lxcpath, sizeof(lxcpath), "%s/tty%d", ttydir, i+1);
if (ret >= sizeof(lxcpath)) {
ERROR("tty pathname too long");
return -1;
}
ret = symlink(lxcpath, path);
if (ret) {
SYSERROR("failed to create symlink for tty %d\n", i+1);
......@@ -682,12 +703,17 @@ static int umount_oldrootfs(const char *oldrootfs)
void *cbparm[2];
struct lxc_list mountlist, *iterator;
int ok, still_mounted, last_still_mounted;
int rc;
/* read and parse /proc/mounts in old root fs */
lxc_list_init(&mountlist);
/* oldrootfs is on the top tree directory now */
snprintf(path, sizeof(path), "/%s", oldrootfs);
rc = snprintf(path, sizeof(path), "/%s", oldrootfs);
if (rc >= sizeof(path)) {
ERROR("rootfs name too long");
return -1;
}
cbparm[0] = &mountlist;
cbparm[1] = strdup(path);
......@@ -696,7 +722,11 @@ static int umount_oldrootfs(const char *oldrootfs)
return -1;
}
snprintf(path, sizeof(path), "%s/proc/mounts", oldrootfs);
rc = snprintf(path, sizeof(path), "%s/proc/mounts", oldrootfs);
if (rc >= sizeof(path)) {
ERROR("container proc/mounts name too long");
return -1;
}
ok = lxc_file_for_each_line(path,
setup_rootfs_pivot_root_cb, &cbparm);
......@@ -750,6 +780,7 @@ static int setup_rootfs_pivot_root(const char *rootfs, const char *pivotdir)
{
char path[MAXPATHLEN];
int remove_pivotdir = 0;
int rc;
/* change into new root fs */
if (chdir(rootfs)) {
......@@ -761,7 +792,11 @@ static int setup_rootfs_pivot_root(const char *rootfs, const char *pivotdir)
pivotdir = "mnt";
/* compute the full path to pivotdir under rootfs */
snprintf(path, sizeof(path), "%s/%s", rootfs, pivotdir);
rc = snprintf(path, sizeof(path), "%s/%s", rootfs, pivotdir);
if (rc >= sizeof(path)) {
ERROR("pivot dir name too long");
return -1;
}
if (access(path, F_OK)) {
......@@ -984,7 +1019,11 @@ static int setup_ttydir_console(const struct lxc_rootfs *rootfs,
}
/* create symlink from rootfs/dev/console to 'lxc/console' */
snprintf(lxcpath, sizeof(lxcpath), "%s/console", ttydir);
ret = snprintf(lxcpath, sizeof(lxcpath), "%s/console", ttydir);
if (ret >= sizeof(lxcpath)) {
ERROR("lxc/console path too long");
return -1;
}
ret = symlink(lxcpath, path);
if (ret) {
SYSERROR("failed to create symlink for console");
......@@ -1178,7 +1217,7 @@ skipvarlib:
skipabs:
snprintf(path, MAXPATHLEN, "%s/%s", rootfs->mount,
r = snprintf(path, MAXPATHLEN, "%s/%s", rootfs->mount,
aux + offset);
if (r < 0 || r >= MAXPATHLEN) {
WARN("pathnme too long for '%s'", mntent->mnt_dir);
......@@ -1209,7 +1248,11 @@ static int mount_entry_on_relative_rootfs(struct mntent *mntent,
}
/* relative to root mount point */
snprintf(path, sizeof(path), "%s/%s", rootfs, mntent->mnt_dir);
ret = snprintf(path, sizeof(path), "%s/%s", rootfs, mntent->mnt_dir);
if (ret >= sizeof(path)) {
ERROR("path name too long");
return -1;
}
ret = mount_entry(mntent->mnt_fsname, path, mntent->mnt_type,
mntflags, mntdata);
......@@ -1684,7 +1727,11 @@ static int instanciate_veth(struct lxc_handler *handler, struct lxc_netdev *netd
if (netdev->priv.veth_attr.pair)
veth1 = netdev->priv.veth_attr.pair;
else {
snprintf(veth1buf, sizeof(veth1buf), "vethXXXXXX");
err = snprintf(veth1buf, sizeof(veth1buf), "vethXXXXXX");
if (err >= sizeof(veth1buf)) { /* can't *really* happen, but... */
ERROR("veth1 name too long");
return -1;
}
veth1 = mktemp(veth1buf);
}
......@@ -1772,7 +1819,9 @@ static int instanciate_macvlan(struct lxc_handler *handler, struct lxc_netdev *n
return -1;
}
snprintf(peerbuf, sizeof(peerbuf), "mcXXXXXX");
err = snprintf(peerbuf, sizeof(peerbuf), "mcXXXXXX");
if (err >= sizeof(peerbuf))
return -1;
peer = mktemp(peerbuf);
if (!strlen(peer)) {
......@@ -1819,7 +1868,11 @@ static int instanciate_vlan(struct lxc_handler *handler, struct lxc_netdev *netd
return -1;
}
snprintf(peer, sizeof(peer), "vlan%d", netdev->priv.vlan_attr.vid);
err = snprintf(peer, sizeof(peer), "vlan%d", netdev->priv.vlan_attr.vid);
if (err >= sizeof(peer)) {
ERROR("peer name too long");
return -1;
}
err = lxc_vlan_create(netdev->link, peer, netdev->priv.vlan_attr.vid);
if (err) {
......
......@@ -52,15 +52,29 @@ static char *choose_init(void)
if (!retv)
return NULL;
snprintf(retv, PATH_MAX-1, LXCINITDIR "/lxc/lxc-init");
ret = snprintf(retv, PATH_MAX, LXCINITDIR "/lxc/lxc-init");
if (ret < 0 || ret >= PATH_MAX) {
ERROR("pathname too long");
return NULL;
}
ret = stat(retv, &mystat);
if (ret == 0)
return retv;
snprintf(retv, PATH_MAX-1, "/usr/lib/lxc/lxc-init");
ret = snprintf(retv, PATH_MAX, "/usr/lib/lxc/lxc-init");
if (ret < 0 || ret >= PATH_MAX) {
ERROR("pathname too long");
return NULL;
}
ret = stat(retv, &mystat);
if (ret == 0)
return retv;
snprintf(retv, PATH_MAX-1, "/sbin/lxc-init");
ret = snprintf(retv, PATH_MAX, "/sbin/lxc-init");
if (ret < 0 || ret >= PATH_MAX) {
ERROR("pathname too long");
return NULL;
}
ret = stat(retv, &mystat);
if (ret == 0)
return retv;
......
......@@ -49,7 +49,11 @@ static int freeze_unfreeze(const char *name, int freeze)
if (ret)
return -1;
snprintf(freezer, MAXPATHLEN, "%s/freezer.state", nsgroup);
ret = snprintf(freezer, MAXPATHLEN, "%s/freezer.state", nsgroup);
if (ret >= MAXPATHLEN) {
ERROR("freezer.state name too long");
return -1;
}
fd = open(freezer, O_RDWR);
if (fd < 0) {
......
......@@ -60,6 +60,7 @@ int main(int argc, char *argv[])
struct lxc_msg msg;
regex_t preg;
int fd;
int len, rc;
if (lxc_arguments_parse(&my_args, argc, argv))
return -1;
......@@ -68,12 +69,18 @@ int main(int argc, char *argv[])
my_args.progname, my_args.quiet))
return -1;
regexp = malloc(strlen(my_args.name) + 3);
len = strlen(my_args.name) + 3;
regexp = malloc(len + 3);
if (!regexp) {
ERROR("failed to allocate memory");
return -1;
}
sprintf(regexp, "^%s$", my_args.name);
rc = snprintf(regexp, len, "^%s$", my_args.name);
if (rc < 0 || rc >= len) {
ERROR("Name too long");
free(regexp);
return -1;
}
if (regcomp(&preg, regexp, REG_NOSUB|REG_EXTENDED)) {
ERROR("failed to compile the regex '%s'", my_args.name);
......
......@@ -582,12 +582,15 @@ static int proc_sys_net_write(const char *path, const char *value)
static int ip_forward_set(const char *ifname, int family, int flag)
{
char path[MAXPATHLEN];
int rc;
if (family != AF_INET && family != AF_INET6)
return -EINVAL;
snprintf(path, MAXPATHLEN, "/proc/sys/net/%s/conf/%s/forwarding",
rc = snprintf(path, MAXPATHLEN, "/proc/sys/net/%s/conf/%s/forwarding",
family == AF_INET?"ipv4":"ipv6" , ifname);
if (rc >= MAXPATHLEN)
return -E2BIG;
return proc_sys_net_write(path, flag?"1":"0");
}
......@@ -605,13 +608,16 @@ int lxc_ip_forward_off(const char *ifname, int family)
static int neigh_proxy_set(const char *ifname, int family, int flag)
{
char path[MAXPATHLEN];
int ret;
if (family != AF_INET && family != AF_INET6)
return -EINVAL;
sprintf(path, "/proc/sys/net/%s/conf/%s/%s",
ret = snprintf(path, MAXPATHLEN, "/proc/sys/net/%s/conf/%s/%s",
family == AF_INET?"ipv4":"ipv6" , ifname,
family == AF_INET?"proxy_arp":"proxy_ndp");
if (ret < 0 || ret >= MAXPATHLEN)
return -E2BIG;
return proc_sys_net_write(path, flag?"1":"0");
}
......
......@@ -75,7 +75,9 @@ static int freezer_state(const char *name)
if (err)
return -1;
snprintf(freezer, MAXPATHLEN, "%s/freezer.state", nsgroup);
err = snprintf(freezer, MAXPATHLEN, "%s/freezer.state", nsgroup);
if (err < 0 || err >= MAXPATHLEN)
return -1;
file = fopen(freezer, "r");
if (!file)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment