Menu

  • Blog
  • Who the Heck?
  • Gigs & Appearances
  • A Novel in 2010
  • YouTube
  • Mail me

Navigation

  • Create content

User login

  • Create new account
  • Request new password

Friendly Types

  • The Naked Speaker
  • Andy Millar
  • Living to Eat!
  • MemeMe
  • Benjamin Gray
  • Charlie Richardson

Sites I Likes

  • xkcd
  • Boing Boing
  • Bloglines
  • Cute Overload! :)
  • Explosm!
  • I Can Has Cheezburger
  • www.AppGiveaway.com
Home » Blogs » Tom's blog

Dumb Stuff Not to do in Java: Synchronize on a Boolean

Submitted by Tom on Mon, 04/13/2009 - 16:00
  • coding
  • Java

One of the great things about coding is that there're always something new to learn: new techniques, new languages, and possibly most amusing of all, thousands of new ways to screw things up.

As a case in point, the other day, I wrote something a bit like the below:

I put this out for a code review (very useful practice - see The Joel Test), and within a few minutes, a colleague replied with the blunt, but informative "NO! You can't synchronize on a Boolean". Being an inquisitive sort, I enquired as to why, did some reading around, and messed with the code to break it.

Why This is Dumb

The assignment jobRunning = true effectively points jobRunning at a pre-created Boolean object representing a true value. This means that jobRunning is no longer the same object as it is when it is false.

To run this through, let's say a thread, T1 calls doJob() when jobRunning = false, then T2 subsequently calls doJob(). T1 will synchronize on jobRunning when it is false, then sets it to true. When T2 synchronizes on jobRunning, it will be a different object, so it won't be blocked, even when T1 is still in the synchronized block of code - the synchronized statement effectively does nothing for these first two calls, and we could end up with two threads running the main body of doJob() at the same time.

Quick Fix

This isn't a particularly difficult problem to fix, you just synchronize on a different object:


Not the most elegant of solutions, but pretty quick to implement in this case.

This is a fairly subtle consequence of the Java abstraction, and could have caused me a huge headache if it had gone unchecked - leaving one of those wonderfully annoying intermittent bugs floating around (the kind that take forever to track down and debug). So I figured it would be more than worth writing about, in the hope I might save someone else this trouble.

Bottom line: Don't synchronize on Booleans.

Bookmark/Search this post with:
  • Delicious
  • Digg
  • StumbleUpon
  • Reddit
  • Facebook
  • Technorati
»
  • Tom's blog
  • Add new comment

or use locks and semaphores -

Submitted by Anonymous on Wed, 04/15/2009 - 20:50.

or use locks and semaphores - they're a much more elegant solution in java 1.5+. check out java.util.concurrent and java.util.concurrent.locks

-- igor

»
  • reply

Or just use a useful language

Submitted by Anonymous (not verified) on Fri, 04/17/2009 - 10:05.

Or just use a useful language for doing concurrency in, like Erlang, not some brain dead threading model that was badly shoehorned into C 40 years ago and then left to infect other languages as time wore on.

»
  • reply

And really the lock should be

Submitted by Anonymous on Mon, 04/13/2009 - 16:11.

And really the lock should be declared final too. Otherwise you won't be protected against accidentally assigning to it. In fact really, if you're using Eclipse, you should alter the templates so that almost everything is final by default.

»
  • reply

Good call, I've updated the

Submitted by Tom on Mon, 04/13/2009 - 16:19.

Good call, I've updated the second example. Thanks for the comment

»
  • reply

Subscribely Goodness

 Subscribe through FeedBurner

Subscribe in Bloglines Add to Google Reader or Homepage 

Add to Technorati Favorites

My Projecty Things

Twitter Updates

    follow me on Twitter