aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorlandley <landley@driftwood>2006-10-25 18:38:37 -0400
committerlandley <landley@driftwood>2006-10-25 18:38:37 -0400
commit00f87f150c3c9769e09e688bb9779947d64eb9d3 (patch)
tree3518450fc26ef74a861cb0ee4dea3ebe9646d0f1
parentcd9dfc3b7b73715840b63180e2e4bfdb6e7ca9a4 (diff)
downloadtoybox-00f87f150c3c9769e09e688bb9779947d64eb9d3.tar.gz
Add xmsprintf(), xgetcwd(), xgetcwd(), find_in_path().
-rw-r--r--lib/functions.c58
-rw-r--r--lib/lib.h3
-rw-r--r--toys.h1
3 files changed, 62 insertions, 0 deletions
diff --git a/lib/functions.c b/lib/functions.c
index dd7c6c52..7ef3a70c 100644
--- a/lib/functions.c
+++ b/lib/functions.c
@@ -62,6 +62,29 @@ void *xstrndup(char *s, size_t n)
return ret;
}
+// Die unless we can allocate enough space to sprintf() into.
+char *xmsprintf(char *format, ...)
+{
+ va_list va;
+ int len;
+ char *ret;
+
+ // How long is it?
+
+ va_start(va, format);
+ len = vsnprintf(0, 0, format, va);
+ len++;
+ va_end(va);
+
+ // Allocate and do the sprintf()
+ ret = xmalloc(len);
+ va_start(va, format);
+ vsnprintf(ret, len, format, va);
+ va_end(va);
+
+ return ret;
+}
+
// Die unless we can exec argv[] (or run builtin command). Note that anything
// with a path isn't a builtin, so /bin/sh won't match the builtin sh.
void *xexec(char **argv)
@@ -86,3 +109,38 @@ FILE *xfopen(char *path, char *mode)
if (!f) error_exit("No file %s\n", path);
return f;
}
+
+// int xread(int fd, char *buf, int len) // Die if can't fill buffer
+// int readall(int fd, char *buf, int len) // Keep reading until full or EOF
+// int toy_read(int fd, char *buf, int len) // retry if interrupted
+
+char *xgetcwd(void)
+{
+ char *buf = getcwd(NULL, 0);
+ if (!buf) error_exit("xgetcwd");
+}
+
+// Find this file in a colon-separated path.
+
+char *find_in_path(char *path, char *filename)
+{
+ char *next, *res = NULL, *cwd = xgetcwd();
+
+ while (next = index(path,':')) {
+ int len = next-path;
+
+ if (len==1) res = xmsprintf("%s/%s", cwd, filename);
+ else res = xmsprintf("%*s/%s",len-1,path,filename);
+ // Is there a file here we can execute?
+ if (!access(res, X_OK)) {
+ struct stat st;
+ // Confirm it's not a directory.
+ if (!stat(res, &st) && S_ISREG(st.st_mode)) break;
+ }
+ free(res);
+ res = NULL;
+ }
+ free(cwd);
+
+ return res;
+}
diff --git a/lib/lib.h b/lib/lib.h
index 157db343..4ac3f7bb 100644
--- a/lib/lib.h
+++ b/lib/lib.h
@@ -7,9 +7,12 @@ void *xmalloc(size_t size);
void *xzalloc(size_t size);
void xrealloc(void **ptr, size_t size);
void *xstrndup(char *s, size_t n);
+char *xmsprintf(char *format, ...);
void *xexec(char **argv);
int xopen(char *path, int flags, int mode);
FILE *xfopen(char *path, char *mode);
+char *xgetcwd(void);
+char *find_in_path(char *path, char *filename);
// llist.c
void llist_free(void *list, void (*freeit)(void *data));
diff --git a/toys.h b/toys.h
index 9460d368..e84736a0 100644
--- a/toys.h
+++ b/toys.h
@@ -12,6 +12,7 @@
#include <stdlib.h>
#include <string.h>
#include <strings.h>
+#include <sys/stat.h>
#include <unistd.h>
#include "lib/lib.h"