SCJD, SCBCD, SCJP
Originally posted by A Mesbah:
...
Lock:
Data class has a Map (implemented as HashMap) of locked contractor
records.
When the lock method is invoked, a check is made to see if the Contractor
already has been locked by another thread (if it can be found in the
locked Map). While it has, the current thread will wait until notified
that it has been unlocked. If not, a Cookie number is generated using the
CookieGenerator class and it is put as the key and the record number is
put as the value in the locking Map. The lock method returns the cookie
number at the end of its operation to the caller.
...
James<br />SCJP 1.4 - 92%<br />SCJD - 93%<br />SCWCD 1.4 - 95%<br />SCBCD 1.3 - 100%<br />SCEA - 92%
Originally posted by A Mesbah:
Lock:
Data class has a Map (implemented as HashMap) of locked contractor
records.
When the lock method is invoked, a check is made to see if the Contractor
already has been locked by another thread (if it can be found in the
locked Map). While it has, the current thread will wait until notified
that it has been unlocked. If not, a Cookie number is generated using the
CookieGenerator class and it is put as the key and the record number is
put as the value in the locking Map. The lock method returns the cookie
number at the end of its operation to the caller.
Originally posted by peter wooster:
Did you really use the cookie as the key to the Map? It should use the record number as the key, since that's what other threads will try to lock.
Did you use notify or notifyAll when unlocking a record? If the wait is on the Map, you need notifyAll, if you wait on a LockedRecord object that contains a queue of waiting threads for that record you could use notify.
Another missing feature in the lock code is preventing sequences such as
client A locks record 1
client B locks record 2
client A tries to lock record 2 but has to wait
client B tries to lock record 1 = deadlock
This can be prevented by restricting clients to a single lock or by requiring that locks be requested by the client in a specified order, such as ascending. There are more complex algorithms that can detect the forth step in the sequence above, but they are probably excessive. To do this requires a queue of waiting clients for each record, if a client wishes to lock an additional record, it must first check that no other client that is waiting on one of its locked records already has the desired record locked.
Another missing feature in the lock code is preventing sequences such as
client A locks record 1
client B locks record 2
client A tries to lock record 2 but has to wait
client B tries to lock record 1 = deadlock
SCJP 1.4<br />SCJD 1.4
Originally posted by Daniel Simpson:
But is that even possible for that to happen when booking a contractor? Then again, I guess one could debate if the network connection is slow, it might take a while to process, but is it possible for a client to try and book two records that fast? I don't think this would be possible in local mode, as locking-booking-unlocking happens in less then a second. Am I wrong in assuming this? Is it necessary to implement the locking above so a client can have only one lock at any time? Or....what if I made my adapter book method synchronized? That would hurt performance as many could be connected but no concurrent bookings or would that be violating or defeating the whole purpose of network mode?
[ January 05, 2005: Message edited by: Daniel Simpson ]
Best Regards <br /> <br />Omar F. Kalaldah<br />---------------------<br />SCJP, SCJD, SCBCD
MCP (C# application dev 70-316) 860<br />SCJP 1.4 100% SCJD (URLyBird) 378<br />MAD 100% nuts
MCP (C# application dev 70-316) 860<br />SCJP 1.4 100% SCJD (URLyBird) 378<br />MAD 100% nuts
Originally posted by peter wooster:
Did you really use the cookie as the key to the Map? It should use the record number as the key, since that's what other threads will try to lock.
Did you use notify or notifyAll when unlocking a record? If the wait is on the Map, you need notifyAll, if you wait on a LockedRecord object that contains a queue of waiting threads for that record you could use notify.
Another missing feature in the lock code is preventing sequences such as
client A locks record 1
client B locks record 2
client A tries to lock record 2 but has to wait
client B tries to lock record 1 = deadlock
This can be prevented by restricting clients to a single lock or by requiring that locks be requested by the client in a specified order, such as ascending. There are more complex algorithms that can detect the forth step in the sequence above, but they are probably excessive. To do this requires a queue of waiting clients for each record, if a client wishes to lock an additional record, it must first check that no other client that is waiting on one of its locked records already has the desired record locked.
Originally posted by peter wooster:
At the very simplest, you should throw an exception if the client tries to lock a record when they already have one locked, note that a lot of simple solutions deadlock if you try to lock a record you already have locked.
SCJP 1.4<br />SCJD 1.4
I have noticed that my program deadlocks if I try to lock a record that I have already locked. I can't, however, figure out how I can check to see if the client is trying to lock a record that they have already locked. Any ideas?
Originally posted by peter wooster:
You can do this in the session object (probably the instance of DBAccess) or in a lock manager. I do it in the lock manager by keeping a map of sessions and their pending and active locks. That way you can enforce one of the following rules:
simplest - a session can only have a single lock request at any time
medium - lock requests must be done in a specified order, eg. ascending, this assumes that the resources implement Comparable.
hard - lock requests may be done in any order, but a sequence that would block is detected by checking if session that already has the desired resource is waiting for a resource that this session has locked.
SCJP 1.4<br />SCJD 1.4
John
Originally posted by Daniel Simpson:
Hey Peter, I'm using sockets in my implementation. What about this idea? What if I used a hashmap that used the record number and the thread's name for the key-value? That way, I can check to see if that thread already is locking a record. Such as it would put into the map- key: 27, value: Thread-1. Then I could do manager.containsValue(Thread.currentThread().getName()) (thus preventing 1)locking multiple records and 2)preventing trying to lock the same record multiple times) what do you think?
--------<br />Andy Zhu<br />scjp 1.4<br />scjd 1.4<br />SAS Certified Programmer 9.0
mooooooo ..... tiny ad ....
We need your help - Coderanch server fundraiser
https://coderanch.com/wiki/782867/Coderanch-server-fundraiser
|