Note: This post was written in 2008. It might or might not still work. I’ve not had time to test. YMMV!
Intro
This is a mini-howto which shows one way to get round an annoying bug in mount.cifs that doesn't look like getting fixed any time soon.
When using smbmount you can have samba do netbios aliasing. Which means that you can have multiple netbios names with different configs on a single samba server. This is a cool thing to do and works nicely if you're using Windows or smbmount. But things are not so nice when you use mount.cifs (which Debian Lenny and Sid and Ubuntu Hoary Hedgehog do). If you have two shares with the same name but different netbios hostnames then, if you try to mount both of them, both mounts will show only the contents of the share first mounted.
Example
This is clearer if we look at an example setup where the bug manifests.
In our global smb.conf we have:
[global]
workgroup = oahusmb
netbios aliases = aa bb
server string = GNU/Linux Samba
------------SNIP-------------
include = /etc/samba/smb.conf.%L
In /etc/samba/smb.conf.aa:
[global]
netbios name = AA
------------SNIP-------------
[home]
volume = home
path = /home/aa
guest ok = yes
writeable = yes
create mask = 777
And in /etc/samba/smb.conf.bb:
[global]
netbios name = BB
------------SNIP-------------
[home]
volume = home
path = /home/bb
guest ok = yes
writeable = yes
create mask = 777
When we try and mount we get:
charlie@client:/home/charlie# mount.cifs //aa/home t1 -o guest,servern=aa
charlie@client:/home/charlie# mount.cifs //bb/home t2 -o guest,servern=bb
charlie@client:/home/charlie# ls t1
admin database .vimrc
charlie@client:/home/charlie# ls t2
admin database .vimrc
charlie@client:/home/charlie#
How to solve it
We'll set up our Samba server with some aliased IPs. These allow our NIC to have more than one IP address. We'll make Samba include our virtual host files based on the IP address on which it receives the request, instead of than by the netbiosname in the request. And we'll make sure that when we look for a given server it will be resolved to the correct IP address (here by using the hosts file, but on a local DNS server if you're that way inclined).
Setting up IP aliasing
Linux lets you create an alias for your NIC provided its on the same subnet. We'll set up two IP aliases for our samba server. This will work for Debian (and probably Ubuntu) boxen - see your distro's networking reference to make it work for you!
Our old /etc/network/interfaces said something like this:
# The loopback network interface
auto lo
iface lo inet loopback
# The primary network interface
iface eth0 inet static
address 192.168.0.202
netmask 255.255.255.0
gateway 192.168.0.253
auto eth0
Let's define two IP aliases for our primary NIC (i.e. eth0). We'll call them eth0:1 and eth0:2 and assign them IP addresses 192.168.0.203 and 192.168.0.204. Make sure nowt else is using those IP addresses or expect trouble!
We insert this in /etc/network/interfaces:
# aa
iface eth0:1 inet static
address 192.168.0.203
netmask 255.255.255.0
auto eth0:1
# bb
iface eth0:2 inet static
address 192.168.0.204
netmask 255.255.255.0
auto eth0:2
Now we bring the aliased IPs up by doing (as root).
charlie:/home/charlie# ifup eth0:1
charlie:/home/charlie# ifup eth0:2
Check that it's worked like this:
charlie:/home/charlie# ifconfig -a
eth0 Link encap:Ethernet HWaddr 00:20:ED:99:9A:8C
inet addr:192.168.0.202 Bcast:192.168.254.255 Mask:255.255.255.0
inet6 addr: fe80::220:edff:fe61:9a8c/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:38378633 errors:398 dropped:2144 overruns:1 frame:0
TX packets:48117343 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:4193786202 (3.9 GiB) TX bytes:2496230628 (2.3 GiB)
Interrupt:185 Base address:0xe400
eth0:1 Link encap:Ethernet HWaddr 00:20:ED:99:9A:8C
inet addr:192.168.0.203 Bcast:192.168.254.255 Mask:255.255.255.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
Interrupt:185 Base address:0xe400
eth0:2 Link encap:Ethernet HWaddr 00:20:ED:99:9A:8C
inet addr:192.168.0.204 Bcast:192.168.254.255 Mask:255.255.255.0
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
Interrupt:185 Base address:0xe400
-----------------------SNIP----------------------
Configure samba to include based on IP
Samba's %i variable lets us include based on the IP address on which the server received a request. Edit /etc/smb.conf adding the line
include = /etc/samba/%i
Now we set up symlinks to our virtual host config files. Like this:
charlie:/home/charlie# cd /etc/samba
charlie:/etc/samba# ln -s 192.168.0.203 smb.conf.aa
charlie:/etc/samba# ln -s 192.168.0.204 smb.conf.bb
Next, we'll edit those files adding an interfaces line. Here's what it looks like in smb.conf.aa:
interfaces = 192.168.0.203
Cool, restart or just reload yer samba config
charlie:/home/charlie# /etc/init.d/samba reload
Configuring the client
We just add a couple of entries to our hosts file and we're ready to rock.
charlie@client:/# echo 192.168.0.203 aa >> /etc/hosts
charlie@client:/# echo 192.168.0.204 bb >> /etc/hosts
And now we can finally do:
charlie@client:/home/charlie# mount.cifs //aa/home t1 -o guest,servern=aa
charlie@client:/home/charlie# mount.cifs //bb/home t2 -o guest,servern=bb
charlie@client:/home/charlie# ls t1
admin database .vimrc
charlie@client:/home/charlie# ls t2
some other .stuff
charlie@client:/home/charlie#
Tip: Keep OpenOffice happy when using CIFS mounts
There's a problem when saving OpenOffice docs to CIFS mounts. OOo says "Error saving the document yourdoc.odt. Error creating object. Could not create backup copy." You can get round this by telling mount.cifs not to send byte range lock requests to the server. Add -o nobrl to the end of your mount.cifs command or put something like the following in /etc/fstab:
//aa/home /mnt/aa_home cifs rw,user,nobrl,noauto,uid=thedude,password=secret 0 2
Tip: Make sure Windows boxes are using WINS
I found that if Windows boxes didn't use WINS to resolve netbios names, they'd pick up the highest virtual IP address from my samba server no matter which netbiosname they were looking for. To turn samba into a WINS server, we can do this in smb.conf:
local master = yes
preferred master = yes
os level = 234
wins support = yes
Now set Windows to use WINS (normally in Networking | TCP/IP | Advanced | WINS) on that machine and enable wins over TCP/IP.