> (b) The second approach is to draw a very simple, square box, and
> say: "You must program in the box".... One simple box is "Use[ers]
> must use synchronization or volatile variables to communicate
> between threads".
I vote for (b), in particular, the specific form of (b) defined above. In
the long run, this will make life simpler for everyone. For example, it
gets rid of the problem brought up in Bill's other message "Dropping
coherence is more complicated than we thought". And this is just one of
the many ways in which it simplifies things.
> The problem with (b) is that lots of existing code is outside any
> simple box we might construct.
I agree this is a problem. Fortunately, there are some mitigating factors:
(1) We can give people time to migrate to the new model. We don't
have to break their programs right away: for example, Java
implementations can have a "legacy-model" flag.
(b) We can give people tools to find the problem spots. All the
problematic legacy code presented on this mailing list uses
unsynchronized communication between threads. It is very easy to
detect such communication during testing using a run-time tool. (BTW,
another advantage of the "always synchronize" methodology is that it
supports extremely effective checking tools.)
Actually, when you think about it, what we're really talking about here is
putting in "volatile" on variables that use things like the single- and
double-check patterns. This is a pain, but it's not too hard, especially
given that we can build tools to detect lack of synchronization.
> A simple rule that requires extra synchronizations on machines that
> do not really need it will be difficult to maintain unless VMs on
> those machines are able to simply remove this overhead when it is
> not needed. People running on pentiums, sparcs, and other machines
> with relatively strong memory models should not be penalized.
I agree that this is an important requirment. I think the "always
synchronize" methodology combined with something like Bill's strawman
memory model (minus the global action ordering) achieves this goal.
Bill's strawman memory model includes two synchronization mechanisms: locks
and volatile variables. It's easier to make uneeded locks run faster under
Bill's strawman proposal than under the existing Java memory model because,
in Bill's model, unshared locks do not imply memory barriers. The problem
of "removing" synchronization from volatile variables on machines with
strong memory models like Pentiums is easy because you never really put it
in to begin with.
> Analysis tools are useful, but almost all QA these days is
> test-driven. If a program passes tests on platforms people have
> around, they declare success, regardless of whether the spec says
> that the program would not work under the officially sanctioned
> memory model.
I agree that QA these days is testing-centric. The nice thing about the
"always synchronize" methodology is that it allows QA orginizations "turbo
charge" their tests by running them using tools that check for
unsynchronized access. If the checker complains about a lack of
synchornization, the code gets thrown back to engineering, even if the
correct output is generated. (I spent some time running an engineering
group and in particular building up its QA team; based on this experience I
would claim that the QA folks would love such a tool for the same reason
that they love code with lots of assertions in it.)
This archive was generated by hypermail 2b29 : Thu Oct 13 2005 - 07:00:21 EDT