The following commit has been merged in the master branch:
commit d25407536dbed4cad2943187b36fbb6c92a6b5ab
Author: Guillem Jover <guil...@debian.org>
Date:   Wed Jul 28 15:06:19 2010 +0200

    dpkg: Assign correct SE Linux label to non-regular files
    
    The call to matchpathcon() was getting passed only the permission bits
    of the mode argument, instead of the format type. Map the tar filetype
    to the Unix mode and OR that information into the tar_entry mode member.
    
    Closes: #587949
    
    Based-on-patch-by: Russell Coker <russ...@coker.com.au>
    Signed-off-by: Guillem Jover <guil...@debian.org>

diff --git a/debian/changelog b/debian/changelog
index 9a1248c..28d26d6 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -97,6 +97,8 @@ dpkg (1.15.8) UNRELEASED; urgency=low
   * Consistently use earlier/later instead of smaller/bigger when describing
     comparison relationships. Closes: #587641
   * Stop exporting DPKG_LIBDIR to maintainer scripts, no need for it anymore.
+  * Assign correct SE Linux label on non-regular files. Based on a patch by
+    Russell Coker <russ...@coker.com.au>. Closes: #587949
 
   [ Updated programs translations ]
   * Catalan (Guillem Jover).
diff --git a/lib/dpkg/tarfn.c b/lib/dpkg/tarfn.c
index c24e85d..c5b598d 100644
--- a/lib/dpkg/tarfn.c
+++ b/lib/dpkg/tarfn.c
@@ -22,6 +22,8 @@
 #include <config.h>
 #include <compat.h>
 
+#include <sys/stat.h>
+
 #include <errno.h>
 #include <string.h>
 #include <pwd.h>
@@ -111,6 +113,45 @@ get_prefix_name(struct TarHeader *h)
        return s;
 }
 
+static mode_t
+get_unix_mode(struct TarHeader *h)
+{
+       mode_t mode;
+       enum tar_filetype type;
+
+       type = (enum tar_filetype)h->LinkFlag;
+
+       switch (type) {
+       case tar_filetype_file0:
+       case tar_filetype_file:
+               mode = S_IFREG;
+               break;
+       case tar_filetype_symlink:
+               mode = S_IFLNK;
+               break;
+       case tar_filetype_dir:
+               mode = S_IFDIR;
+               break;
+       case tar_filetype_chardev:
+               mode = S_IFCHR;
+               break;
+       case tar_filetype_blockdev:
+               mode = S_IFBLK;
+               break;
+       case tar_filetype_fifo:
+               mode = S_IFIFO;
+               break;
+       case tar_filetype_hardlink:
+       default:
+               mode = 0;
+               break;
+       }
+
+       mode |= OtoL(h->Mode, sizeof(h->Mode));
+
+       return mode;
+}
+
 static int
 DecodeTarHeader(char *block, struct tar_entry *d)
 {
@@ -139,7 +180,7 @@ DecodeTarHeader(char *block, struct tar_entry *d)
        else
                d->name = StoC(h->Name, sizeof(h->Name));
        d->linkname = StoC(h->LinkName, sizeof(h->LinkName));
-       d->mode = (mode_t)OtoL(h->Mode, sizeof(h->Mode));
+       d->mode = get_unix_mode(h);
        d->size = (size_t)OtoL(h->Size, sizeof(h->Size));
        d->mtime = (time_t)OtoL(h->ModificationTime,
                                sizeof(h->ModificationTime));
diff --git a/src/archives.c b/src/archives.c
index 31c5f0c..d1daed4 100644
--- a/src/archives.c
+++ b/src/archives.c
@@ -261,6 +261,10 @@ set_selinux_path_context(const char *matchpath, const char 
*path, mode_t mode)
   security_context_t scontext = NULL;
   int ret;
 
+  /* If there's no file type, just give up. */
+  if ((mode & S_IFMT) == 0)
+    return;
+
   /* Set selinux_enabled if it is not already set (singleton). */
   if (selinux_enabled < 0)
     selinux_enabled = (is_selinux_enabled() > 0);
@@ -274,7 +278,7 @@ set_selinux_path_context(const char *matchpath, const char 
*path, mode_t mode)
 
   /* Do nothing if we can't figure out what the context is, or if it has
    * no context; in which case the default context shall be applied. */
-  ret = matchpathcon(matchpath, mode & ~S_IFMT, &scontext);
+  ret = matchpathcon(matchpath, mode & S_IFMT, &scontext);
   if (ret == -1 || (ret == 0 && scontext == NULL))
     return;
 
@@ -761,9 +765,7 @@ tarobject(void *ctx, struct tar_entry *ti)
     internerr("unknown tar type '%d', but already checked", ti->type);
   }
 
-  set_selinux_path_context(fnamevb.buf, fnamenewvb.buf,
-                           nifd->namenode->statoverride ?
-                           nifd->namenode->statoverride->mode : ti->mode);
+  set_selinux_path_context(fnamevb.buf, fnamenewvb.buf, ti->mode);
 
   /* CLEANUP: Now we have extracted the new object in .dpkg-new (or,
    * if the file already exists as a directory and we were trying to extract

-- 
dpkg's main repository


-- 
To UNSUBSCRIBE, email to debian-dpkg-cvs-requ...@lists.debian.org
with a subject of "unsubscribe". Trouble? Contact listmas...@lists.debian.org

Reply via email to