Closed matthias-g closed 5 years ago
SGXAPI sgx_seal_data only supports linear buffer (identified by ptr+len).
So the seal+unseal combination performs a bit-by-bit copy of a linear buffer, which is equivalent to the definition of Copy.
The memory object of a Vec
structure contains a pointer field. And this is the reason why we cannot duplicate a Vec
by simply memcpy it.
I would recommend you use the ported serde for serialization and use serde_cbor for encoding. This combination would generate a byte string which is dense and friendly to sgx_seal_data
.
Can't you just do this?
#[derive(Clone, Copy)]
struct A<'a> (pub &'a [u8]);
unsafe impl sgx_types::marker::ContiguousMemory for A {};
Then you can put a vec in there using:
v.as_slice()
/ v.into_boxed_slice
/ slice::from_raw_parts(s.as_ptr(), v.len())
Thanks for your replies! That helped me to get a better understanding of what happens here.
However I can't get it working yet. To show you the problem, I adapted the sealeddata
sample using a combination of your replies.
The app is terminated by signal SIGILL (Illegal instruction). This is probably because the data read during verify_sealeddata
differs from the data written in create_sealeddata
. In my case the first 32 bytes are different and the remaining are the same. Do you see where this difference comes from? How can this be implemented correctly?
Hmmmm I just find that the fixed-length array works fine with your EncodedData
let a: [u8;4] = [0x11,0x22,0x33,0x44]
But Vec<u8>
like this not working:
let b: Vec<u8> = vec![0x11,0x22,0x33,0x44]
I think there's something wrong with sgx_tseal when dealing with fat pointers.
Sorry for the wrong answer. I just deleted it.
seal_data function uses mem::size_of_val
to get the buffer length:
let len = mem::size_of_val(encrypt_text);
len
of the EncodedData
is always 16 no matter how long the data is. I think this may be the problem.
use std::mem;
#[derive(Clone, Copy)]
struct EncodedData<'a> (pub &'a [u8]);
impl<'a> From<&'a[u8]> for EncodedData<'a> {
fn from(data: &'a[u8]) -> Self {
EncodedData(data)
}
}
fn main() {
let a:[u8;20] = [0x11,0x22,0x33,0x44,0x11,0x22,0x33,0x44,0x11,0x22,0x33,0x44,0x11,0x22,0x33,0x44,0x11,0x22,0x33,0x44];
let enc_a = EncodedData::from(&a[..]);
println!("size_of_val of a = {}", mem::size_of_val(&a)); // 20
println!("size_of_val of enc_a = {}", mem::size_of_val(&enc_a)); // 16
}
The current sgx_tseal can seal a
but not enc_a
. Hmmmm.
So I think you can just put the output of serde_cbor (data stored in [u8]
) to the data sealing API. No need for additional data structure such as EncodedData
, which only contains an immutable reference.
EncodedData
seems to be a FatPtr<FatPtr<...>>
and the sealing API only supports FatPtr<T> where T: Copy + ContiguousMemory
.
Ok, thanks for looking into it.
I removed EncodedData
in #70 so that we now pass a slice with the output of serde_cbor to seal_data
. However this does not compile because the necessary traits are not implemented for &[u8]
.
In seal.rs
there is an implementation of SgxSealedData
for T where T: Copy + ContiguousMemory
and an implementation for [T] where T: Copy + ContiguousMemory
. Maybe an implementation for slices is needed there as well?
Closing since new code sample shows how to implement this. https://github.com/baidu/rust-sgx-sdk/pull/70#issuecomment-488071572
How can I use
seal_data
for a struct containing aVec
? Starting from the samplesealeddata
: If I add a field containing aVec
toRandData
, I don't understand how to seal the struct then, becauseVec
does not implementCopy
:An idea was to use corepack to serialize the struct. But this results in a
Vec<u8>
which does not really help. There is an implementation ofSgxSealedData
for[T]
whereT
isCopy + ContiguousMemory
, but none for&[T]
which I could get fromvec.as_slice()
.Generally I don't understand, why the
Copy
trait is required. Can someone help me here?