Proposal: Security Working Group


I definitely agree that it’s a hard problem, as illustrated by all of the existing attempts. However, I think it’s worthwhile enough to make it worth pursuing. There’s essentially a class of code - important code at that - which cannot be written in pure Rust without relying on unreliable hacks. But yes, definitely a hard problem :slight_smile:

cc @hdevalence who’s interested in this


There’s probably going to be overlap with the Unsafe Code Guidelines and Formal Verification working groups. I’m also interested in participating in this one, so I’d be happy to help with coordination etc.

This is a huge space and I’m excited to see where it leads–hopefully it will expand and we’ll have various subdomain groups in the future!


What would be great is if Rust had a no-op black-box function whose output was opaque. On nightly this can be basically accomplished by an empty inline assembly block, but inline assembly isn’t stable (and probably shouldn’t be).

So it would be nice if Rust provided a black-box function, even if it were implemented using inline asm, which had defined behaviour people could reason about.




That’d be a nice intermediate step, but that still doesn’t guarantee that the compiler or backend (LLVM, WASM, etc) won’t be super smart in the future. I’m actually planning on bringing this up at a WASM community meeting soon if you’d like to join. I was going to poke you directly, but poke-via-forum works too :slight_smile:


Yes, the current implementation of test::black_box works, but it’s a) not stable and b) doesn’t define its behaviour in a way that makes it useful in this context: it’s intended for benchmarking.

What’s important is that there’s a stable black_box with the property that the compiler cannot infer any information about the output of black_box other than its type, and that that property is provided by Rust, so that if the backend changes, it’s the responsibility of the stdlib to maintain the black_box contract.


I’d sure volunteer for this WG!


I’m totally in.


That’d be a nice intermediate step,

I’m not sure it’s an intermediate step – I think the key is to have some function with defined properties which make it possible to reason about the optimizer, so that it’s possible to build things like Tim Maclean’s rust-timing-shield or my and Isis’ subtle. What would a more advanced step look like?

but that still doesn’t guarantee that the compiler or backend (LLVM, WASM, etc) won’t be super smart in the future.

Ultimately “constant-time” is not a property of the software, but of the combination of software and hardware, so this is basically unavoidable, since Rust only controls (some of) the software and not the hardware.


I’d be interested in participating in something like this. I think one of the first things that needs to be addressed is the actual scope, as there’s a lot of potential for overlap with other WGs, and I worry about spreading ourselves too thin.

I think interoperability between various cryptographic libraries and potentially a “crypto” crate would be interesting things to address.


A more advanced step would be “the compiler guarantees that this will execute in constant time according to the semantics of the IR.” That, of course, requires that the IR provides a similar guarantee - “the backend guarantees that this will execute in constant time according to the semantics of the machine instruction set.” Obviously this is never a perfect guarantee because there are CPU bugs, but it’s the best we can get.

In particular, this is “more advanced” than simply being opaque to the optimizer in that the optimizer could still legally do stupid things like say, “even though I think this is an i8, I will branch on whether its value is 25.” Obviously that’d be silly, but the semantics don’t rule out such an optimization (or, more realistically, actually-useful optimizations that still introduce branching).

Yes, but that’s true of any language semantics. Rust doesn’t literally guarantee that the code it compiles executes correctly, but rather that the IR it emits has the same semantics as your program. The same is true of the IR -> machine code translation.


I agree. Perhaps that should be discussed at the first meeting?


I was thinking about this group. Something that is often over looked but can be extremely useful for newer users is high quality examples and documentation for common security related tasks. I think we’ve all seen authentication and session management handled many different, incorrect ways. Going through a lot of the common web frameworks and making sure they have a clear, properly implemented example showing someone performing a login, checking the password against a properly hashed record, getting issued a session token and then using that to consume an protected API could be extremely useful.


I would love to join this WG!


Yeah, that’s a really good idea.


I’m fairly unfamiliar with the process of working groups and the internals of Rust in general. Would this WG have something to do with the recent CVE-2018-1000657 with regards to unsound implementations of standard library functionality?


There is already a recently-formed group of maintainers for sodiumoxide, since the original contributor doesn’t have time to maintain the crate, which consists largely of rusty (i.e., oxidized) bindings to the C NaCl (i.e., sodium chloride, salt) library.

Re constant-time operations, which is an approach to eliminate one class of straightforward side-channel timing attacks, MIR would need a way to annotate a region of its output to suppress certain classes of optimization by LLVM and other compiler backends. I don’t think it’s likely that LLVM and other backends, which are driven primarily by the needs of C and C++, will evolve support for such a feature. Even if they do, the resulting code is still exposed to all the other classes of side-channel timing attacks.

The Rust subtle crate uses Nightly and assembly to nominally “touch” a register, with the intent of suppressing LLVM optimizations across that point in the code. As @hdevalence mentioned, there’s no guarantee that this approach will continue to work with LLVM, or work at all with other potential backends.

As of today, the best way to reduce timing side-channel attacks is to write the susceptible code in assembly. Unfortunately, that’s an architecture-specific Nightly feature, and is likely to remain so. It also does little to mitigate the ever-growing class of attacks (e.g., Spectre, Meltdown, …) against the speculative execution hardware in many modern processors, and can’t do anything about instructions with data-dependent variable timing, such as scalar integer multiply on PowerPC and ARM processors.

The long-term answer is to develop high-throughput processors without such susceptibility, as well as cryptographic algorithms in which any potentially timing-dependent operations offer little assistance to cryptanalysis. Progress is being made on both those fronts.

In the shorter term it would be worth developing a way to convert a conditional into a uN bit mask (all zeros or all ones) in constant time, first in MIR and then propagated through LLVM and other backends. That would be enough to permit constant-time pseudo-Boolean bit operations (e.g., and, or, xor, not), as well as conditional-select, conditional-negate, conditional-swap, conditional-assign and perhaps other basic conditional operations. The subtle crate offers a starting point.


It would certainly be in the group’s wheelhouse, yeah. Although it’s more squarely within the scope of the Unsafe Code Guidelines WG.


I don’t think that’s what I said. Actually, I suggested stabilizing that feature as a concrete and achievable step that would allow Rust to do meaningfully better than it does now.

In general, I feel that rewriting LLVM so that its IR encodes timing side-channel information, or developing new processor architectures, are out of scope for a Rust working group.


I feel specific feature discussions should be done in a different thread. This discussion was to scope a potential new working group, not discuss defenses against timing attacks