Resend - with PINE

sunny at sunny at
Fri Nov 23 12:11:05 GMT 2001

Hello Jeremy,
Thanks for your prompt answer.

Asynchronous open will not ensure the file was really opened successfully.
This might be a problem when open() is used to verify a file exists.

Why is the traversal needed on every new process - can't it be moved
before Samba starts processing requests (i.e. before any fork() takes

PS: I hope this finally goes out as ASCII.

-----Original Message-----
From: Jeremy Allison [mailto:jra at]
Sent: Friday, November 23, 2001 13:27
To: Sunny Marueli
Cc: samba-technical at
Subject: Re: Samba seems to behave serially with regard to "open"
operations (resend - ASCII)

On Fri, Nov 23, 2001 at 01:24:13PM +0200, Sunny Marueli wrote:

"some html which doesn't open under mutt".

Please don't send html mail to a list. Please use ascii.

In answer to your other question, the traversal is neccessary
to ensure robustness under smbd abnormal termination (so no
"dead" records are left in the lock database).

I would look into ways of making your network open processing



-----Original Message-----
From: Sunny Marueli
Sent: Friday, November 23, 2001 13:24
To: samba-technical at
Subject: Samba seems to behave serially with regard to "open" operations
(resend - ASCII)

I am currently writing a file system that needs to perform some network
operations during the processing of the open() system call. When I run
samba and share that file system, I have found out that while one user
opens a file, no other can connect to the samba server.

Browsing the Samba code, I have found the following: 
1) Samba fulfills open requests by calling reply_open, which eventually
results locking the file in an internal lock DB maintained by the tdb
module. (reply_open==>open_file_shared==>lock_share_entry(dev,
inode)==>tdb_chainlock(dev, inode))

2) When new clients connect to smbd, it supplies them with a fresh new
copy of smbd by forking. 
3) After the fork() takes place, samba performs all sorts of
initialization code for the newly born process, one of which is the
locking_init(1) (actually this is the first thing samba does after forking
- see server.c:main()).

4) The locking_init function traverses the whole lock DB (as the remark in
the code says - to "delete any dead locks"), and in doing so it apparently
grabs some kind of an index lock (this must be a "chainlock"). If the open
operation is long enough, the new forked process gets eventually to the
lock that was already taken at stage 2 above, and blocks.

Attached: the stack from a blocked forked process. 
#0  0x40136f43 in __libc_fcntl (fd=15, cmd=7) 
    at ../sysdeps/unix/sysv/linux/i386/fcntl.c:122 
#1  0x810d9b0 in tdb_brlock () 
#2  0x810da96 in tdb_lock () 
#3  0x810eeae in tdb_next_lock () 
#4  0x810f0eb in tdb_traverse () 
#5  0x80e97e3 in locking_init () 
#6  0x804c0ae in main () 
#7  0x40081b65 in __libc_start_main (main=0x804bb0c <main>, argc=2, 
    ubp_av=0xbffff7f4, init=0x804a1a8 <_init>, fini=0x811c45c <_fini>, 
    rtld_fini=0x4000df24 <_dl_fini>, stack_end=0xbffff7ec) 
    at ../sysdeps/generic/libc-start.c:111 
I don't understand the reason for this traversal. Not being so familiar
with the samba code and it's history, I wonder if this is a real design
flaw (or a mis-consideration of the fact that an open() can be slow), or
can it be fixed easily.

Can you advise ? 
Sunny Marueli 
System Architect, DiskSites 

More information about the samba-technical mailing list