I recently wrote an article for Bluecoat describing how to limit Skype access based on usernames and passwords. The article is available here.
This got me wondering if I can achieve the same functionality that the Bluecoat ProxySG offers but using open source programs. In short…. yes we can with a little tinkering. For those of you not interested in reading through the draft for BlueCoat, here is a summary of requirements that this article attempts to achieve:
Skype is allowed to be installed on the desktops, but Skype connectivity should be allowed/denied based on username and password, not on source IP or destination IP. ideally, the usernames and passwords are centrally managed through Active Directory.
The above problem was tackled with BlueCoat by using SOCKS authentication. The Bluecoat proxy then uses it’s BCAAA agent to verify the provided username and password with Active Directory.
After some research, it turn out you can achieve the above method by using DANTE socks server. The site for Dante is here:
I wont go through the caveats and security implications of this method, for that, see the BlueCoat document above. I will go into the technical details of setting up a DANTE socks server and using LDAP to verify usernames/passwords against an AD domain controller.
For my particular setup, I’ve used an Ubuntu machine which already has SQUID installed on it. DANTE and SQUID run happily side by side. Ubuntu has DANTE as a package in Synaptic so installing it is a simple matter of applying the package. When configuring DANTE, the following three sites from their documentation really helped to clarify what needed to be done:
http://www.inet.no/dante/config/server.html
http://www.inet.no/dante/config/auth.html
http://www.inet.no/dante/doc/faq.html
Let me highlight step by step what needed to be done in my case:
1. Install the DANTE server and pre-requisites for LDAP PAM authentication:
sudo apt-get install danted libpam-ldap libnss-ldap
2. These should install successfully and you should now be able to modify the DANTE configuration file located at /etc/danted.conf. This was my (basic) configuration. I’ve commented in some explanations to the statements:
#enable logging to a particular file (/var/log/dante.log)
logoutput: stdout /var/log/dante.log
#instruct the server which IPs and ports to listen on. In my case, the server has only a single #interface, so both IPs are the same. Note the standard SOCKS port of 1080
internal: 10.91.25.3 port = 1080
external: 10.91.25.3# (this was part of the automatically generated default configuration) when doing something that # can require privilege, it will use the userid:
user.privileged: proxy# (this was part of the automatically generated default configuration) when running as usual, it # will use the unprivileged userid of:
user.notprivileged: nobody# (this was part of the automatically generated default configuration)
# If you compiled with libwrap support, what userid should it use
# when executing your libwrap commands? “libwrap”.
user.libwrap: nobody# the following instructs the SOCKS server which authentication method to support. In my case, # since DANTE is going to pass the credentials on to PAM which in turn hands over to LDAP, I # specified “pam” and “none”. (see note on point 3 below)
clientmethod: pam none
method: username pam none# these rules define who is allowed to use the SOCKS server. These rules get applied before any # SOCKS data is passed so PAM authentication is not applied here (only can only authenticate # using IP information at this stage)
client pass {
from: 0.0.0.0/0 to: 0.0.0.0/0
log: error connect disconnect
}# these rules define what the SOCKS clients can reach. This is where we enforce PAM # authentication using the method keyword, so only authenticated users can connect to the # outside world
pass {
from: 0.0.0.0/0 to: 0.0.0.0/0
command: bind connect udpassociate bindreply udpreply
method: pam
log: error connect disconnect iooperation
}
3. A quick note on the above configuration file. I found that the SOCKS server would reset the skype conenction if I used
clientmethod: pam
method: username pam
Right after Skype provides it’s supported methods of authentication, SOCKS reset the connection. It seems that Skype provides two methods of authentication: none and username/password. It seems that the SOCKS server needs to be configured to support both these methods also. Using
clientmethod: pam none
method: username pam none
resolved this issue for me
Also, note that in a production environment the access rules should be very much more restricted. Keep in mind that as I outlined in the bluecoat document, the username and password are still sent as cleartext so you need very restrictive access rules in case those credentials are compromised.
4. As per the DANTE FAQ, we next modify the PAM file for the socks server to instruct it to use LDAP for authentication. The file to be created is /etc/pam.d/socksd:
# cat /etc/pam.d/socksd
#%PAM-1.0
auth required /lib/security/pam_ldap.so
account required /lib/security/pam_ldap.so
password required /lib/security/pam_ldap.so
Note I deviated from the proposed file in the FAQ. The FAQ proposition checked first the LDAP server, then if that failed, checked the local password file. In my case, I want to restrict logins to only AD users, so in the above file I force PAM to use LDAP only
5. Still following the FAQ, we next move on to modify the file /etc/ldap.conf. This file controls the LDAP client, which the PAM subsytem uses to check the credentials supplied to it. In Ubuntu, the file is already pre-populated with information generated when installing the packages in step 1, but after uncommenting some lines you should end up with something similar to the fillowing:
/etc/ldap.conf
host 10.91.25.2
base dc=davidv,dc=local
ldap_version 3
binddn cn=Administrator,cn=Users,dc=davidv,dc=local
bindpw password02!
#rootbinddn cn=Administrator,cn=Users,dc=davidv,dc=local
pam_filter objectclass=user
pam_login_attribute cn
A couple of points:
- The auto-generated file uses and LDAP URI to define which host to connect to. This didnt work for me and I had to change to the host 10.91.25.2 statement
- The file proposed by the FAQ uses the “rootbinddn” statement, which I commented out above since the LDAP client is nornally nut run under root privileges and so I stuck to the “binddn” statement
That was really all there is to it. Of course you need to instruct users on setting up Skype to use your new SOCKS server – see the bluecoat document for info on how to do this.
Verification and Troubleshooting Tips
I found two files to be of great help during verification and troubleshooting:
/var/log/dante.log : the SOCKS server log that I specified in the configuration file
/var/log/auth.log : the PAM logs – this is where you’ll see authentication issues
Some examples of the logs:
- Non-working dante.log (the problem here was authentcation – wrong credentials)
minty davvas # tail /var/log/dante.log
Mar 15 07:57:44 (1300175864) danted[20026]: block(0): tcp/connect [: pam%Administr@10.91.25.1.3769 -> 78.141.181.38.21219: pam_authenticate(): Authentication failure
Mar 15 07:57:44 (1300175864) danted[20024]: block(0): tcp/connect [: pam%Administr@10.91.25.1.3767 -> 78.141.181.26.33033: pam_authenticate(): Authentication failure
- Working dante.log
minty davvas # tail /var/log/dante.log
Mar 15 07:54:01 (1300175641) danted[20027]: pass(1): tcp/connect ]: 39 -> pam%Administrator@10.91.25.1.3642 -> 42, 42 -> pam%Administrator@10.91.25.3.1080 -> 39: remote closed
Mar 15 07:54:01 (1300175641) danted[20027]: pass(1): tcp/connect ]: 39 -> pam%Administrator@10.91.25.1.3642 -> 42, 42 -> 93.156.120.52.21516 -> 39: remote closed
Mar 15 07:54:02 (1300175642) danted[20027]: pass(1): tcp/connect -: 78.141.181.31.21219 -> pam%Administrator@10.91.25.1.3644 (0)
Mar 15 07:54:02 (1300175642) danted[20027]: pass(1): tcp/connect ]: 32 -> pam%Administrator@10.91.25.1.3644 -> 53, 53 -> pam%Administrator@10.91.25.3.1080 -> 32: remote closed
Mar 15 07:54:02 (1300175642) danted[20027]: pass(1): tcp/connect ]: 32 -> pam%Administrator@10.91.25.1.3644 -> 53, 53 -> 78.141.181.31.21219 -> 32: remote closed
Mar 15 07:54:06 (1300175646) danted[20027]: pass(1): tcp/connect -: pam%Administrator@10.91.25.1.3629 -> 78.141.181.21.21219 (163)
Mar 15 07:54:06 (1300175646) danted[20027]: pass(1): tcp/connect -: 78.141.181.21.21219 -> pam%Administrator@10.91.25.1.3629 (4)
Mar 15 07:54:07 (1300175647) danted[20027]: pass(1): tcp/connect -: pam%Administrator@10.91.25.1.3629 -> 78.141.181.21.21219 (0)
Mar 15 07:54:07 (1300175647) danted[20027]: pass(1): tcp/connect ]: 13352 -> pam%Administrator@10.91.25.1.3629 -> 20681, 20681 -> pam%Administrator@10.91.25.3.1080 -> 13352: client closed
Mar 15 07:54:07 (1300175647) danted[20027]: pass(1): tcp/connect ]: 13352 -> pam%Administrator@10.91.25.1.3629 -> 20681, 20681 -> 78.141.181.21.21219 -> 13352: client closed
- Non working auth.log file (bad credentials)
Mar 15 07:57:39 minty danted: pam_unix(sockd:auth): check pass; user unknown
Mar 15 07:57:39 minty danted: pam_unix(sockd:auth): authentication failure; logname= uid=0 euid=13 tty= ruser= rhost=10.91.25.1
As always, wireshark is a great help. You can see the Skype authentication to SOCKS (note the cleartext credentials!):
And you can also see the SOCKS server verifying the credentials with LDAP:
Note that by default the LDAP client uses simple authentication, which sends the password out in cleartext… if this is a security issue consider securing LDAP using SSL/TLS
Some useful links for linux / microsoft LDAPS:
http://www.openldap.org/doc/admin24/tls.html