Java memory model
I. CPU memory model (emphasis: multi-level cache and out-of-order execution optimization)
Cache: as a buffer between memory and processor, to solve the problem of CPU waiting caused by the large difference between the computer’s storage and processing speed. When a program is running, it copies the data needed for an operation from main memory to the CPU’s cache. Then the CPU can read and write data directly from its cache when performing a calculation. When the operation is complete, the data in the cache is refreshed to main memory.
Cache consistency
When computing tasks of multiple cpus all involve the same main memory area, their caches may be inconsistent. If this happens, whose cached data will be used when synchronizing back to main memory?
Cache line: The smallest unit of data stored in the CPU cache. The size is 64 bytes
Solution:
- By locking the bus: Because the CPU communicates with other components through the bus, if you lock the bus, you block other cpus from accessing other components (such as memory), so that only one CPU can use the variable’s memory
- Through cache consistency protocols (such as THE MESI protocol) : Copies of shared variables used in each cache are guaranteed to be consistent. Core ideas: When the CPU to write information, if found operating variables are Shared variables, namely there are also a copy of the variable in the other CPU, sends a signal to notify the other CPU will be the variable cache line for invalid state, so when other CPU need to read the variable, found himself in the cache cache the variable cache line is invalid (sniffs), Then it will re-read from memory
CPU optimization is performed out of order
The CPU may optimize out-of-order execution of input code to maximize the utilization of its internal arithmetic unit
Ii. Java Memory Model (JMM)
The Java memory model is basically similar to the CPU memory model. The MEMORY model defined by the JVM shields the differences of memory access between different operating systems and hardware to achieve a consistent memory access effect across all platforms. [Compile once, run everywhere]
Definition: a control mechanism for communication between threads, which defines the abstract relationship between main memory and threads. The Java memory model has main memory, and each thread has its own working memory. When the thread performs a calculation, it first copies data from main memory to its working memory, and then flushes the data back to main memory
JMM rules on synchronization:
- The shared variable must be flushed to main memory before the thread is unlocked.
- Before a thread locks, it must read the latest value of main memory into its own working memory.
- Lock unlocking is the same lock.
JMM solves problems of atomicity, visibility and order
- Atomicity: Java is implemented through the synchronized keyword, based on the two advanced bytecode instructions provided by Java, monitorenter and Monitorexist
- Visibility: To ensure visibility of variables in multithreading operations, the modified variables are immediately synchronized to main memory after modification, and the other threads refresh from main memory before using the modified variables. In Java, volatile guarantees the visibility of variables, as do synchronized and final.
- Order: Ensures that operations are ordered between multiple threads in different ways. Volatile prevents instruction reordering. The synchronized keyword ensures that only one thread can operate at a time