From nobody@FreeBSD.org  Tue Aug  8 14:41:37 2006
Return-Path: <nobody@FreeBSD.org>
Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125])
	by hub.freebsd.org (Postfix) with ESMTP id 2418216A4E0
	for <freebsd-gnats-submit@FreeBSD.org>; Tue,  8 Aug 2006 14:41:37 +0000 (UTC)
	(envelope-from nobody@FreeBSD.org)
Received: from www.freebsd.org (www.freebsd.org [216.136.204.117])
	by mx1.FreeBSD.org (Postfix) with ESMTP id A913043D45
	for <freebsd-gnats-submit@FreeBSD.org>; Tue,  8 Aug 2006 14:41:36 +0000 (GMT)
	(envelope-from nobody@FreeBSD.org)
Received: from www.freebsd.org (localhost [127.0.0.1])
	by www.freebsd.org (8.13.1/8.13.1) with ESMTP id k78EfahJ030120
	for <freebsd-gnats-submit@FreeBSD.org>; Tue, 8 Aug 2006 14:41:36 GMT
	(envelope-from nobody@www.freebsd.org)
Received: (from nobody@localhost)
	by www.freebsd.org (8.13.1/8.13.1/Submit) id k78Efao3030119;
	Tue, 8 Aug 2006 14:41:36 GMT
	(envelope-from nobody)
Message-Id: <200608081441.k78Efao3030119@www.freebsd.org>
Date: Tue, 8 Aug 2006 14:41:36 GMT
From: Spencer Minear <minear@securecomputing.com>
To: freebsd-gnats-submit@FreeBSD.org
Subject: Restore does not preserve uid and gid on short symlinks
X-Send-Pr-Version: www-2.3

>Number:         101660
>Category:       bin
>Synopsis:       restore(8) does not preserve uid and gid on short symlinks
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    maxim
>State:          closed
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Tue Aug 08 14:50:13 GMT 2006
>Closed-Date:    Sun Oct 08 05:53:09 GMT 2006
>Last-Modified:  Sun Oct 08 05:53:09 GMT 2006
>Originator:     Spencer Minear
>Release:        6.0
>Organization:
Securecomputing Corp.
>Environment:
Running on our SecureOS variant of 6.0
>Description:
The problem appears to come from the fact that short link information is stored in the inode (header data in the case of a restore file), and for longer links the link information is stored in the data.

In the tape.c:extract_file function is called to store a short link the static variable, curfile, contains information about the link being restored.  Many of the attributes are extracted from curfile at the entry to the function.  Later in the case IFLNK processing a call is made to getfile to obtain the data with the link value.  (NOTE:  I have not studied the workings of getfile so I'm conjecturing based on observation with gdb).  When a short link is being processed the is no data to read.  In this case getfile appears to read in the next file header in the restore file/stream and save the results in the curfile static variable.  The processing then proceeds to build the symbolic link and then set it attibutes.  All but two of the attributes are taken from data taht was carefully set asside on entry to the function.  Those last two attributes,  user id and group id, are read from the current file varible and are NOT necessarily the correct values.  Note the before and aft
 er lists below.

Before Dump

alpha:Admn {76} % ls -l
total 4
-r-xr-xr-x  1 a    user   0 Aug  7 16:44 F
lrwxr-xr-x  1 a    bin    1 Aug  8 08:46 FL -> F
lrwxr-xr-x  1 b    bin    1 Aug  8 08:49 ThelongwaytogettoFishere -> F
-rw-r--r--  1 bin  bin   54 Aug  7 07:34 fwregisterd.conf
-rw-r--r--  1 bin  bin   54 Aug  7 07:34 fwregisterd.conf.bak

After restore

alpha:Admn {66} % ls -l
total 4
-r-xr-xr-x  1 a    user   0 Aug  7 16:44 F
lrwxr-xr-x  1 bin  bin    1 Aug  8 08:46 FL -> F
lrwxr-xr-x  1 a    user   1 Aug  8 08:49 ThelongwaytogettoFishere -> F
-rw-r--r--  1 bin  bin   54 Aug  7 07:34 fwregisterd.conf
-rw-r--r--  1 bin  bin   54 Aug  7 07:34 fwregisterd.conf.bak

>How-To-Repeat:
Set up a directory near the root of the file system, a file with a short name, a link with a short name and link with a long name and a few other files.

Build the links using different identities so that the group owener are different.

Do a dump of the containing file system, then wipe out the directory and restor.

It is likely that the attributes on the short link will change to those of another file or link in the directory.

>Fix:
I believe that the fix for the problem is to simply save all of the relvant attributes on entry to the function and do not ever use attributes from curfile once the likes of getfile is called.
>Release-Note:
>Audit-Trail:

From: "Andrey V. Elsukov" <bu7cher@yandex.ru>
To: bug-followup@FreeBSD.org, minear@securecomputing.com
Cc:  
Subject: Re: bin/101660: restore(8) does not preserve uid and gid on short
 symlinks
Date: Wed, 16 Aug 2006 16:28:41 +0400

 Can you try the following patch:
 
 Index: tape.c
 ===================================================================
 RCS file: /mnt/cvs/ncvs/src/sbin/restore/tape.c,v
 retrieving revision 1.44
 diff -u -r1.44 tape.c
 --- tape.c	29 May 2005 15:57:00 -0000	1.44
 +++ tape.c	16 Aug 2006 12:18:00 -0000
 @@ -554,6 +554,7 @@
   	mode_t mode;
   	struct timeval mtimep[2], ctimep[2];
   	struct entry *ep;
 +	u_int32_t luid, lgid;
 
   	curfile.name = name;
   	curfile.action = USING;
 @@ -593,6 +594,8 @@
   	case IFLNK:
   		lnkbuf[0] = '\0';
   		pathlen = 0;
 +		luid = curfile.uid;
 +		lgid = curfile.gid;
   		getfile(xtrlnkfile, xtrlnkskip);
   		if (pathlen == 0) {
   			vprintf(stdout,
 @@ -600,7 +603,7 @@
   			return (GOOD);
   		}
   		if (linkit(lnkbuf, name, SYMLINK) == GOOD) {
 -			(void) lchown(name, curfile.uid, curfile.gid);
 +			(void) lchown(name, luid, lgid);
   			(void) lchmod(name, mode);
   			(void) lutimes(name, ctimep);
   			(void) lutimes(name, mtimep);
 
 -- 
 WBR, Andrey V. Elsukov

From: Spencer Minear <spencer_minear@securecomputing.com>
To: "Andrey V. Elsukov" <bu7cher@yandex.ru>
Cc: bug-followup@FreeBSD.org, minear@securecomputing.com
Subject: Re: bin/101660: restore(8) does not preserve uid and gid on short
 symlinks
Date: Wed, 16 Aug 2006 07:38:59 -0500

 The change you have is logically consistent with the change I put into
 our code tree a while back and it has proven to work fine and solved
 the problem I found.
 
 The only differences are that I used, pid_t and gid_t in the variable
 definitions, and I the values for the two new variables on function
 entry at the same time we get all of the other values out of curfile
 for later use.
 
 Thus, though I have not run your exact code, I believe it will fix the
 problem.
 
 -- Spence
 
  ---------------------------------------------------------------
 
    The information contained in this email message may be privileged,
    confidential and protected from disclosure. If you are not the
    intended recipient, any review, dissemination, distribution or
    copying is strictly prohibited. If you have received this email
    message in error, please notify the sender by reply email and
    delete the message and any attachments.
 
  Spencer Minear Ph. D. 			Secure Computing Corp.
  minear@securecomputing.com		2340 Energy Park Drive
  (651) 628-2756				St. Paul, MN 55108 U.S.A.
  (651) 628-2701 (fax)
  ---------------------------------------------------------------
 

From: "Andrey V. Elsukov" <bu7cher@yandex.ru>
To: bug-followup@FreeBSD.org, minear@securecomputing.com,
	maxim@freebsd.org
Cc:  
Subject: Re: bin/101660: restore(8) does not preserve uid and gid on short symlinks
Date: Wed, 16 Aug 2006 19:45:50 +0400 (MSD)

 I've merged some changes in tape.c from NetBSD.
 Patch is here: 
 http://butcher.heavennet.ru/patches/other/restore/tape.c.diff
 
 -- 
 WBR, Andrey V. Elsukov

From: Spencer Minear <spencer_minear@securecomputing.com>
To: bu7cher@yandex.ru
Cc: bug-followup@FreeBSD.org, minear@securecomputing.com, maxim@FreeBSD.org
Subject: Re: bin/101660: restore(8) does not preserve uid and gid on short symlinks
Date: Wed, 16 Aug 2006 10:48:18 -0500

 Thanks for the update.  They cleary covered the one issue I found.
 
 Looks like they took the uid/gid settings and applied the usage
 uniformly.  I did not go that far, but believe it definitly safe, if
 not necessary.
 
 -- Spence
 
  ---------------------------------------------------------------
 
    The information contained in this email message may be privileged,
    confidential and protected from disclosure. If you are not the
    intended recipient, any review, dissemination, distribution or
    copying is strictly prohibited. If you have received this email
    message in error, please notify the sender by reply email and
    delete the message and any attachments.
 
  Spencer Minear Ph. D. 			Secure Computing Corp.
  minear@securecomputing.com		2340 Energy Park Drive
  (651) 628-2756				St. Paul, MN 55108 U.S.A.
  (651) 628-2701 (fax)
  ---------------------------------------------------------------
 

From: Maxim Konovalov <maxim@macomnet.ru>
To: "Andrey V. Elsukov" <bu7cher@yandex.ru>
Cc: bug-followup@FreeBSD.org, minear@securecomputing.com
Subject: Re: bin/101660: restore(8) does not preserve uid and gid on short
 symlinks
Date: Wed, 16 Aug 2006 21:06:44 +0400 (MSD)

 On Wed, 16 Aug 2006, 19:45+0400, Andrey V. Elsukov wrote:
 
 > I've merged some changes in tape.c from NetBSD.
 > Patch is here:
 > http://butcher.heavennet.ru/patches/other/restore/tape.c.diff
 
 Thanks, I'll take a look at the diff tomorrow.
 
 -- 
 Maxim Konovalov
State-Changed-From-To: open->patched 
State-Changed-By: maxim 
State-Changed-When: Fri Aug 25 05:51:37 UTC 2006 
State-Changed-Why:  
I've just committed Andrey's patch.  Thanks! 


Responsible-Changed-From-To: freebsd-bugs->maxim 
Responsible-Changed-By: maxim 
Responsible-Changed-When: Fri Aug 25 05:51:37 UTC 2006 
Responsible-Changed-Why:  
Feedbacks trap. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=101660 
State-Changed-From-To: patched->closed 
State-Changed-By: maxim 
State-Changed-When: Sun Oct 8 05:52:53 UTC 2006 
State-Changed-Why:  
Merged to RELENG_6. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=101660 
>Unformatted:
