mycroes

There's always time to play

Saturday, April 21, 2012

When security matters ...

... password restrictions are retarded. When I wanted to activate an online account for my creditcard I entered the same secure password I always use, but guess what, it was not accepted. The password restrictions are as follows:
Het door u gekozen wachtwoord voldoet niet aan de eisen. Uw wachtwoord moet bestaan uit minimaal één cijfer en vijf letters. De maximale lengte is tien cijfers en/of letters. Leestekens en symbolen zoals !@#$%&^*_ worden niet herkend. Let op: uw wachtwoord is hoofdlettergevoelig.
... in English:
The chosen password does not meet our requirements. Your password has to contain at least one digit and five characters. The maximum length is ten digits and/or characters. Punctuation marks and symbols such as !@#$%&^*_ are not recognized. Attention: your password is case sensitive.
Seriously? Please International Card Services, get your stuff together and stop the retarded password restrictions and accept secure passwords for a change...

Friday, February 10, 2012

Linux integration with Active Directory: part 1

At work I've been running Samba 4 for quite a while. Because Samba 4 is still in Alpha I didn't just move everything over to use Samba 4 for authentication, but instead I started out by moving services over one by one. I actually started with e-mail routing (will detail in a later post) and authentication. Later on I added proxy authentication and fileserver authentication / authorization, Windows XP and Windows 7 clients and last but not least actual Linux (PAM) user authentication.

In this post I will detail how to join a (Debian / Ubuntu) Linux machine to the domain, setup Kerberos, setup nss to make Linux aware of domain users and setting up PAM to allow domain user authentication. I'm using Samba 4 as Active Directory implementation, however this should all just work against a Windows server hosted Active Directory as well. I'm going to make use of a feature that requires Windows Server 2003R2 or newer, or IDMU (Identity Management for Unix), but that's only used to store the users' shell in Active Directory.

First off, I'm assuming that DNS is properly set up. It's not needed, since both Kerberos and Samba can be made to work without DNS, but best case that means a lot of hosts file mess on almost all involved computers. Honestly it's easier to even do a manual DNS setup than to keep such a hosts file mess up to date. I will detail some parts for the non-DNS case as well, since it's useful information.

Setting up Kerberos


Now on to the real work. Setting up Kerberos is really easy:
# apt-get install krb5-config

This should probably ask just one question: the default Kerberos realm. This normally is the uppercase Active Directory domain name. If you don't have DNS setup it will also ask two more questions:
  • The kerberos servers
  • The kerberos admin servers

These are the Active Directory Domain Controllers (although Samba 4 doesn't provide the kadmin interface right now). You probably need to add these to your hosts file as well.

If you actually want to check if it's working, you should probably install krb5-user as well and try to do a kinit to acquire a Kerberos ticket, but if you've done a few servers you'll probably believe me when I tell you you don't need krb5-user for Kerberos support.

Joining the domain


Now it's time to join the Linux machine to the domain (since Kerberos is working). We start by installing winbind:
# apt-get install winbind
# /etc/init.d/winbind stop

We don't need an active winbind instance around, so let's stop it right away. If smbd or nmbd are running stop those as well.

Now continue by editing /etc/samba/smb.conf to contain all of the required configuration for Active Directory support:
[global]
netbios name = yourhostname
server string = your host description

realm = YOUR.REALM
workgroup = YOURWORKGROUP
security = ADS
local master = no
preferred master = no
dns proxy = no

# set password server if you don't have functional DNS
#password server = dc.domain.tld

encrypt passwords = true
# setting kerberos method = system keytab prevents pam_winbind from
# authenticating users for me, but the following does work
kerberos method = secrets and keytab

# Using winbind default domain = yes makes usernames work without domain part
winbind use default domain = yes
winbind enum groups = yes
winbind enum users = yes
# winbind nss info = rfc2307 makes winbind use posix attributes from AD
winbind nss info = rfc2307

# map untrusted to domain = yes allows any user to be mapped to the domain user
# with the same username, but also prevents local samba accounts from being used
map untrusted to domain = no

# template homedir can be used to designate the location of users' home
# directories
template homedir = /home/%U
# template shell defines the default shell for when none is set in the posix
# loginShell attribute for a user. Setting this to /bin/false allows login only
# for those users that have this attribute set. pam_winbind also has an option
# to limit access to several groups only, which is actually a real security
# measure unlike this attribute which might be changed by users
template shell = /bin/false

# The first two idmap lines are for the domain, the other two for local samba
# accounts. Using the rid backend maps the ids to the end of the user's SID,
# which makes consistent id mapping across servers possible.
idmap config yourworkgroup : backend = rid
idmap config yourworkgroup : range = 10000 - 49999
idmap uid = 50000 - 100000
idmap gid = 50000 - 100000
Replace all the fields in bold with values applicable to your domain.

Now it's time to join the domain:
# net join -UAdministrator
Enter Administrator's password:
Using short domain name -- YOURDOM
Joined 'YOURHOST' to realm 'your.domain'
[2012/02/10 21:15:35, 0] libads/kerberos.c:333(ads_kinit_password)
kerberos_kinit_password YOURHOST$@YOUR.REALM failed: Client not found in Kerberos database
DNS update failed!
# /etc/init.d/winbind start
* Starting the Winbind daemon winbind [ OK ]
#

If DNS is not properly set up, use net join -UAdministrator -Sdc.yourdom, this tells net what server it should use for the join.

As far as I know these errors are nothing to be concerned about, but the DNS update failed means that net/Samba wasn't able to register the host in DNS. If you have DDNS updates from a DHCP server or there's already a static entry for the server in DNS then you don't need to worry at all. Now try wbinfo -u and see if the Active Directory users show up.

Setting up nss


Setting up nss is another easy step, we just need to add two references to winbind, for both passwd and group. Edit /etc/nsswitch.conf and change the passwd and group lines:
...
passwd: compat winbind
group: compat winbind
...

Verify with getent passwd that all the domain users are listed and their home directories make sense. Now would be a good time to change the loginShell attribute for your user, because as you can see it now is /bin/false for all users.

Setting up PAM


Now that the users actually 'exist' on the machine, let's enable authentication for them as well (if your package manager hasn't already done that for you):
# pam-auth-update
...
Some PAM module packages provide profiles that can be used to
automatically adjust the behavior of all PAM-using applications on the
system. Please indicate which of these behaviors you wish to enable.

PAM profiles to enable:

[*] Unix authentication
[*] Winbind NT/Active Directory authentication
...


Now let's logon to the server from another computer:
$ ssh user@yourhost
user@yourhost's password:
...
Could not chdir to home directory /home/user: No such file or directory
user@yourhost:/$

That's not good is it? Well, it is, but let's make it better, but first...

It doesn't work!


Oh well, bad things can happen. It should work, it works for me on multiple machines, both freshly installed and some older installations, both latest and long-term Ubuntu releases and different Debian releases. But it doesn't work for you... There's a few places you can check right now, one is /var/log/auth.log. However, this might not be the most useful log file in case of authentication failures against Active Directory. A good help though is to start winbind in debug mode:
# winbindd -d 3 -i

This will list a lot of debug information. Look at the messages that occur during a login attempt, it helped me to discover that I needed to use kerberos method = secrets and keytab in smb.conf. It wasn't saying so directly, and don't expect it to tell you the solution to all your problems, but the error messages can be informative...

Finishing touches


Now to continue where we left off, apparently we don't have a home directory on the server yet. This makes sense, and there's a proper solution. We just need to tell pam to use a module that will make a home directory for a user logging in. Let's do so by adding one line to the end of /etc/pam.d/common-account:
session required pam_mkhomedir.so umask=0077 skel=/etc/skel
You can change the umask, but 0077 means that the directory is owned by the user and that group and other have no permissions at all. Now if we login we end up in our newly created home directory.

Next up is sudo. There's a possibility you want to grant sudo rights to someone in your domain, for instance to the Domain Admins group. Of course this is not any different from granting permissions to a local group, I'm detailing it here for a more complete solution. Edit /etc/sudoers in your favorite editor and add the following line:
%domain\ admins ALL=(ALL) ALL

The backslash is just used to escape the space in the group name, otherwise this is no different than any other sudoers entry.

We've come a long way from where we started, but there's still room for improvement. We enabled login using Active Directory credentials, but what if we already logged in somewhere else? In Windows SSO (Single SignOn) works out of the box, but let's add it to our Linux machine(s) as well. What we need for SSO is Kerberos, and since we just set that up we can use it for other services as well. For now I'll only discuss on setting this up for OpenSSH. In /etc/ssh/sshd_config there are two commented lines that we need to change and uncomment so they look like this:
...
GSSAPIAuthentication yes
GSSAPICleanupCredentials yes
...

Don't be fooled by the Kerberos lines, they're not needed for Single SignOn. Now restart SSH:
# /etc/init.d/ssh restart
Rather than invoking init scripts through /etc/init.d, use the service(8)
utility, e.g. service ssh restart

Since the script you are attempting to invoke has been converted to an
Upstart job, you may also use the restart(8) utility, e.g. restart ssh
ssh start/running, process 32441

Now back to the other computer to do a ssh login and see if you can log in without having to supply a password. If it doesn't work, try the following command:
$ ssh -vvv -o PreferredAuthentications=gssapi-with-mic user@yourhost

This will show a lot of debug messages, probably with a descriptive error message near the end. One thing to keep in mind is that the client needs to know the Kerberos principal for the host it's connecting to. This is because with Kerberos, the client is also verifying that the server is actually (according to Kerberos) who it's trying to connect to. The way ssh determines the principal is by using the HostKeyAlias, which defaults to the host you're connecting to. However, it's easy to cheat if there's no working dns by supplying -o HostKeyAlias=yourhost on the ssh commandline.

We can make this even better than it is right now. You might have noticed that if you're logging in using password authentication that you actually get a Kerberos ticket, pam_winbind makes sure this happens. But now that we log in using Kerberos authentication, we don't get a ticket. Seems strange, but it's not. Ssh has decided to turn credential delegation off by default, but we can turn it on again. To do this on a per-user basis you can edit ~/.ssh/config and add the following line:
GSSAPIDelegateCredentials yes
Now if you logon to the machine using Kerberos your ticket is delegated and you can use it to ssh to other computers as well.

Final notes


You should now have a quite-well-integrated Linux machine. In future parts I will discuss mail routing and authentication and proxy server authentication and authorization. This post might be expanded to include some topics that were missing at first, I will try to keep an update list in here as well.

Wednesday, October 12, 2011

Enabling higher resolutions on Matrox G200eW

Recently we bought 5 DELL PowerEdge T110 servers to deploy to customers. After installing Windows XP on the PERC S100 RAID (more on that in a future post) I had to look for a driver for the graphics card. Of course you can't easily find it at Matrox's site, so I went over to DELL support and downloaded the Windows Server 2003 Matrox driver. Server 2003 and XP both being NT5 this worked like a charm, as was to be expected. There is another issue however, by default the Matrox driver supports 4:3 resolutions up to 1280x1024, but we use widescreen monitors which can do 1920x1080, and we're relying on that.

Just a week ago I was fiddling with Matrox drivers for a G450, where I had the same issue with resolutions, where the latest driver did support the correct 16:9 resolutions. When I was comparing the drivers, I noticed there's a resolution reference directly in the driver inf file. For the G200eW, this listed just a few resolutions, but for the G450 there was a long list. Changing this value to what the G450 had listed was enough to get it working, so now our G200eW can do 1920x1080 without issues. Here's the changed value for future reference:
HKR,,Mga.SingleResolutions,0x00000001,\
40,01,C8,00,40,01,F0,00,00,02,80,01,80,02,90,01,\ ; 320x 200, 320x 240, 512x 384, 640x 400
80,02,E0,01,20,03,58,02,50,03,E0,01,58,03,E0,01,\ ; 640x 480, 800x 600, 848x 480, 856x 480
60,03,E0,01,C0,03,60,09,00,04,00,02,00,04,00,03,\ ; 864x 480, 960x2400, 1024x 512, 1024x 768
00,04,00,05,00,04,00,06,30,04,58,02,80,04,60,03,\ ;1024x1280, 1024x1536, 1072x 600, 1152x 864
B0,04,40,06,00,05,D0,02,00,05,00,03,00,05,20,03,\ ;1200x1600, 1280x 720, 1280x 768, 1280x 800
00,05,C0,03,00,05,00,04,00,05,40,06,50,05,00,03,\ ;1280x 960, 1280x1024, 1280x1600, 1360x 768
58,05,00,03,60,05,00,03,78,05,1A,04,A0,05,84,03,\ ;1368x 768, 1376x 768, 1400x1050, 1440x 900
40,06,00,04,40,06,B0,04,40,06,00,05,90,06,1A,04,\ ;1600x1024, 1600x1200, 1600x1280, 1680x1050
00,07,40,05,08,07,A0,05,40,07,70,05,80,07,0A,04,\ ;1792x1344, 1800x1440, 1856x1392, 1920x1034
80,07,38,04,80,07,B0,04,80,07,A0,05,00,08,00,06 ;1920x1080, 1920x1200, 1920x1440, 2048x1536

Wednesday, July 27, 2011

DELL Vostro 3550 stacking issue

At work I often order a few laptops at the same time. Because of this it often occurs I install one of the laptops, then put another one on top to install that one. Now I had a Vostro 3550 on my desk and I put another one on top of it. When I turned it on the screen stayed black, or at least so it seemed. After a while I noticed there was a faint graphic showing, so my guess was the backlight was broken. I pushed the power button, pressed F2 to enter BIOS hoping that would help, then when I turned the laptop to the light to see if there was something on the screen it turned on. I put the laptop down again, it turned off. Lift the front up half a centimeter, screen turns on.

So I was thinking, must be a bad connection, right? Well I had another 3550 still in the box, so I removed the top 3550, put it aside, put the other one on there, turned it on, same issue! This was too much coincidence for me and I quickly noticed that the 3550 doesn't have any buttons to detect whether the lid is closed, so it uses magnets to do this. Well of course if you stack two laptops on top there's always a lid nearby, I didn't expect it to be this sensitive though...

Monday, May 30, 2011

Moving "Documents and Settings" to another partition in Windows XP

Because you can't depend on Windows, it's nice to have some kind of backup scheme for when things go wrong. One of those solutions is to store important data on a seperate drive. I've seen a lot of people doing this the wrong way. User folder in C:\Documents and Settings\[user] and a partition D: or E: which then contains folders like Documents, Downloads, Photos and Music.

A home directory is not just a home directory for nothing, so store your files in there. The solution is simple, with NTFS drivers you can have a volume mount point, which allows you to use a seperate NTFS filesystem as if it was just a folder in another NTFS filesystem. Of course this doesn't make it easy yet, so these are the steps that need to be taken to have it fully functional:
  1. Format the new partition as NTFS
  2. In Disk Management in Windows setup the new filesystem as volume mount point on C:\newdoc
  3. Boot to something that is capable of moving stuff around on your drive (Parted Magic will do)
  4. Copy the contents of Documents and Settings to the new filesystem
  5. Move Documents and Settings to olddoc
  6. Move newdoc to Documents and Settings
  7. Reboot into Windows

Depending on what you used to copy the contents of Documents and Settings you might have to reset some of the file attributes (or permissions even), because otherwise a lot of Desktop.ini files will pop up.

One last improvement that can be made is to fix the icon for the mount point. By default this will show as a disk icon, but because we abstracted this fact we might also want to show it as a folder. Just create C:\Documents and Settings\autorun.inf with the following contents:
[autorun]
icon=%SystemRoot%\system32\SHELL32.dll,3

This requires a reboot before visible, but after that will work great.

Because we make effective use of NTFS volume mount points all legacy applications that probe for C:\Documents and Settings instead of using the proper functions to find profile directories will work as ever before. Just keep in mind to follow these steps after a Windows reinstall, except for the file copy part!

Wednesday, May 11, 2011

Linksys E4200 as an access point

At work we bought two Linksys E4200's to extend our wireless network. We wanted to use them as access points / wireless gateways instead of their normal router configuration. Googling turns up a few half-documented solutions, which might even work in case you've got a small home network set up, but I still couldn't get it to work. So I took one of the routers home, and this is what I've come up with (tested at home only right now):
  1. Start the router
  2. Connect a cable between your computer and one of the E4200 LAN ports
  3. Turn on remote management on the E4200
  4. Verify that the E4200 doesn't have a local address that belongs in your network's subnet (change it otherwise)
  5. Connect a cable between the E4200 WAN port and your network
  6. Connect a cable between your computer and network
  7. Turn off the DHCP server on the E4200
  8. Connect a cable between your network and one of the E4200 LAN ports
  9. Connect a cable between the E4200 WAN port and one of the E4200 LAN ports

Now you can wirelessly connect to your network using the E4200 and you can still access the E4200 admin interface as well!

Of course this all won't be necessary when DD-WRT or other alternative firmware releases are available for the E4200, but right now this probably is the best solution.

Thursday, April 28, 2011

touchmoused: Logitech Touch Mouse server for Linux

Recently I was looking at a way to control the Mac Mini I have connected to my TV. I don't have a keyboard or mouse connected (only a gamepad), but I do have an iPod Touch. Soon I found Logitech Touch Mouse, a simple app providing a keyboard and mouse over the network. Of course Logitech isn't capable of delivering a Linux server for it's app, so I decided to write it myself.

After a quick Wireshark dump I started hacking away. Using the recently released Shairport as a reference I started hacking away on my first Perl program. This also being my first program where I had no documentation on protocol whatsoever, it took me a while to figure out I had to listen both on TCP and UDP. Then it also took me a while before I figured Perl doesn't write directly on a print statement unless autoflush is set on the file descriptor. I managed to find that one on a page detailing serial port communication with Perl.

When these hurdles were overcome I could really start interpreting events, sending them through to the Linux UInput facility. Today another big issue was fixed, mouse movement was broken until I added left mouse button support. So anyone trying to send mouse movements using uinput, be sure to enable left mouse button events!

Anyway, I've now come to a point where the Touch Mouse app can be effectively used as a trackpad replacement. Moving, clicking, (two-finger) scrolling, it all works. Also alphanumeric keys are working, Ctrl and Alt are working and some character keys are working. This also means I think I've come far enough to promote the app here on my blog, so anyone willing to try it out should move on to my github project page.