- Modified arguments checking code to support an allowed types mask instead
authorMatthew Mondor <mmondor@pulsar-zone.net>
Thu, 14 Sep 2006 05:53:00 +0000 (05:53 +0000)
committerMatthew Mondor <mmondor@pulsar-zone.net>
Thu, 14 Sep 2006 05:53:00 +0000 (05:53 +0000)
- Added fchown(2) which can be passed integers or strings as wanted

mmsoftware/js/classes/js_fd.c

index a453df9..df683e0 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: js_fd.c,v 1.7 2006/09/07 05:17:26 mmondor Exp $ */
+/* $Id: js_fd.c,v 1.8 2006/09/14 05:53:00 mmondor Exp $ */
 
 /*
  * Copyright (c) 2005, Matthew Mondor
 #include <assert.h>
 #include <errno.h>
 #include <fcntl.h>
-#include <unistd.h>
+#include <grp.h>
 #include <poll.h>
+#include <pwd.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <unistd.h>
 
 #include <jsapi.h>
 
@@ -129,10 +131,10 @@ struct poll_fds {
 
 /* Functions arguments types */
 enum jsarg_types {
-       JSAT_INTEGER = 1,
-       JSAT_DOUBLE,
-       JSAT_STRING,
-       JSAT_OBJECT
+       JSAT_INTEGER =  (1 << 1),
+       JSAT_DOUBLE =   (1 << 2),
+       JSAT_STRING =   (1 << 3),
+       JSAT_OBJECT =   (1 << 4)
 };
 
 
@@ -168,6 +170,7 @@ static JSBool       fd_m_read(JSContext *, JSObject *, uintN, jsval *, jsval *);
 static JSBool  fd_m_fdatasync(JSContext *, JSObject *, uintN, jsval *,
                    jsval *);
 static JSBool  fd_m_lseek(JSContext *, JSObject *, uintN, jsval *, jsval *);
+static JSBool  fd_m_fchown(JSContext *, JSObject *, uintN, jsval *, jsval *);
 static JSBool  fd_m_fchmod(JSContext *, JSObject *, uintN, jsval *, jsval *);
 static JSBool  fd_m_flock(JSContext *, JSObject *, uintN, jsval *, jsval *);
 static JSBool  fd_m_fstat(JSContext *, JSObject *, uintN, jsval *, jsval *);
@@ -210,6 +213,7 @@ enum fd_methods_args_enum {
        FDMA_WRITE,
        FDMA_FDATASYNC,
        FDMA_LSEEK,
+       FDMA_FCHOWN,
        FDMA_FCHMOD,
        FDMA_FLOCK,
        FDMA_FSTAT,
@@ -234,6 +238,8 @@ static int fd_methods_args_array[FDMA_MAX][6] = {
        { 1, JSAT_STRING },                             /* WRITE */
        { 0 },                                          /* FDATASYNC */
        { 2, JSAT_DOUBLE, JSAT_INTEGER },               /* LSEEK */
+       { 2, JSAT_STRING | JSAT_INTEGER,
+               JSAT_STRING | JSAT_INTEGER },           /* FCHOWN */
        { 1, JSAT_INTEGER },                            /* FCHMOD */
        { 1, JSAT_INTEGER },                            /* FLOCK */
        { 0 }                                           /* FSTAT */
@@ -260,6 +266,7 @@ static JSFunctionSpec fd_methods[] = {
        { "write", fd_m_write, 1, 0, 0 },
        { "fdatasync", fd_m_fdatasync, 0, 0, 0 },
        { "lseek", fd_m_lseek, 2, 0, 0 },
+       { "fchown", fd_m_fchown, 2, 0, 0 },
        { "fchmod", fd_m_fchmod, 1, 0, 0 },
        { "flock", fd_m_flock, 1, 0, 0 },
        { "fstat", fd_m_fstat, 0, 0, 0 },
@@ -1527,6 +1534,61 @@ fd_m_lseek(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
 }
 
 static JSBool
+fd_m_fchown(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
+{
+       jsfd_t          *jsfd;
+       struct passwd   *pwd;
+       struct group    *grp;
+       char            *str, e[1024];
+       uid_t           uid;
+       gid_t           gid;
+
+       *rval = OBJECT_TO_JSVAL(NULL);
+
+       if ((jsfd = fd_methods_args_check(cx, obj, "fchown", FDMA_FCHOWN,
+           argc, argv, JSFD_FILE)) == NULL)
+               return JS_FALSE;
+
+       if (JSVAL_IS_STRING(argv[0])) {
+               if ((str = JS_GetStringBytes(JSVAL_TO_STRING(argv[0])))
+                   == NULL) {
+                       QUEUE_EXCEPTION("Internal error!");
+                       return JS_FALSE;
+               }
+               if ((pwd = getpwnam(str)) == NULL) {
+                       (void) snprintf(e, 1023, "Unknown user '%s'", str);
+                       QUEUE_EXCEPTION(e);
+                       return JS_FALSE;
+               }
+               uid = pwd->pw_uid;
+       } else
+               uid = JSVAL_TO_INT(argv[0]);
+
+       if (JSVAL_IS_STRING(argv[1])) {
+               if ((str = JS_GetStringBytes(JSVAL_TO_STRING(argv[1])))
+                   == NULL) {
+                       QUEUE_EXCEPTION("Internal error!");
+                       return JS_FALSE;
+               }
+               if ((grp = getgrnam(str)) == NULL) {
+                       (void) snprintf(e, 1023, "Unknown group '%s'", str);
+                       QUEUE_EXCEPTION(e);
+                       return JS_FALSE;
+               }
+               gid = grp->gr_gid;
+       } else
+               gid = JSVAL_TO_INT(argv[1]);
+
+       if (fchown(jsfd->fd, uid, gid) == -1) {
+               jsfd->error = errno;
+               QUEUE_EXCEPTION(strerror(errno));
+               return JS_FALSE;
+       }
+
+       return JS_TRUE;
+}
+
+static JSBool
 fd_m_fchmod(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
 {
        jsfd_t          *jsfd;
@@ -1957,6 +2019,36 @@ fd_methods_args_check(JSContext *cx, JSObject *obj, const char *fun, int id,
        }
 
        for (p++, i = 0; i < argc; i++) {
+               int     cur;
+
+               cur = 0;
+               if (JSVAL_IS_INT(argv[i]) || JSVAL_IS_DOUBLE(argv[i]))
+                       cur |= JSAT_INTEGER | JSAT_DOUBLE;
+               else if (JSVAL_IS_STRING(argv[i]))
+                       cur |= JSAT_STRING;
+               if ((p[i] & cur) == 0) {
+                       char    types[256];
+
+                       *types = '\0';
+                       if ((p[i] & JSAT_INTEGER) != 0)
+                               (void) strcat(types, "INTEGER ");
+                       if ((p[i] & JSAT_DOUBLE) != 0)
+                               (void) strcat(types, "DOUBLE ");
+                       if ((p[i] & JSAT_STRING) != 0)
+                               (void) strcat(types, "STRING ");
+                       if ((p[i] & JSAT_OBJECT) != 0)
+                               (void) strcat(types, "OBJECT ");
+                       types[strlen(types) - 1] = '\0';
+                       (void) snprintf(line, 1023,
+                           "%s() - argument #%d not of expected type(s) (%s)",
+                           fun, i + 1, types);
+                       QUEUE_EXCEPTION(line);
+                       return NULL;
+               }
+       }
+
+       /*
+       for (p++, i = 0; i < argc; i++) {
                switch (p[i]) {
                case JSAT_INTEGER:
                        if (!JSVAL_IS_INT(argv[i])) {
@@ -1994,6 +2086,7 @@ fd_methods_args_check(JSContext *cx, JSObject *obj, const char *fun, int id,
                        return NULL;
                }
        }
+       */
 
        if ((jsfd = JS_GetInstancePrivate(cx, obj, &fd_class, NULL))
            == NULL) {