]> WPIA git - gigi.git/commitdiff
Merge "add: support configuring SetUID behavior"
authorBenny Baumann <BenBE1987@gmx.net>
Tue, 20 Sep 2016 19:23:41 +0000 (21:23 +0200)
committerGerrit Code Review <gigi-system@dogcraft.de>
Tue, 20 Sep 2016 19:23:41 +0000 (21:23 +0200)
natives/org_cacert_gigi_natives_SetUID.c
src/org/cacert/gigi/Launcher.java

index 6c94d619a397dfdf891d25136753febe390be827..1b2350b4ab856102906013b6fcf80dfe8b0e6da5 100644 (file)
@@ -18,20 +18,45 @@ static jobject getStatus(JNIEnv *env, int successCode, const char * message) {
 }
 
 JNIEXPORT jobject JNICALL Java_org_cacert_gigi_natives_SetUID_setUid
-        (JNIEnv *env, jobject obj, jint uid, jint gid) {
+        (JNIEnv *env, jobject obj, jint uid_, jint gid_) {
 
     /* We don't need the reference for the object/class we are working on */
     (void)obj;
+    /* Fix uid and gid types */
+    uid_t uid = (uid_t)uid_;
+    if ((jint)uid != uid_) {
+      return getStatus(env, 0, "UID does not fit in uid_t type.");
+    }
+    gid_t gid = (gid_t)gid_;
+    if ((jint)gid != gid_) {
+      return getStatus(env, 0, "GID does not fit in gid_t type.");
+    }
 
-    if(setgid((int)gid)) {
-        return (jobject)getStatus(env, 0, "Error while setting GID.");
+    unsigned char work = 0;
+
+    if(getgid() != gid || getegid() != gid) {
+        if(setgid(gid)) {
+            return getStatus(env, 0, "Error while setting GID.");
+        }
+        work |= 1;
     }
 
-    if(setuid((int)uid)) {
-        return (jobject)getStatus(env, 0, "Error while setting UID.");
+    if(getuid() != uid || geteuid() != uid) {
+        if(setuid(uid)) {
+            return getStatus(env, 0, "Error while setting UID.");
+        }
+        work |= 2;
     }
 
-    return (jobject)getStatus(env, 1, "Successfully set uid/gid.");
+    char *status;
+    switch (work) {
+    case 0: status = "UID and GID already set."; break;
+    case 1: status = "Successfully set GID (UID already set)."; break;
+    case 2: status = "Successfully set UID (GID already set)."; break;
+    case 3: status = "Successfully set UID and GID."; break;
+    default: return getStatus(env, 0, "Unexpected internal state.");
+    }
+    return getStatus(env, 1, status);
 }
 
 #ifdef __cplusplus
index 5f767a63956a3da4ce8cb4be5256e8403b77da68..7c588d8e95a28b49183735478489b2f09e6309f0 100644 (file)
@@ -132,9 +132,23 @@ public class Launcher {
 
         s.start();
         if ((isSystemPort(ServerConstants.getSecurePort()) || isSystemPort(ServerConstants.getPort())) && !System.getProperty("os.name").toLowerCase().contains("win")) {
-            SetUID uid = new SetUID();
-            if ( !uid.setUid(65536 - 2, 65536 - 2).getSuccess()) {
-                Log.getLogger(Launcher.class).warn("Couldn't set uid!");
+            String uid_s = conf.getMainProps().getProperty("gigi.uid", Integer.toString(65536 - 2));
+            String gid_s = conf.getMainProps().getProperty("gigi.gid", Integer.toString(65536 - 2));
+            try {
+                int uid = Integer.parseInt(uid_s);
+                int gid = Integer.parseInt(gid_s);
+                if (uid == -1 && gid == -1) {
+                    // skip setuid step
+                } else if (uid > 0 && gid > 0 && uid < 65536 && gid < 65536) {
+                    SetUID.Status status = new SetUID().setUid(uid, gid);
+                    if ( !status.getSuccess()) {
+                        Log.getLogger(Launcher.class).warn(status.getMessage());
+                    }
+                } else {
+                    Log.getLogger(Launcher.class).warn("Invalid uid or gid (must satisfy 0 < id < 65536)");
+                }
+            } catch (NumberFormatException e) {
+                Log.getLogger(Launcher.class).warn("Invalid gigi.uid or gigi.gid", e);
             }
         }
     }