RFR (M) 8195099: Concurrent safe-memory-reclamation mechanism
Robbin Ehn
robbin.ehn at oracle.com
Wed Apr 11 11:38:19 UTC 2018
Hi,
On 04/11/2018 12:57 PM, David Holmes wrote:
>
> Sorry no, I don't understand what this counter is doing at all. I feel I need to
> see what is between the begin/end critical section for this to make any sense to
> me. And to see what the writer actually does.
From gtest:
Read side do:
49 GlobalCounter::critical_section_begin(this);
50 volatile TestData* test = OrderAccess::load_acquire(_test);
51 long value = OrderAccess::load_acquire(&test->test_value);
52 ASSERT_EQ(value, GOOD);
53 GlobalCounter::critical_section_end(this);
Write side do:
101 volatile TestData* free_tmp = test;
102 tmp = new TestData();
103 tmp->test_value = GOOD;
104 OrderAccess::release_store(&test, tmp);
105 GlobalCounter::write_synchronize();
106 free_tmp->test_value = BAD;
107 delete free_tmp;
If a reader is context switch between line 50 and 51, it will have a cached
value of the pointer "_test", thus no one should free it.
Before freeing the writer calls write_synchronize which guarantees that no
reader can see the old pointer and can then free it.
If the reader is context switch inside critical_section_begin this does not
matter since the fence in critical_section_begin prohibits the load of test
pointer from floating up. If write_synchronize is done before this reader gets
back on CPU it will see the new value but have an counter of an old generation.
If it gets back on CPU before write_synchronize I will see the old pointer.
If we call the pointer values TEST_gen_1, TEST_gen_2, ...
test_pointer starts equal to TEST_gen_1 and generation starts at 1.
Writer: tmp_pointer = test_pointer
Writer: test_pointer = TEST_gen_2
Reader: load global counter (fetches 1)
Reader: context switched out
Writer: write_synchronized generation = 2, and do not see the reader.
Reader: store local counter to 1 // critical section begin
Reader: load test_pointer (TEST_gen_2) // This load will always happen *after*
the store to local counter
Writer: free tmp_pointer (TEST_gen_1) // ABA safe
Writer: tmp_pointer = test_pointer
Writer: test_pointer = TEST_gen_3
Writer: write_synchronized generation = 3, and _sees_ on old reader => wait.
Reader: store local counter OFF // critical section end
Writer: write_synchronized now finishes.
Writer: free tmp_pointer (TEST_gen_2) // ABA safe
/Robbin
>
> David
> -----
More information about the hotspot-dev
mailing list