« February 2009 »
SunMonTueWedThuFriSat
1
2
4
5
6
7
8
9
10
11
13
14
15
16
17
18
19
21
23
24
25
27
       
       
Today
XML

Neat blogs

Navigation

Editing

Powered by Roller Weblogger.

statcounter.com

clustrmaps.com

Locations of visitors to this page

technorati.com

20090212 Thursday February 12, 2009
Playing with 'sec=none' and using AUTH_NONE

AUTH_NONE is one of the least understood security flavors you can use with NFS (see nfssec(5) for more details). When you share a resource, you can specify the security flavors with 'sec'. You can also specify an anonymous uid with 'anon'. I mention that because the two interact.

The way they interact is that any unauthenticated user id is mapped to the anonymous uid. The primary way to be unauthenticated is to be the root uid on the client and not be in the 'root' access list. As the default for 'anon' is -1, this means that the client root typically has no permissions on the server. A server admin can grant clients root permissions by saying 'anon=0' in the share. As we will see, that can be very dangerous.

The secondary way to be unauthenticated requires that the share to have 'sec=none' set. share_nfs(1M) states that if the client uses either AUTH_NONE or a security mode is one that is not in the share, then the NFS request is treated as unauthenticated.

Let's try some examples:

On the server

[root@pnfs-9-24 ~]> zfs create pnfs2/sysnone
[root@pnfs-9-24 ~]> zfs create pnfs2/sysnone0
[root@pnfs-9-24 ~]> zfs create pnfs2/sysnone55
[root@pnfs-9-24 ~]> zfs set sharenfs=sec=sys:none,anon=0 pnfs2/sysnone0
[root@pnfs-9-24 ~]> zfs set sharenfs=sec=sys:none pnfs2/sysnone
[root@pnfs-9-24 ~]> zfs set sharenfs=sec=sys:none,anon=55 pnfs2/sysnone55
[root@pnfs-9-24 ~]> chmod 777 /pnfs2/sysnone

Note that we have held off on doing the following:

[root@pnfs-9-24 ~]> chmod 777 /pnfs2/sysnone0
[root@pnfs-9-24 ~]> chmod 777 /pnfs2/sysnone55

And on the client:

[root@pnfs-9-23 ~]> mount -o vers=3,sec=none pnfs-9-24:/pnfs2/sysnone /mnt
[root@pnfs-9-23 ~]> ls -la /mnt
total 8
drwxrwxrwx   2 root     root           2 Feb 12 16:20 .
drwxr-xr-x  35 root     root          37 Feb 12 16:31 ..
[root@pnfs-9-23 ~]> touch /mnt/foo
[root@pnfs-9-23 ~]> ls -la !$
ls -la /mnt/foo
-rw-r--r--   1 nobody   nobody         0 Feb 12 21:58 /mnt/foo
[root@pnfs-9-23 ~]> umount /mnt

Since there was no anon set, we get -1.

[root@pnfs-9-23 ~]> mount -o vers=3,sec=none pnfs-9-24:/pnfs2/sysnone0 /mnt
[root@pnfs-9-23 ~]> touch /mnt/foo
[root@pnfs-9-23 ~]> ls -la /mnt/foo
-rw-r--r--   1 root     root           0 Feb 12 22:00 /mnt/foo
[root@pnfs-9-23 ~]> umount /mnt

Since 'anon=0', we are going to use uid 0. I'll point out the danger later.

[root@pnfs-9-23 ~]> mount -o vers=3,sec=none pnfs-9-24:/pnfs2/sysnone55 /mnt
[root@pnfs-9-23 ~]> touch /mnt/foo
touch: cannot create /mnt/foo: Permission denied

What happened here? Well, remember that we didn't set directory permissions, so it is most likely that root owns this 'directory':

[root@pnfs-9-24 ~]> ls -la /pnfs2/sysnone55
total 6
drwxr-xr-x   2 root     root           2 Feb 12 22:15 .
drwxr-xr-x  12 root     root          12 Feb 12 22:15 ..
[root@pnfs-9-24 ~]> chmod 777 /pnfs2/sysnone0
[root@pnfs-9-24 ~]> chmod 777 /pnfs2/sysnone55

The prior example worked because 'anon=0' matched up perfectly. So now:

[root@pnfs-9-23 ~]> touch /mnt/foo
[root@pnfs-9-23 ~]> ls -la /mnt/foo
-rw-r--r--   1 55       55             0 Feb 12 22:01 /mnt/foo
[root@pnfs-9-23 ~]> nfsstat -m /mnt
/mnt from pnfs-9-24:/pnfs2/sysnone55
 Flags:         vers=3,proto=tcp,sec=none,hard,intr,link,symlink,acl,rsize=32768,wsize=32768,retrans=5,timeo=600
 Attr cache:    acregmin=3,acregmax=60,acdirmin=30,acdirmax=60

Let's see some non-root behavior here:

[thud@pnfs-9-23 ~]> touch /mnt/bar
[thud@pnfs-9-23 ~]> ls -la /mnt
total 10
drwxrwxrwx   2 root     root           4 Feb 12 22:18 .
drwxr-xr-x  35 root     root          37 Feb 12 16:31 ..
-rw-r--r--   1 55       55             0 Feb 12 22:18 bar
-rw-r--r--   1 55       55             0 Feb 12 22:01 foo

And if we go back to the prior case (pnfs2/sysnone0):

[thud@pnfs-9-23 ~]> touch /mnt/bar
[thud@pnfs-9-23 ~]> ls -la /mnt
total 10
drwxrwxrwx   2 root     root           4 Feb 12 22:20 .
drwxr-xr-x  35 root     root          37 Feb 12 16:31 ..
-rw-r--r--   1 root     staff          0 Feb 12 22:20 bar
-rw-r--r--   1 root     root           0 Feb 12 22:00 foo

So if we mix 'sec=none' and 'anon=0', it is easy enough to give every remote user root access on the server.

But we haven't examined the real power of 'sec=none' here:

[root@pnfs-9-23 ~]> mount -o vers=3,sec=krb5i pnfs-9-24:/pnfs2/sysnone0 /mnt
nfs mount: security mode does not match the server exporting pnfs-9-24:/pnfs2/sysnone0
[root@pnfs-9-23 ~]> mount -o vers=4,sec=krb5i pnfs-9-24:/pnfs2/sysnone0 /mnt
[root@pnfs-9-23 ~]> nfsstat -m /mnt
/mnt from pnfs-9-24:/pnfs2/sysnone0
 Flags:         vers=4,proto=tcp,sec=krb5i,hard,intr,link,symlink,acl,rsize=1048576,wsize=1048576,retrans=5,timeo=600
 Attr cache:    acregmin=3,acregmax=60,acdirmin=30,acdirmax=60

Okay, our NFS tester extraordinary, Helen Chao, found a bug here. According to the man pages, you can argue that either the v3 case should have seen the mount succeed or fail. On the one hand, you specified that you wanted the mount to only be krb5i. On the other hand, you told the share to map all unlisted modes to AUTH_NONE. The slight bug here is that we need to clearly document what our expectations are here.

The next bug is not as minor one - v3 and v4 should have the same behavior. We don't care which side of the fence we fall on about allowed or denied, we just want consistency.

The next bug is very subtle here - 'nfsstat -m' reports that the mount is via krb5i. But is it? (Is this even a bug?)

[root@pnfs-9-23 ~]> touch /mnt/gar
[root@pnfs-9-23 ~]> ls -la /mnt
total 11
drwxrwxrwx   2 root     root           5 Feb 12 22:29 .
drwxr-xr-x  35 root     root          37 Feb 12 16:31 ..
-rw-r--r--   1 root     staff          0 Feb 12 22:20 bar
-rw-r--r--   1 root     root           0 Feb 12 22:00 foo
-rw-r--r--   1 root     root           0 Feb 12 22:29 gar

Can't tell anything there. Can I as a normal user?

[thud@pnfs-9-23 ~]> touch /mnt/googoo
touch: cannot stat /mnt/googoo: Permission denied
[thud@pnfs-9-23 ~]> kinit
Password for thud@NFSV4.SUN.COM: 
[thud@pnfs-9-23 ~]> touch /mnt/googoo
[thud@pnfs-9-23 ~]> ls -al /mnt
total 12
drwxrwxrwx   2 root     root           6 Feb 12 22:32 .
drwxr-xr-x  35 root     root          37 Feb 12 16:31 ..
-rw-r--r--   1 root     staff          0 Feb 12 22:20 bar
-rw-r--r--   1 root     root           0 Feb 12 22:00 foo
-rw-r--r--   1 root     root           0 Feb 12 22:29 gar
-rw-r--r--   1 root     root           0 Feb 12 22:32 googoo

Okay, so it isn't a bug at all - the client is correct here. I.e., the client is using kerberos to talk to the server. The share does not absolve the server from having to understand kerberos. We can clearly see that in that the user without a ticket is denied permission to create a file. And we also see that the uid is clearly mapped to the anon uid on the server.


Originally posted on Kool Aid Served Daily
Copyright (C) 2009, Kool Aid Served Daily