Live data from Hacker News

A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

github.com

11–20 of 141 posts

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#11
post #3

And arm-windows will (does already?) run x86 binaries with weaker memory ordering than they were written for. So this could be a real thing soon.

Are you sure the translators don't insert code necessary to maintain ordering? I would be shocked if most threaded code works when you throw out the x86 memory model. Managed runtimes like .NET definitely generate code for each target designed to maintain the correct memory model.

Maintaining the memory model guarantees is what causes the steep cost in performance when using x86 apps on Windows on Arm.

That said, heuristics are used to speed it up. I would recommend not sharing values in the stack between threads for synchronisation for example.

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#12

Earlier quoted context omitted.

Are you sure the translators don't insert code necessary to maintain ordering? I would be shocked if most threaded code works when you throw out the x86 memory model. Managed runtimes like .NET definitely generate code for each target designed to maintain the correct memory model.

They better do, but then, how would an automatic translator know that this is a "release semantics" atomic store operation? Because on x86 it is, no special barriers or instructions necessary. mov [shared_data], 1 mov [release_flag], 1

It’s pessimistic and converts over a lot of memory accesses to RCpc or atomics.

(on ARMv8.0 where you don’t have those, barriers are used more)

TSO pessimization is the only way to make the thing work at a translation time cost that isn’t too high.

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#15
post #2

Lock-free programming is really tough. There are really only a few patterns that work (e.g. Treiber stack). Trying to invent a new lock-free algorithm, as this vulnerable code demonstrates, almost always ends in tears.

IMO lock-free MP or MC algorithms are harder to get right than SPSC structures (atomics for shared memory, queues for messaging, triple buffers for tear-free shared memory). But even SPSC algorithms can be tricky; I've found the same (theoretical) ordering error in three separate Rust implementations of triple buffering (one of them mine), written by people who've already learned the ordering rules (which I caught with Loom). And initially learning to reason about memory ordering is a major upfront challenge too.

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#16
post #4
post #3

And arm-windows will (does already?) run x86 binaries with weaker memory ordering than they were written for. So this could be a real thing soon.

Now I am worried. Do you have a reference please?

Best I could find. It's not a great reference because it doesn't give any details but it does prove that it's a thing. https://docs.microsoft.com/en-us/windows/uwp/porting/apps-on...

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#17
post #13

Have i told you about our lord and savior Rust? Anyways, https://github.com/tokio-rs/loom is used by any serious library doing atomic ops/synchronization and it blew me away with how fast it can catch most bugs like this.

Rust doesn't catch memory ordering errors, which can result in behavioral bugs in safe Rust and data races and memory unsafety in unsafe Rust. But Loom is an excellent tool for catching ordering errors, though its UnsafeCell API differs from std's (and worse yet, some people report Loom returns false positives/negatives in some cases: https://github.com/tokio-rs/loom/issues/180, possibly https://github.com/tokio-rs/loom/issues/166).

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#18
post #9
post #3

And arm-windows will (does already?) run x86 binaries with weaker memory ordering than they were written for. So this could be a real thing soon.

Normally the code should have all the needed memory fences as if running on DEC Alpha, e.g. linux does that, and the compilers omit the unneeded ones.

And since the compiler omitted it on x86, an x86 emulator doesn't have access to where they're required as seen by the compiler.

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#19
post #13

Have i told you about our lord and savior Rust? Anyways, https://github.com/tokio-rs/loom is used by any serious library doing atomic ops/synchronization and it blew me away with how fast it can catch most bugs like this.

Rust doesn't catch memory ordering errors, which can result in behavioral bugs in safe Rust and data races and memory unsafety in unsafe Rust. But Loom is an excellent tool for catching ordering errors, though its UnsafeCell API differs from std's (and worse yet, some people report Loom returns false positives/negatives in some cases: https://github.com/tokio-rs/loom/issues/180 , possibly https://github.com/tokio-rs/…

I think it's fixable, the main reactor is what matters. You can add or remove as many synchronisation primitive as you like.

Other tooling, like Jepsen, will interact with your program at a higher level.

Re: A bug that doesn’t exist on x86: Exploiting an ARM-only race condition

#20
post #3

And arm-windows will (does already?) run x86 binaries with weaker memory ordering than they were written for. So this could be a real thing soon.

Are you sure the translators don't insert code necessary to maintain ordering? I would be shocked if most threaded code works when you throw out the x86 memory model. Managed runtimes like .NET definitely generate code for each target designed to maintain the correct memory model.

https://docs.microsoft.com/en-us/windows/uwp/porting/apps-on...

> You can also select multi-core settings, as shown here... These settings change the number of memory barriers used to synchronize memory accesses between cores in apps during emulation. Fast is the default mode, but the strict and very strict options will increase the number of barriers. This slows down the app, but reduces the risk of app errors. The single-core option removes all barriers but forces all app threads to run on a single core.

https://news.ycombinator.com/item?id=28732273

zamadatix's interprets this as Microsoft saying that by default, Windows on ARM runs x86 apps without x86 TSO, and turns on extra memory barriers using per-app compatibility settings. But if an app needs TSO but isn't in Windows's database, it will crash or silently corrupt data.

Post reply on HN