-
Notifications
You must be signed in to change notification settings - Fork 120
Make remote_attestation crate no_std compatible #2556
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Make remote_attestation crate no_std compatible #2556
Conversation
df1e7c8
to
297ab62
Compare
297ab62
to
917e0be
Compare
Do we have a CI command that compiles it with |
By default it is built as |
log = "*" | ||
prost = "*" | ||
prost = { version = "*", default-features = false, features = ["prost-derive"] } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since we are not restricting versions, is it possible that the future versions of our dependencies will become std
instead of no_std
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, it is possible. I am not sure whether there is a good way to detect that automatically.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't this crate fail to compile in that case (at least with the defaul features, i.e. alloc instead of std)?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If prost
removes no_std
compatibility and removes the std
feature so that it always pulls in std
I think it will still compile. std
reexports the core
and alloc
types, so the types will still be compatible.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Drive-by: the best way I've found to check no_std
compatibility is to have a CI step that cross-compiles for a target with no std
available.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks. At the moment the build requires a target OS because that is required by ring
. We should be able to build it for a UEFI target once briansmith/ring#1406 has been merged.
hkdf::{Salt, HKDF_SHA256}, | ||
rand::{SecureRandom, SystemRandom}, | ||
signature::{EcdsaKeyPair, EcdsaSigningAlgorithm, EcdsaVerificationAlgorithm, KeyPair}, | ||
}; | ||
use sha2::{digest::Digest, Sha256}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did sha2
require std?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No, but ring
already provides the ability to generate sha256 hashes, so I removed sha2
to reduce the dependencies.
remote_attestation/rust/Cargo.toml
Outdated
[features] | ||
default = ["alloc"] | ||
std = ["anyhow/std", "prost/std"] | ||
alloc = [] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this actually needed for anything, or is it more for documentation purposes?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It was something I experimented with and forgot to delete. Deleted now.
log = "*" | ||
prost = "*" | ||
prost = { version = "*", default-features = false, features = ["prost-derive"] } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't this crate fail to compile in that case (at least with the defaul features, i.e. alloc instead of std)?
@@ -234,7 +235,7 @@ impl KeyNegotiator { | |||
&agreement::UnparsedPublicKey::new(KEY_AGREEMENT_ALGORITHM, peer_public_key), | |||
anyhow!("Couldn't derive session keys"), | |||
|key_material| { | |||
let key_material = key_material.try_into().context(format!( | |||
let key_material = key_material.try_into().context(alloc::format!( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would suggest just re-use all these things from alloc, instead of qualifying them everywhere. In fact I'm surprised they are not already in some prelude. Maybe we should build our own prelude? (see https://doc.rust-lang.org/core/prelude/v1/index.html)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It seems that there used to be an experimental alloc prelude, but it no longer exists. Importing custom preludes does not seem to be encouraged (https://doc.rust-lang.org/beta/unstable-book/language-features/prelude-import.html), so I added use statements as needed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't see anything that discourages custom preludes, a lot of libraries do that. The feature to bake a prelude in the compiler is another story, I don't recommend we use that, just use oak_uefi::prelude::*
basically.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you mean that we have to add the use statement to all modules that use it? Or is there another way (apart from prelude-import
) to use it for the entire crate?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes we would need to import it. e.g. https://docs.rs/futures/latest/futures/prelude/index.html
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Created #2564
0191a18
to
97977e1
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks.
remote_attestation/rust/Cargo.toml
Outdated
[features] | ||
default = ["alloc"] | ||
std = ["anyhow/std", "prost/std"] | ||
alloc = [] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It was something I experimented with and forgot to delete. Deleted now.
log = "*" | ||
prost = "*" | ||
prost = { version = "*", default-features = false, features = ["prost-derive"] } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If prost
removes no_std
compatibility and removes the std
feature so that it always pulls in std
I think it will still compile. std
reexports the core
and alloc
types, so the types will still be compatible.
@@ -234,7 +235,7 @@ impl KeyNegotiator { | |||
&agreement::UnparsedPublicKey::new(KEY_AGREEMENT_ALGORITHM, peer_public_key), | |||
anyhow!("Couldn't derive session keys"), | |||
|key_material| { | |||
let key_material = key_material.try_into().context(format!( | |||
let key_material = key_material.try_into().context(alloc::format!( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It seems that there used to be an experimental alloc prelude, but it no longer exists. Importing custom preludes does not seem to be encouraged (https://doc.rust-lang.org/beta/unstable-book/language-features/prelude-import.html), so I added use statements as needed.
Reproducibility Index:
Reproducibility Index diff: diff --git a/reproducibility_index b/reproducibility_index
index c47b5ab..5cb7e3b 100644
--- a/reproducibility_index
+++ b/reproducibility_index
@@ -1,2 +1,2 @@
-e81b77bd5e6aa364b806b14ab64215ef811892a6492f7d4b2cfdf3066b60d029 ./target/x86_64-unknown-linux-musl/release/oak_functions_loader_base
-ed45262f841ab276d9411219c7f5eee7a3aaeefbc7dbe32740089f07e1939407 ./target/x86_64-unknown-linux-musl/release/oak_functions_loader_unsafe
+d16e9c355afdf34390d3991d52504b574665f6b829136b83c1de9b57aa230a24 ./target/x86_64-unknown-linux-musl/release/oak_functions_loader_base
+537dda6bc3e1eb4854d9ff76abb5b019b743b0e0ae8e83f02331629079a51e38 ./target/x86_64-unknown-linux-musl/release/oak_functions_loader_unsafe
|
This PR reduces dependencies of the
remote_attestation
crate and makes it usable inno_std
environments.Reducing the dependencies should simplify future code audits. An important part of the change is to move away from the
bincode
crate to manual serialization of the handshake messages. Thebincode
crate requiresstd
, and manual serialization will also provide more control over the structure of these handshake messages.Fixes #2294