glibc: close privil. escalation hole ($origin libpath) with S/GUID.
authorArne Fitzenreiter <arne_f@ipfire.org>
Tue, 19 Oct 2010 16:12:09 +0000 (18:12 +0200)
committerArne Fitzenreiter <arne_f@ipfire.org>
Tue, 19 Oct 2010 16:12:09 +0000 (18:12 +0200)
lfs/glibc
src/patches/glibc-2.3.6-dont_use_origin_on_privil_exec.patch [new file with mode: 0644]

index 82394a2..c540b98 100644 (file)
--- a/lfs/glibc
+++ b/lfs/glibc
@@ -95,6 +95,8 @@ $(TARGET) : $(patsubst %,$(DIR_DL)/%,$(objects))
        @$(PREBUILD)
        @rm -rf $(DIR_APP) $(DIR_SRC)/glibc-build && cd $(DIR_SRC) && tar jxf $(DIR_DL)/$(DL_FILE)
        @mkdir $(DIR_SRC)/glibc-build
        @$(PREBUILD)
        @rm -rf $(DIR_APP) $(DIR_SRC)/glibc-build && cd $(DIR_SRC) && tar jxf $(DIR_DL)/$(DL_FILE)
        @mkdir $(DIR_SRC)/glibc-build
+       cd $(DIR_APP) && patch -Np1 -i $(DIR_SRC)/src/patches/$(THISAPP)-dont_use_origin_on_privil_exec.patch
+
 ifeq "$(ROOT)" ""
        cd $(DIR_APP) && patch -Np1 -i $(DIR_SRC)/src/patches/$(THISAPP)-linux_types-1.patch
        cd $(DIR_APP) && patch -Np1 -i $(DIR_SRC)/src/patches/$(THISAPP)-inotify-1.patch
 ifeq "$(ROOT)" ""
        cd $(DIR_APP) && patch -Np1 -i $(DIR_SRC)/src/patches/$(THISAPP)-linux_types-1.patch
        cd $(DIR_APP) && patch -Np1 -i $(DIR_SRC)/src/patches/$(THISAPP)-inotify-1.patch
diff --git a/src/patches/glibc-2.3.6-dont_use_origin_on_privil_exec.patch b/src/patches/glibc-2.3.6-dont_use_origin_on_privil_exec.patch
new file mode 100644 (file)
index 0000000..26c8ac8
--- /dev/null
@@ -0,0 +1,67 @@
+diff -Naur glibc-2.3.6.org/elf/dl-load.c glibc-2.3.6/elf/dl-load.c
+--- glibc-2.3.6.org/elf/dl-load.c      2005-04-06 04:50:10.000000000 +0200
++++ glibc-2.3.6/elf/dl-load.c  2010-10-19 17:41:09.000000000 +0200
+@@ -176,8 +176,7 @@
+ static size_t
+-is_dst (const char *start, const char *name, const char *str,
+-      int is_path, int secure)
++is_dst (const char *start, const char *name, const char *str, int is_path)
+ {
+   size_t len;
+   bool is_curly = false;
+@@ -206,11 +205,6 @@
+          && (!is_path || name[len] != ':'))
+     return 0;
+-  if (__builtin_expect (secure, 0)
+-      && ((name[len] != '\0' && (!is_path || name[len] != ':'))
+-        || (name != start + 1 && (!is_path || name[-2] != ':'))))
+-    return 0;
+-
+   return len;
+ }
+@@ -225,13 +219,12 @@
+     {
+       size_t len;
+-      /* $ORIGIN is not expanded for SUID/GUID programs (except if it
+-       is $ORIGIN alone) and it must always appear first in path.  */
++      /* $ORIGIN is not expanded for SUID/GUID programs.  */
+       ++name;
+-      if ((len = is_dst (start, name, "ORIGIN", is_path,
+-                       INTUSE(__libc_enable_secure))) != 0
+-        || (len = is_dst (start, name, "PLATFORM", is_path, 0)) != 0
+-        || (len = is_dst (start, name, "LIB", is_path, 0)) != 0)
++      if (((len = is_dst (start, name, "ORIGIN", is_path)) != 0
++         && !INTUSE(__libc_enable_secure))
++        || (len = is_dst (start, name, "PLATFORM", is_path)) != 0
++        || (len = is_dst (start, name, "LIB", is_path)) != 0)
+       ++cnt;
+       name = strchr (name + len, '$');
+@@ -263,12 +256,17 @@
+         size_t len;
+         ++name;
+-        if ((len = is_dst (start, name, "ORIGIN", is_path,
+-                           INTUSE(__libc_enable_secure))) != 0)
+-          repl = l->l_origin;
+-        else if ((len = is_dst (start, name, "PLATFORM", is_path, 0)) != 0)
++        if ((len = is_dst (start, name, "ORIGIN", is_path)) != 0)
++          {
++              // Ignore this path at SUID/GUID
++              if (INTUSE(__libc_enable_secure))
++                      repl = (const char *) -1;
++              else
++              repl = l->l_origin;
++          }
++        else if ((len = is_dst (start, name, "PLATFORM", is_path)) != 0)
+           repl = GLRO(dl_platform);
+-        else if ((len = is_dst (start, name, "LIB", is_path, 0)) != 0)
++        else if ((len = is_dst (start, name, "LIB", is_path)) != 0)
+           repl = DL_DST_LIB;
+         if (repl != NULL && repl != (const char *) -1)