This is an evolving and ever-explored field... The "current" (and in typically used in production 8 and 11) versions of OpenJDK and HotSpot performs safepoint as an all-or-nothing, Stop-The-World (STW) event. Since the frequency of STW pauses will generally tend to be low (for obvious reasons, if it were high, you'd be facing much bigger complaints), the likelihood of a safepoint poll actually triggering will be VERY low (think "1 in a billion" or less for a practical order of magnitude feel). As such, code that accepts STW pauses tends to be optimized for trhe NOT triggering case, and a "blind load" from a potentially protected location has bee (empirically chosen as) the fastest way to perform the poll.
A way to look at a read from a potentially protected page is as 1) An implicit "predicted not taken" form of a check CPUs will never predict that fault will be taken (that would be silly) so no branch prediction state is needed for this. On Sunday, May 17, 2020 at 9:27:36 PM UTC-7, Steven Stewart-Gallus wrote: > > Hi > As I understand it most VMs poll for safepoints by using memory management > tricks to page fault polling threads. A page is set aside to read from and > whenever a safepoint is desired the page is set to be unreadable. > > But can't a number of other hardware traps be used instead > https://wiki.osdev.org/Exceptions ? > > Not sure if a conditional jump to a trapping debug instruction would be > slow or not. > > Also why not read from a pointer to a page instead of reading directly? > That way only a an atomic write to a pointer is needed instead of a whole > memory protection syscall. > > Also an atomicly written boolean flag is only one of many possible types > of branches. > You could have an indirect call or possibly jump and just overwrite a > function pointer to install your handler for example. > > The standard way of doing things seems pretty sensible but it's just I've > never actually seen a concrete comparison. > > Basically in pseudocode why > > void poll() { > page[0]; > } > void trap() { > mprotect(page, 0); > } > > over > > void poll() { > page[0]; > } > void trap() { > page = 0; > } > > or > > void poll() { > 1 / bit; > } > void trap() { > bit = 0; > } > > And why > > void poll() { > if (flag) dostuff(); > } > > over > > void poll() { > f(); > } > void trap() { > f = handler; > } > > Or > > void poll() { > if (flag) __builtin_trao(); > } > > Probably makes sense to do safepoint polls the standard way but I've never > seen a detailed comparison exactly why. > > -- You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To view this discussion on the web, visit https://groups.google.com/d/msgid/mechanical-sympathy/8cd7f05d-def0-4f9c-8fff-e54ca39312f2%40googlegroups.com.
