From c6705af4231b8071830721f98021d0e79223da12 Mon Sep 17 00:00:00 2001 From: Rob Landley Date: Tue, 9 Sep 2014 23:42:25 -0500 Subject: Two problems: 1) Sometimes toy_exec() needs to re-exec to gain dropped root permissions, 2) shouldn't recurse forever without exec, stack depth increases and we may leak other resources. Limit it to ~5 levels. --- main.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'main.c') diff --git a/main.c b/main.c index 5bd44602..cfa2cc99 100644 --- a/main.c +++ b/main.c @@ -119,12 +119,18 @@ void toy_init(struct toy_list *which, char *argv[]) } // Like exec() but runs an internal toybox command instead of another file. -// Only returns if it can't find the command, otherwise exit() when done. +// Only returns if it can't run command internally, otherwise exit() when done. void toy_exec(char *argv[]) { struct toy_list *which; + // Return if we can't find it, or need to re-exec to acquire root, + // or if stack depth is getting silly. if (!(which = toy_find(argv[0]))) return; + if (toys.recursion && (which->flags & TOYFLAG_ROOTONLY) && getuid()) return; + if (toys.recursion++ > 5) return; + + // Run command toy_init(which, argv); if (toys.which) toys.which->toy_main(); if (fflush(NULL) || ferror(stdout)) perror_exit("write"); -- cgit v1.2.3