Linux and Active Directory round 2

* edit Jan 12 2010. Better more reliable scripts.

* edit Oct 27th The netbook deployment went well this time. Feedback is generally that they have less problems than our Windows machines. Using Impress instead of MS powerpoint seems to be the biggest issue as Impress has trouble importing some powerpoint files in the office open XML format. Next on my todo list is play around with Unison file sync, NFS, and update this guide to reflect some improvements a colleague made.

The goal here is to create typical Windows Active Directory connect like Linux workstation. This includes being able to log in using Active Directory and mount various shared folders. It also must be idiot proof. We don’t want users saving on the desktop not realizing the desktop is not part of their smb share. It also must be cloneable. There should be absolutely no required interaction with the the computer after putting on this image.

Active Directory Integration

I choose to use Centrify for this. Likewise open is another option, but it seemed more buggy and I hate the way you have to configure it.

Ok make sure partner repositories are enabled and install centrifydc. If you want to make a clone-able image set your host name as something generic like “stockimage”. Add this script to crontab’s @restart

#!/bin/bash
hostCurrent=$(hostname)
hostOld='image'
commonauth='/etc/pam.d/common-auth'
if [ "$hostCurrent" == "$hostOld" ]
then
    (
    set -x
    host1=$(/usr/sbin/dmidecode | grep 'Serial Number: ' | sed 's/.*: \(.*\)/\1/;q')
    host2=
    host=$host1$host2
    host=$(echo $host | sed 's/[ ]*//g')
    hostname $host
    echo $host > /etc/hostname
    # TODO: axe this ugly hack and have upstart call us when we're connected
    counter=0
    while [ $counter -lt 60 ] && [ ! `/sbin/route -n | sed -rn 's/^0\.0\.0\.0[ ]+([0-9.]+)[ ]+0\.0\.0\.0.*/\1/p'` ]
    do
        sleep 1
        counter=`expr $counter + 1`
    done
    # Do NOT put regular administrator password here!
    # Use a special account and keep it DISABLED.
    /usr/sbin/adleave -u 'j' -p 'secret'
    /usr/share/centrifydc/bin/centrifydc stop
    /usr/sbin/adjoin -f -u 'j' -p 'secret' -w --name $host youradserver.com
set +x
    ) >& /opt/ad.log
    /sbin/reboot
elif [ "`sed 1q $commonauth | grep '^# lines inserted by Centrify'`" ]
then
    # Prevent double password prompt
    pammount=`sed -rn '/^auth[ ]+optional[ ]+pam_mount.so$/p' $commonauth`
    sed -ri '/^auth[ ]+optional[ ]+pam_mount.so$/d' $commonauth
    sed -ri 's/^(auth[ ]+sufficient[ ]+pam_centrifydc.so)$/\1 try_first_pass/' $commonauth
    sed -i  "1i\\$pammount" $commonauth
    /sbin/reboot
fi

That script will rename the hostname to something unique and join your domain. Because it’s on @reboot it runs every time the computer is turned on thus when you image it, it runs! Maybe put this in crontab last because you don’t want it running on your image. If you’re only joining one machine to AD then just run the adjoin command.

Ok bug work around time! I said Centrify is less buggy remember. This is only important for multi user machines, if there will only be one user you may skip this section. Ubuntu will boot well before you are online and thus a new user will get Authentication Error when trying to log in right away. To fix this first of all make sure if you use wireless that “enabled for all users” is checked in NetworkManager.

Next we need GDM to wait for centrify to connect before starting. We can do this with upstart.

Edit /etc/init/gdm.conf and look for the start on section. This basically tells GDM to only start once certain things have happened. Add centrify-connected to the bottom as seen here.

start on (filesystem
and started dbus
and (graphics-device-added fb0 PRIMARY_DEVICE_FOR_DISPLAY=1
or drm-device-added card0 PRIMARY_DEVICE_FOR_DISPLAY=1
or stopped udevtrigger)
and centrify-connected)

Now it we need to make the centrify-connected signal. Edit /etc/init.d/centrifydc and look for case “$CMD” in start). Add “initctl emit centify-connected” under wait_adclient  Like this.

start)
adclient_check
echo -n "Starting $NAME: "
start-stop-daemon --start --quiet --exec $DAEMON --pidfile $PIDFILE \
-- $OPTIONS
RETVAL=$?
if [ $RETVAL -eq 0 ]; then
echo "OK"
wait_adclient
# upstart won't start gdm until we say we're connected
initctl emit centrify-connected  # added
else
echo "FAIL

That emits the signal telling GDM that Centrify is connected. The script is part of Centrify, it just didn’t emit the signal. It’s like they thought of this problem but didn’t actually fix it.You could reboot now if you wanted and it should work, but there’s much more we can do.

If your splash no longer shows up (happens to me 100% of the time on 10.04). You can try this command to fix it. I add this note because it can take a while for wifi to connect, then centrify to find AD, then GDM to start. If the users stares at the black screen for 1 minute they will probably assume the computer is just broken.

sudo -i
echo FRAMEBUFFER=y > /etc/initramfs-tools/conf.d/splash Code:
update-initramfs -u

Mount Windows Shares

Now your users will fire up nautilus and start browsing windows shares. smb://something.company.com/user$/myuser/documents is so easy to remember right? 😛

Lets face it users don’t know what a file share is usually. Lets mount them automatically for them like Windows does.

sudo apt-get install libpam-mount smbfs

Now edit /etc/security/pam_mount.conf.xml

make it looks something like this in the section <pam_mount> Make sure to change it for your own purposes. In this example I’m mounting a user’s documents folder.


<pam_mount>

<!-- Volume definitions -->

<volume user="*" fstype="cifs" server="server" path="users/%(DOMAIN_USER)" mountpoint="~/Documents" />

Don’t try mounting anything as Desktop because gnome won’t like it. There is a workaround here if you really need Desktop to be part of the share. First turn off the auto-creation of these folders (this puts you in charge of making them! Nautilus will not start if it doesn’t have these folders! Yes Nautilus sucks.) Edit /etc/xdg/user-dirs.conf and set enabled to False. Now edit /etc/skel/.profile and add the lines

mkdir "$HOME/Documents/Desktop" 2> /dev/null
ln -s "$HOME/Documents/Desktop" "$HOME/Desktop" 2> /dev/null
mkdir "$HOME/Documents/Downloads" 2> /dev/null
ln -s "$HOME/Documents/Downloads" "$HOME/Downloads" 2> /dev/null

This would symlink the Desktop and Downloads folder to be inside of Documents. Documents in actually a smb share. This should keep users saving files in places that are in smb.

There are two Ubuntu bugs related to smbfs. If your system hangs at logout look here

https://bugs.launchpad.net/ubuntu/+source/libpam-mount/+bug/574329

If it hangs at shutdown look here

https://bugs.launchpad.net/ubuntu/+source/samba/+bug/211631

Ok another Centrify bug work around is explained here Centrify goofs up pam_mount. I mean who would really want to connect to shares AND use active directory  😉  If you can’t handle clicking

1) Open /etc/pam.d/common-auth file

2) Check if “auth optional pam_mount.so” is the first line and “auth sufficient pam_centrifydc.so” second line. If “yes” then change the second line to:

auth       sufficient     pam_centrifydc.so try_first_pass

I also found that adding try_first_pass to the pam_unix.so line will allow non AD users to log in without entering the password twice.

Odds and ends

If you want to give some users sudo edit /etc/sudoers and add

%ADMIN\\UnixAdmins ALL = (ALL) ALL

That command would give the UnixAdmins group in the domain ADMIN sudo access.

If you want to edit the default desktop install a program called sabayon. It crashes sometimes but when not crashing it works pretty well. For some reason rebooting fixes it’s crashing…weird.

Another problem is that non admin users can disable network manager for the entire system even after a reboot! I’m not sure what to do about this, it’s a major headache because users won’t be able to log in at all without networking. I can’t think of any fix other than disabling network manager, but this is not ideal as sometimes there are legitimate uses for network manager.

As Mike pointed one could use the adjoin –selfserve command if AD knows the hostnames in advance. I choose to use an account that is usually disabled so if users see the password, they won’t be able to do much.

Compared to Windows this is a huge pain the first time to get right but cloning is way easier. I love running one image on many different models of computers. I moved the image around to several computers fine tuning it for each one. That included installing specific drivers. In the end I have one image that can be deployed anywhere.

I’m still missing a few must have features such as syncing the entire home folder to a share. NFS home folder is not enough, try leaving the building with your NFS home folder laptop. iFolder is an option I want to look into more. My initial experience is that it’s difficult to configure. It also doesn’t give you a CIFS interface which is often nice to have. There are any number of hosted solutions (Dropbox, JungleDisk, Ubuntu one, etc) that might work for you. It’s a shame Canonical won’t offer this as an on site solution like they do Landscape. Sparkle Share is an upcoming project that aims to meet this need but it’s not ready yet. You could also look into CMS software such as Alfresco.

19 thoughts on “Linux and Active Directory round 2”

  1. A couple tricks to improve your scripts:

    1. If you know the hostnames in advance, you can pre-create the computer account in Active Directory ADUC->Action->New->Computer and use the “adjoin –selfserve” option to join the domain without requiring a password in the script.

    2. adinfo has a -m option to just report the connected/starting/disconnected status. 0 is connected, 1 is not connected, any other return means it’s still starting or not running.

  2. Thanks for the great guide

    I’ve got one problem – as soon as I join the domain I can’t use sudo. I get ‘k is not in the sudoers file. This incident will be reported.’

    My /etc/sudoers file is unchanged and k is still in the admin group.

    I’m using ubuntu 10.10. Any ideas?

    Thanks

  3. That’s strange. I believe it’s the “sudo” group that determines this not admin. Make sure k is in the sudo group. You can also add groups to your sudors file
    %group_name = (ALL) ALL

    Or you can add a specific user
    k ALL=(ALL) ALL

    Hope that helps.

  4. Thanks for the comments, managed to solve it – if there’s a user or group called admin in AD it messes it up, need to add admin to the /etc/centrifydc/group.ignore file.

    BTW, it is incredibly difficult to work out where to put the captcha code on your page – the text box is the same colour as the background and there’s no border so it blends in

  5. Mainly Centrify is easier to set up. Winbind is a nightmare to set up. It also doesn’t take into account the wait for networking issue (To be fair Centrify requires some configuring to get this to work). Winbind in my opinion is the apex of what’s wrong in Linux.

    I do use of Samba. Samba is also a very poor solution in terms of features. In a mobile world one needs hybrid solutions between mounting as a traditional network share and syncing locally. There isn’t any good alternative sadly.

  6. Hi David,

    Been folowing your guide and it works nicely on Ubuntu 11.10 also…
    Have you had any luck with making the all home folder redirected to a share?

    Any way pam_mount or any other solution to create the a home folder inside a primary share when it doesnt exist on the server?

    Thanks!

  7. I haven’t had any luck mounting the entire home in AD. I’ve seen people claim it possible but I’ll believe it when I see it. You might consider syncing the home folder rather than mounting it, or at least just many of the folders. Unison sync script but the issue here is syncing takes some time, so you can’t depend on it for the first boot. I’m guessing you want the config files mounted but this won’t work and having the sync script start changing them might cause instability.

    Now if you really wanted to get your hands dirty you could make Linux sync the config files before loading the desktop environment. You can see Windows does this on first boot there is that somewhat annoying (but SO useful) loading profile that takes a minute or two.

    Login > unison grabs files from server (or if not existing creates them) > Gnome or whatever loads.

    I’m not sure where you could put the script that would need to finish before Gnome starts. You’d also have to notify the user somehow else they would just assume the computer crashed.

    For making the folders in the server, you will have to script it. I have it scripted on my user creation, but you could probably get the client to do it too if the folder doesn’t exist. There’s no automatic prepackaged way of doing this that I know of.

  8. Hi again David,

    Never thought about syncing folders but its a nice aproach since mounting the all home folder seems not be an option for now.

    I saw your scrit and it works just fine.

    I was thinking on trying to put it on logon or loggoff so it sync some folders. Do you think that is possible to let the cript recognize the domain user name so it could run on logon or logoff?

    Thanks once again!

  9. Syncing has worked for me as long as it’s just one user since it doesn’t do any conflict resolution (new time always wins).

    $USER should work fine for you since your domain user should be the same. If you have multiple domains where you need something like $DOMAIN/$USER that might make it more complicated. I use pam_mount to put the user’s networked home folder in ~/.home which is a hidden file the user never sees. Then I sync ~/whatever to ~/.home/whatever I’m sure this is just one of many ways to do it but by using pam_mount you can trust the mount will just be there without having to think about authentication.

Leave a Reply

Your email address will not be published. Required fields are marked *

*