Bug 1235 - [PATCH] scp does unnecessary getpwuid(), breaking chroot
Summary: [PATCH] scp does unnecessary getpwuid(), breaking chroot
Status: CLOSED WORKSFORME
Alias: None
Product: Portable OpenSSH
Classification: Unclassified
Component: scp (show other bugs)
Version: -current
Hardware: Other Linux
: P2 normal
Assignee: Assigned to nobody
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2006-09-25 09:59 AEST by Matthijs Kooijman
Modified: 2015-08-11 23:04 AEST (History)
2 users (show)

See Also:


Attachments
Patch for scp (480 bytes, patch)
2006-09-25 10:00 AEST, Matthijs Kooijman
no flags Details | Diff
Updated patch (480 bytes, patch)
2006-09-25 10:06 AEST, Matthijs Kooijman
no flags Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Matthijs Kooijman 2006-09-25 09:59:05 AEST
When started, scp will always call getpwuid() to retrieve information about the current user. 

This information is used by scp in "client mode" to determine the login name when none has been specified on the command line. scp in "server mode" (ie, when called with -t or -f) will never use the user information at all, but still requests it at startup.

Though this is not strictly a bug, it does have some unwanted side effects. In particular, this creates an added dependency for running scp inside a chroot jail, since username lookups must be enabled. This means that the passwd file or the used nss libs should be present inside the jail, which might not be wanted or possible (in our case).

The attached patch will simply skip the gepwuid() call when scp is called in "server mode". It has been running in our production environment for a while now. Though the patch has been created against OpenSSH 3.8 (FreeBSD 5.4), I've checked the CVS version and nothing seems to have changed that would break this patch.
Comment 1 Matthijs Kooijman 2006-09-25 10:00:13 AEST
Created attachment 1187 [details]
Patch for scp
Comment 2 Matthijs Kooijman 2006-09-25 10:06:19 AEST
Created attachment 1188 [details]
Updated patch

W00ps, the first patch was accidentally reversed. Here's a correct one.
Comment 3 Damien Miller 2008-06-15 05:56:31 AEST
I don't think this is correct: pwd is used in toremote() too, probably for remote->remote copies.
Comment 4 Matthijs Kooijman 2008-06-17 04:16:12 AEST
Hmm, I seem to remember that it was really unnecesary. This probably changed somewhere in the last two years :-)

Since then, we've moved from using an RSS chroot to a full FreeBSD jail, so I have no longer an interest in fixing this problem. Feel free to close this report if there is nobody else interested.
Comment 5 donkishoot 2009-06-24 23:41:20 AEST
I have a bug that i think is similar.

I'm trying to make a jail for winbind sftp users who must have an only sftp service (no shell).

This is the error i found when debugging (i replace scponlyc by bash for the test):

ssh usersftp1@192.168.2.1
bash-4.0$ chroot .
bash-4.0$ ./usr/libexec/openssh/sftp-server
No user found for uid 10653

Is their a workaround ?

I had no problem with this solution on an old Fedora.
Comment 6 Matthijs Kooijman 2009-06-25 00:26:33 AEST
(In reply to comment #3)
> I don't think this is correct: pwd is used in toremote() too, probably
> for remote->remote copies.
I just had another peek at the code, you are actually right. When I wrote the patch, I probably missed the fact that pwd is a global variable, and never used remote->remote copies.

Perhaps a more proper fix is then a gepwd() function, that uses the global variable as a cache. Something like:

struct passwd* getpwd() {
    if (pwd == NULL)
         if ((pwd = getpwuid(userid)) == NULL)
             fatal("unknown user %u", (u_int) userid);
    return pwd;
}

Replace the current pwd assignment with:

pwd = NULL;
userid = getuid()

and all the uses of pwd with getpwd().

It's not much of a patch, but I think the above would be all changes needed. This would of course still not allow remote->remote copies on a system without working usernames, but that's certainly a lot better than the current situation.

As I've said, we no longer use a setup like this, so I won't be able to provide a full and tested patch.

(In reply to comment #5)
> Is their a workaround ?

The problem is caused because winbind is not running / available inside the chroot. The nss_winbind library is probably not available, and if it was, the socket that it uses to connect to winbind is not available inside the chroot. You could try to fix these things, but I don't think that will be easy.

Another solution would be to ensure there is an /etc/passwd file inside the chroot, that at least contains the details of the current user. This you could probably achieve with a shell script, that should be wrapped _around_ scponly (i.e., it should be set as the user's shell and exec scponly at the end). This will probably generate a bunch of passwd files lying around.

The best thing you could do to solve this problem, is to try the changes to the code I suggested above, properly test them and submit a proper patch back here. Then you might be able to convince the OpenSSH developers to properly fix this issue once and for all.

Good luck!
Comment 7 Damien Miller 2013-10-24 11:12:35 AEDT
(In reply to donkishoot from comment #5)
> I have a bug that i think is similar.
> 
> I'm trying to make a jail for winbind sftp users who must have an
> only sftp service (no shell).
> 
> This is the error i found when debugging (i replace scponlyc by bash
> for the test):
> 
> ssh usersftp1@192.168.2.1
> bash-4.0$ chroot .
> bash-4.0$ ./usr/libexec/openssh/sftp-server
> No user found for uid 10653
> 
> Is their a workaround ?
> 
> I had no problem with this solution on an old Fedora.

We added "internal-sftp" to make sftp in chroot easier. See sshd_config's manpage and search for "internal-sftp".
Comment 8 Damien Miller 2015-08-11 23:04:55 AEST
Set all RESOLVED bugs to CLOSED with release of OpenSSH 7.1