aspose file tools*
The moose likes Developer Certification (SCJD/OCMJD) and the fly likes SCJD B&S locking Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Certification » Developer Certification (SCJD/OCMJD)
Bookmark "SCJD B&S locking" Watch "SCJD B&S locking" New topic
Author

SCJD B&S locking

Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
hey Folks,
I have been reading a few threads on B&S Locking & it appears that most have used the await() method i.e it will wait forever as opposed to the await(long time, TimeUnit t) which will timeout, according to my spec it has the following



So sorry if this is a silly question but I know Sun/Oracle are very stringent when it comes to the spec, so basically from reading the above I should use the await() method & hence the thread will wait without taking CPU cycles forever with no timeout, I also know in this case I need to notify these object in case of deletion etc but that is another issue

On another topic has anybody had any experience of SCJD since Oracle bought Sun? do the mark harder or easier etc? I also seen from another thread here that on Aug 2011 Oracle will require mandatory courses for SCJD, I originally signed up to SCJD probs >5 years ago, luckily I decided to do it now with Oracle's latest move, alas if there is one good thing Oracle can do its make money

Thanks again for your time
/Rob
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Rob Symth wrote:I should use the await() method



Rob Symth wrote:do the mark harder or easier etc?

The only thing that changed: in the sunny days you got a score per section (network server, general considerations,...) and a total score on 400 points; in the Oracle days you just get pass or fail score (if you got a fail score, you'll get the per section score). So it's impossible to know if they grade harder or not, because nobody knows if they passed with 320/400 or 400/400.


SCJA, SCJP (1.4 | 5.0 | 6.0), SCJD
http://www.javaroe.be/
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
Thanks again Roel,
You have probably noticed that I am getting into the thick of things as more questions are flowing!

I would like to run 1 design choice made by me in relation to deletion of a locked record, ok, of course there maybe other threads waiting on this record when the lock holder deletes the record, this is fine as i just use signalAll & to check if the record is deleted & if so throw back a RCNF exception to each client who was waiting on the lock condition.
However for simplicity I have implemented that when a record is deleted by the lock owner this deleteReservation method will poll [using lock.hasWaiters(lock.getCondition())] that all waiting threads have awoken & have thrown the RCNF exception back to their clients, this simplifies my coding as once we are assured all waiting thread have awoken we can safely remove the lock entry from the HashMap. Also during this any new subsequent locks on this record will immediately throw a RCNF exception as the lock is marked deleted.

So my main question is do you think its ok for the deleteReservation method to poll for all waiting threads to have awoken & thrown a RCNF exception back to the client? or do you see this extra overhead as inefficient & the method should just return as soon as the lock has been marked deleted? if the latter is the case this introduces some more complexity.
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Is the deleteReservation a method in your Data class? Or is this some kind of business service method? Like the method's name indicates this method should just delete the reservation; nothing more, nothing less. The unlock-method is responsible for releasing a lock. And honestly I don't see how not polling for waiting threads (when a record is deleted) can result in more complexity (but that's maybe because I didn't use lock conditions, just used the simple wait/notifyAll technique). I would think when a record is deleted (and unlocked) all waiting threads will get informed and these threads will see that the record is deleted and a RNFE will be thrown.
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
Hey Roel,
Yes the delete reservation is part of my Data class but is separate from the ContractorFileAccess (DAO) class, sorry my naming is a bit unclear, I should just call it as deleteLock & which you state below should only delete a lock & nothing more.
I guess in the unlock method a check could be made to determine if the lock is deleted via the method above via some switch & then handle the polling logic to ensure all waiting thread have awoken & returned RCNF exception to their clients, do you think this is semantically correct?
The complexity introduced with the polling I do not think is that complicated as we can just add another condition on the lock & call await on it from the deleteRecord & the last record who was awaiting can then signal this waiting thread which in turns remove the recNo & lock object from the HashMap.
But the feeling I get from your last post that this is all a bit contrived, I agree that this is probably the most complicated part of the locking system, sounds like you went for a more simpler approach for when a record is deleted, but does it handle the case for all waiting thread to wake up & return RCNF back to the client & alsoa client who attempts to lock the lock whilst the lock is in the deleted state?

Thanks again for your reply
/Rob
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

That sounds way to complex!

When I remove the locked record in my unlock-method all waiting threads (threads waiting for this record + threads waiting for other records) will be informed and are moved back to the runnable state. So each thread will get some CPU time and will try to lock the record again (if they try to lock a deleted record, a RNFE will be thrown from the lock-record).
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
Yeah I guess it is, I was trying to implement a lock handover situation in the case that only the threads waiting on a specific lock are woke up & not all the threads waiting on all locks, I guess for this performance gain & the added complexity it might be a bit complicated.
As per your solution below with all threads being awoken what comes to mind is to have lock method a recursive function which first obtains the lock if not locked & return otherwise wait on the lock or do you think the recursion adds to the complexity & of course the overhead associated inherently with recursion?

Thanks
/Rob
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Why would you opt for making it recursive, because that's just insane?
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
yeah I can start to see myself making this more complicated than needed, I guess check check on the while loop in which the wait is called to determine if the lock is free or deleted & work with that, I guess simplicity rules in this assignment with the 'junior programmer' reference so having all thread awoken will not result in a score penalty even though its less efficient.
But good exercise none the less which I will state in my design decisions doc.

Thanks again for your help Roel

Also I came across groboutils which I found handy for multi threaded junit test cases, I also heard testNG is also good for this, have you had exposure to either?

Thanks
/Rob
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Rob Symth wrote:Also I came across groboutils which I found handy for multi threaded junit test cases, I also heard testNG is also good for this, have you had exposure to either?

No, I used JUnit
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
Hey Joel in response to your comment below

When I remove the locked record in my unlock-method all waiting threads (threads waiting for this record + threads waiting for other records) will be informed and are moved back to the runnable state. So each thread will get some CPU time and will try to lock the record again (if they try to lock a deleted record, a RNFE will be thrown from the lock-record).


Does this imply the locking mechanism should share some state with the DAO i.e in this case share the list of deleted records?
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Rob Symth wrote:Does this imply the locking mechanism should share some state with the DAO i.e in this case share the list of deleted records?

My Data class contains both file access and the locking mechanism, I didn't use seperate helper classes. But indeed you need to know in the lock-method if the record exists or not.
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
Yeah seems that way!
My thinking however could lead to a race condition, well with my solution anyways, when a record is deleted its record number which is an index into the flat file can be reused for creation of a new record, so lets assume this scenario, a record is locked, its then deleted by the lock owner, its then unlocked, the waiting threads then are awoken, so lets say there are 2 waiting thread, the first one correctly sees that record is deleted & throws RCNF expception, this thread is switched out, a new thread creates a new record (this same recNo get reused) & then attempts to lock this record, the second waiting thread then see's that this record is no longer deleted (buts its a new record with same recNo) so this scenario could be problematic, any thoughts on this?
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Maybe I'm missing something, but I don't see any issue with that scenario.

But first I'll give the understanding of your scenario a shot. Here we go:

t1 locks record 1 --> lock granted
t2 locks record 1 --> has to wait
t3 locks record 1 --> has to wait
t1 deletes record 1 --> rec1 is deleted
t1 unlocks record 1 --> all waiting threads are notified (t2 & t3 are in runnable state now)
t3 locks record 1 --> RNFE is thrown
t4 creates a new record --> recNo 1 is reused for this new record

and if now t4 wants to lock record 1 too, it all depends on which thread will get the cpu time (that's in the hands of the thread scheduler). if t2 gets the cpu-time it will successfully lock record 1 (but it's another thread that it initially wanted to lock) and t4 will have to wait; if t4 again gets cpu time, then it will lock record 1 and t2 still has to wait.

So what's the problem you are referring to? Is it that t2 locks a record which it does not wanted to lock?
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
yup it could be potentially that t2 gets a lock on a different record with the same recNo that it originally attempted to lock, do we leave this up to the end user to resolve? might be a note in the usage instructions?
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

Ah, and that's called a race condition?

In my application I show the CSR who wants to book a room, a dialog containing all room details (all fields disabled) and only the customer id can be entered. So the CSR should notice the change of room

The real solution would be to implement something like a version property which is incremented each time when the record changes (similar to JPA's Version annotation). But I didn't do anything special to get around this issue (and I did re-use deleted entries). The easiest solution would be not to reuse deleted entries and use this problem as explanation why you didn't opt for re-using deleted entries
Rob Symth
Ranch Hand

Joined: Apr 29, 2011
Posts: 32
would you not consider this a race condition?
i.e two different scenarios based on who gets the cpu?
scenario 1 : t2 & t3 manage to get the lock & throw RCNF exception, t4 creates & locks record
scenario 2: t2 gets lock throws RCNF exception, t4 creates & locks record, t4 unlocks record & t3 gets lock on same recNo but different record?

haha just got a warning on my english had to change 'u' to you I guess I am a bit narrow minded that way
Roel De Nijs
Bartender

Joined: Jul 19, 2004
Posts: 5539
    
  13

From [url=http://en.wikipedia.org/wiki/Race_conditionthe wiki page[/url]:
A race condition or race hazard is a flaw in an electronic system or process whereby the output and/or result of the process is unexpectedly and critically dependent on the sequence or timing of other events.

So that's indeed a race condition. One you could easily solve if you want to (remove re-use of deleted entries). I can't remember me mentioning this issue in my decisions document).
 
It is sorta covered in the JavaRanch Style Guide.
 
subject: SCJD B&S locking