Java Core | Modern Java Concurrency | Martijn Verburg & Ben Evans


Published on

Published in: Technology, News & Politics
1 Comment
No Downloads
Total views
On SlideShare
From Embeds
Number of Embeds
Embeds 0
No embeds

No notes for slide
  • * Hands up for Java 6, 5, 4.... * Hands up for j.u.c
  • Hands up if you’re daunted by the refactoring that would be required
  • The practice of managing your threads (or Otters!) is governed by four forces (after Doug Lea)
  • It’s a little-known fact that Otters are scared of log-linear graphs
  • Very successful within own frame of reference, but caveats Reference Mechanical sympathy again here
  • * So you can contort more and more, but you’re chasing diminishing returns * Ultimately, that exponent gap between clock speed and memory will do for you
  • * Raise your hand if you use the process monitor on Ubuntu or another Linux. OK, have you seen how Java processes behave under that?
  • * Explain that we’re going to show replacements for using synchronized * Raise your hand if you know why we use the keyword “synchronized” to denote a critical section in Java
  • How performant do we think FS objects are? Immutability is good, but watch the copy-cost
  • happens-before defines a “partial order” (if you’re a mathematician) JMM is even worse than the generics constraints part of the spec!
  • * Hands up if you know what a NUMA architecture is? * In some ways, this is actually easier to explain on a NUMA arch...
  • Lock basically replaces synchronized, but is more flexible MONITORENTER & MONITOREXIT
  • Condition takes the place of wait() / notify() (Object monitors) Talk to the cases - 1 putter, 1 taker, many putters, few takers, few putters, many takers - think about this stuff at the design stage
  • Basically it’s a drop-in replacement for regular HashMap “ What’s the worst thing that can happen if you’re iterating over the keys of a regular HashMap and someone alters it underneath you?”
  • Not quite a drop-in replacement - Performance needs to be thought about Talk about Iterators
  • BlockingQueue offers several different ways to interact with it (see the Javadoc)
  • offer is similar to add but doesn’t throw exceptions Producers adding trade orders for example
  • Let’s step through a quasi-realistic example
  • As well as RecursiveAction there’s the more general ForkJoinTask
  • Multithreaded Quicksort - shows a speedup from O(nlog n) to O(n) - not quite linear, but not bad
  • So this is pretty much a statement of the state-of-the-art in Java concurrency
  • * Thread is the assembly language of concurrency * We need to move to a more managed model
  • Coroutines, etc
  • Java Core | Modern Java Concurrency | Martijn Verburg & Ben Evans

    1. 1. Modern Java Concurrency <ul><li>Ben Evans and Martijn Verburg </li></ul><ul><li>(@kittylyst @karianna) </li></ul><ul><li> </li></ul><ul><li>Creative Commons - Attribution-NonCommercial-NoDerivs 3.0 </li></ul>Slide Design by
    2. 2. No, we’re not in sales! <ul><li>Directors of TeamSparq </li></ul><ul><ul><li>“Optimisation for Technical Teams” </li></ul></ul><ul><li>Ben is known for his performance and concurrency work </li></ul><ul><li>Martijn is “the Diabolical Developer” - @diabolicaldev </li></ul><ul><li>Authors of “The Well-Grounded Java Developer” </li></ul><ul><li>Co-Leaders of the LJC (London’s Java User Group) </li></ul><ul><ul><li>Hold a seat on the JCP SE/EE Executive Committee </li></ul></ul><ul><li>Regular conference speakers (JavaOne, Devoxx, OSCON, etc) </li></ul>
    3. 3. Who are these two anyway?
    4. 4. About this talk <ul><li>We only have 1 hour to talk today </li></ul><ul><li>Huge amount to talk about </li></ul><ul><li>This subject fills 2 (or even 4) days worth of training </li></ul><ul><li>We will give you some highlights today </li></ul>
    5. 5. Modern Java concurrency <ul><li>Not a new subject </li></ul><ul><ul><li>Underwent a revolution with Java 5 </li></ul></ul><ul><li>More refinements since </li></ul><ul><ul><li>Still more coming in 7 </li></ul></ul><ul><li>java.util.concurrent (j.u.c) really fast in 6 </li></ul><ul><ul><li>Better yet in 7 </li></ul></ul><ul><li>However, still under-appreciated by a surprising number </li></ul><ul><li>Too much Java 4-style concurrency code still in PROD </li></ul><ul><ul><li>Why...? </li></ul></ul>
    6. 6. Java concurrency - Why not upgrade? <ul><li>Too much legacy code? </li></ul><ul><ul><li>People scared to refactor? </li></ul></ul><ul><li>People don’t know j.u.c is easier than “classic” Java concurrency? </li></ul><ul><li>People don’t know j.u.c is faster than classic? </li></ul><ul><li>People don’t know that you can mix-and-match (with a bit of care)? </li></ul><ul><li>Still not being taught at Universities? </li></ul><ul><li>Not enough people reading Doug Lea or Brian Goetz? </li></ul>
    7. 7. Modern Java concurrency <ul><li>Perhaps: Previous treatments haven’t involved enough otters. </li></ul><ul><li>We will rectify this. </li></ul><ul><li>If you suffer from lutraphobia, you may want to leave now... </li></ul>
    8. 8. Otterly Amazing Tails of Modern Java Concurrency <ul><li>Srsly. </li></ul><ul><li>Otters! </li></ul>
    9. 9. Why Otters? <ul><li>Otters are a very good metaphor </li></ul><ul><li>for concurrency </li></ul><ul><li>Not just because they look a bit </li></ul><ul><li>like threads (i.e. long and thin) </li></ul><ul><li>Collaborative, Competitive & Sneaky </li></ul><ul><li>Can hare off in opposite directions </li></ul><ul><li>Capable of wreaking havoc </li></ul><ul><li>if not contained </li></ul>
    10. 10. Otter Management <ul><li>Safety </li></ul><ul><ul><li>Does each object stay self-consistent? </li></ul></ul><ul><ul><li>No matter what other operations are happening? </li></ul></ul><ul><li>Liveness </li></ul><ul><ul><li>Does the program eventually progress? </li></ul></ul><ul><ul><li>Are any failures to progress temporary or permanent? </li></ul></ul><ul><li>Performance </li></ul><ul><ul><li>How well does the system take advantage of processing cores? </li></ul></ul><ul><li>Reusability </li></ul><ul><ul><li>How easy is it to reuse the system in other applications? </li></ul></ul>
    11. 11. Some History <ul><li>Until recently, most computers had only one processing core </li></ul><ul><li>Multithreading was simulated on a single core </li></ul><ul><ul><li>Not true concurrency </li></ul></ul><ul><li>Serial approach to algorithms often sufficed </li></ul><ul><li>Interleaved multithreading can mask errors </li></ul><ul><ul><li>Or be more forgiving than true concurrency </li></ul></ul><ul><li>Why and how (and when) did things change? </li></ul>
    12. 12. Moore’s Law <ul><li>“ The number of transistors on an economic-to-produce chip roughly doubles every 2 years” </li></ul><ul><li>Originally stated in 1965 </li></ul><ul><ul><li>Expected to hold for the 10 years to 1975 </li></ul></ul><ul><ul><li>Still going strong </li></ul></ul><ul><li>Named for Gordon Moore (Intel founder) </li></ul><ul><ul><li>About transistor counts </li></ul></ul><ul><ul><li>Not clock speed </li></ul></ul><ul><ul><li>Or overall performance </li></ul></ul>
    13. 13. Transistor Counts
    14. 14. Moore’s Law - Problems <ul><li>Not about overall performance </li></ul><ul><li>Memory latency exponent gap </li></ul><ul><ul><li>Need to keep the processing pipeline full </li></ul></ul><ul><ul><li>Add memory caches of faster SRAM “close” to the CPU </li></ul></ul><ul><ul><ul><li>(L1, L2 etc) </li></ul></ul></ul><ul><li>Code restricted by L1 cache misses rather than CPU speed </li></ul><ul><ul><li>After JIT compilation </li></ul></ul>
    15. 15. Spending the transistor budget More and more complex contortions... ILP, CMT, Branch prediction, etc, etc
    16. 16. Multi-core <ul><li>If we can’t increase clock speed / overall performance </li></ul><ul><ul><li>Have to go multi-core </li></ul></ul><ul><ul><li>Concurrency and performance are tied together </li></ul></ul><ul><li>Real concurrency </li></ul><ul><ul><li>Separate threads executing on different cores at the same moment </li></ul></ul><ul><li>The JVM runtime controls scheduling </li></ul><ul><ul><li>Java thread scheduling does NOT behave like OS scheduling </li></ul></ul><ul><li>Concurrency becomes the performance improver </li></ul>
    17. 17. Classic Concurrency <ul><li>Provides exclusion </li></ul><ul><li>Need locking to make mutation concurrency-safe </li></ul><ul><li>Locking gets complicated </li></ul><ul><li>Can become fragile </li></ul><ul><li>Why synchronized ? </li></ul>
    18. 18. Three approaches to Concurrent Type Safety <ul><li>Fully-synchronized Objects </li></ul><ul><ul><li>Synchronize all methods on all classes </li></ul></ul><ul><li>Immutability </li></ul><ul><ul><li>Useful, but may have high copy-cost </li></ul></ul><ul><ul><li>Requires programmer discipline </li></ul></ul><ul><li>Be Very, Very Careful </li></ul><ul><ul><li>Difficult </li></ul></ul><ul><ul><li>Fragile </li></ul></ul><ul><ul><li>Often the only game in town </li></ul></ul>
    19. 19. The JMM <ul><li>Mathematical description of memory </li></ul><ul><li>Most impenetrable part of the Java language spec </li></ul><ul><li>JMM makes </li></ul><ul><li>minimum guarantees </li></ul><ul><li>Real JVMs (and CPUs) may do more </li></ul><ul><li>Primary concepts </li></ul><ul><li>synchronizes-with </li></ul><ul><li>happens-before </li></ul><ul><li>release-before-acquire </li></ul><ul><li>as-if-serial </li></ul>
    20. 20. Synchronizes-with <ul><li>Threads have their own description of an object’s state </li></ul><ul><ul><li>This must be flushed to main memory and other threads </li></ul></ul><ul><li>synchronized means that this local view has been synchronized-with the other threads </li></ul><ul><li>Defines touch-points where threads must perform synching </li></ul>
    21. 21. java.util.concurrent <ul><li>Thanks, Doug! </li></ul><ul><li>j.u.c has building blocks for </li></ul><ul><li>concurrent code </li></ul><ul><ul><li>ReentrantLock </li></ul></ul><ul><ul><li>Condition </li></ul></ul><ul><ul><li>ConcurrentHashMap </li></ul></ul><ul><ul><li>CopyOnWriteArrayList </li></ul></ul><ul><ul><li>Other Concurrent Data Structures </li></ul></ul>
    22. 22. Locks in j.u.c <ul><li>Lock is an interface </li></ul><ul><li>ReentrantLock is the usual implementation </li></ul>
    23. 23. Conditions in j.u.c
    24. 24. Conditions in j.u.c
    25. 25. ConcurrentHashMap (CHM) <ul><li>HashMap has: </li></ul><ul><ul><li>Hash function </li></ul></ul><ul><ul><li>Even distribution of buckets </li></ul></ul><ul><li>Concurrent form </li></ul><ul><ul><li>Can lock independently </li></ul></ul><ul><ul><li>Seems lock-free to users </li></ul></ul><ul><ul><li>Has atomic operations </li></ul></ul>
    26. 26. CopyOnWriteArrayList (COWAL) <ul><li>Similar idea to CHM </li></ul><ul><ul><li>Makes separate copies of underlying structure </li></ul></ul><ul><li>Iterator will never throw ConcurrentModificationException </li></ul>
    27. 27. CountDownLatch <ul><li>A group consensus construct </li></ul><ul><li>countDown() decrements the count </li></ul><ul><li>await() blocks until count == 0 </li></ul><ul><ul><li>i.e. consensus </li></ul></ul><ul><li>Constructor takes an int param </li></ul><ul><ul><li>The count </li></ul></ul><ul><li>Quite a few use cases </li></ul><ul><ul><li>e.g. Multithreaded testing </li></ul></ul>
    28. 28. Example - CountDownLatch
    29. 29. Handoff Queue (in-mem) <ul><li>Efficient way to hand off work </li></ul><ul><li>between threadpools </li></ul><ul><li>BlockingQueue a good pick </li></ul><ul><li>Has blocking ops with timeouts </li></ul><ul><ul><li>e.g. for backoff / retry </li></ul></ul><ul><li>Two basic implementations </li></ul><ul><ul><li>ArrayList and LinkedList backed </li></ul></ul><ul><li>Java 7 introduces the shiny new TransferQueue </li></ul>
    30. 30. Example - LinkedBlockingQueue <ul><li>Imagine multiple producers and consumers </li></ul>
    31. 31. Executors <ul><li>j.u.c execution constructs </li></ul><ul><ul><li>Callable , Future , </li></ul></ul><ul><ul><li>FutureTask </li></ul></ul><ul><li>In addition to the venerable </li></ul><ul><ul><li>Thread and Runnable </li></ul></ul><ul><li>Stop using TimerTask ! </li></ul><ul><li>Executors class provides factory methods for making threadpools </li></ul><ul><ul><li>ScheduledThreadPoolExecutor is one standard choice </li></ul></ul><ul><li>Final building block for modern concurrent applications with Java </li></ul>
    32. 32. Example - ThreadPoolManager
    33. 33. Example - QueueReaderTask
    34. 34. Fork/Join <ul><li>Java 7 introduces F/J </li></ul><ul><ul><li>similar to MapReduce </li></ul></ul><ul><ul><li>useful for a certain class of problems </li></ul></ul><ul><ul><li>F/J executions are not really threads </li></ul></ul><ul><li>In our example, we </li></ul><ul><li>subclass RecursiveAction </li></ul><ul><li>Need to provide a compute() method </li></ul><ul><ul><li>And a way of merging results </li></ul></ul><ul><li>F/J provides an invokeAll() to hand off more tasks </li></ul>
    35. 35. Fork/Join <ul><li>Typical divide and conquer style problem </li></ul><ul><ul><li>invokeall() performs the threadpool/worker queue magic </li></ul></ul>
    36. 36. Concurrent Java Code <ul><li>Mutable state (objects) protected by locks </li></ul><ul><li>Concurrent data structures </li></ul><ul><ul><li>CHM, COWAL </li></ul></ul><ul><li>Be careful of performance </li></ul><ul><ul><li>especially COWAL </li></ul></ul><ul><li>Synchronous multithreading - explicit synchronization </li></ul><ul><li>Executor -based threadpools </li></ul><ul><li>Asynch multithreading communicates using queue-like handoffs </li></ul>
    37. 37. Stepping Back <ul><li>Concurrency is key to the future of performant code </li></ul><ul><li>Mutable state is hard </li></ul><ul><li>Need both synch & asynch state sharing </li></ul><ul><li>Locks can be hard to use correctly </li></ul><ul><li>JMM is a low-level, flexible model </li></ul><ul><ul><li>Need higher-level concurrency model </li></ul></ul><ul><ul><li>Thread is still too low-level </li></ul></ul>
    38. 38. Imagine a world... <ul><li>The runtime & environment helped out the programmer more </li></ul><ul><ul><li>Runtime-managed concurrency </li></ul></ul><ul><ul><li>Collections were thread-safe by default </li></ul></ul><ul><ul><li>Objects were immutable by default </li></ul></ul><ul><ul><li>State was well encapsulated and not shared by default </li></ul></ul><ul><li>Thread wasn’t the default choice for unit of concurrent execution </li></ul><ul><li>Copy-on-write was the basis for mutation of collections / synchronous multithreading </li></ul><ul><li>Hand-off queues were the basis for asynchronous multithreading </li></ul>
    39. 39. What can we do with Java? <ul><li>We’re stuck with a lot of heritage in Java </li></ul><ul><li>But the JVM and JMM are very sound </li></ul><ul><li>You don’t have to abandon Java </li></ul><ul><ul><li>LMAX’s OSS “Disruptor” framework proves this </li></ul></ul><ul><ul><li>Modern low-latency Java trading systems are screamingly fast </li></ul></ul><ul><ul><li>Mechanical sympathy and clean code get you far </li></ul></ul><ul><ul><li>The JIT compiler just gets better and better </li></ul></ul><ul><li>If we wanted to dream of a new language </li></ul><ul><ul><li>It should be on the JVM </li></ul></ul><ul><ul><li>It should build on what we’ve learned in 15 years of Java </li></ul></ul>
    40. 40. New Frontiers in Concurrency <ul><li>There are several options now on the JVM </li></ul><ul><ul><li>New possibilities built-in to the language syntax </li></ul></ul><ul><ul><li>Synch and asynch models </li></ul></ul><ul><li>Scala offers an Actors model </li></ul><ul><ul><li>And the powerful Akka framework </li></ul></ul><ul><li>Clojure is immutable by default </li></ul><ul><ul><li>Has agents (like actors) & shared-nothing by default </li></ul></ul><ul><ul><li>Also has a Software Transactional Memory (STM) model </li></ul></ul><ul><li>Groovy has GPARs </li></ul>
    41. 41. Acknowledgments <ul><li>All otter images Creative Commons or Fair Use </li></ul><ul><li>Photos owned by Flickr Users </li></ul><ul><ul><li>moff, spark, sodaro, lonecellotheory, tomsowerby </li></ul></ul><ul><ul><li>farnsworth, prince, marcus_jb1973, mliu92, Ed Zitron, </li></ul></ul><ul><ul><li>NaturalLight & monkeywing </li></ul></ul><ul><li>Dancing Otter by the amazing Nicola Slater @ folksy </li></ul><ul><li>Slide design by </li></ul><ul><li>The Disruptor! </li></ul>
    42. 42. Thanks for listening! (@kittylyst, @karianna) <ul><li> </li></ul><ul><li> </li></ul>