Skip to content
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

Insecure time through rdtscp #648

Closed

Conversation

raoulstrackx
Copy link
Contributor

SGXv2 platforms support calling the rdtscp instruction inside an enclave. This PR implements logic to keep track of the time inside of an enclave. Note that the value rdtscp returns, can be manipulated by an attacker; even with these changes insecure_time is (almost) as insecure as before. There's only an option to force the time to be monotonic.

This PR is blocked on internal API review

@raoulstrackx raoulstrackx marked this pull request as draft October 31, 2024 14:18
@raoulstrackx raoulstrackx force-pushed the raoul/rte-204-insecure_time_through_rdtscp branch from a9025ee to f5643ac Compare October 31, 2024 15:19
pub fn from_duration(duration: Duration, freq: &Freq) -> Self {
let freq = freq.as_u64();
let ticks_secs = duration.as_secs() * freq;
let ticks_nsecs = duration.subsec_nanos() as u64 * freq / NANOS_PER_SEC as u64;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

consider using subsec_millis

let time = time::SystemTime::now()
.duration_since(time::UNIX_EPOCH)
.unwrap();
(time.subsec_nanos() as u64) + time.as_secs() * 1_000_000_000
let t = (time.subsec_nanos() as u64) + time.as_secs() * 1_000_000_000;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Use a constant as before NANOS_PER_SECOND

/// # Miscellaneous
impl Usercalls {
/// This returns the number of nanoseconds since midnight UTC on January 1,
/// 1970\. The enclave must not rely on the accuracy of this time for
/// security purposes, such as checking credential expiry or preventing
/// rollback.
pub fn insecure_time() -> u64 { unimplemented!() }
pub fn insecure_time() -> (u64, *const InsecureTimeInfo) { unimplemented!() }
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR guard, in case this needs to be addressed in a subsequent commit

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR change was approved

fn abs_diff(&self, other: &Self) -> Duration {
match self.duration_since(*other) {
Ok(duration) => duration,
Err(e) => e.duration()
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just learned about duration_since. Since it is odd, I think it merits a comment explaining that Err(e) contains the duration when other is earlier than self.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a comment

}
}

pub struct Freq(AtomicU64);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From the code I understand this is an integer number representing the amount of ticks per second (add a comment).

Also is this a reasonable assumption? E.g. each second has an (exact) integer amount of ticks? Put otherwise, are ticks aligned to seconds?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Keeping track of the time is tricky. Some platforms do report their frequency, but do that incorrectly, others report it not at all (for older platforms, probably), or incompletely. The expectation is that processors that do support SGXv2 (and can thus call rdtsc in the enclave) do report their frequency, but running the main application it was observed that this reported frequency isn't correct (and deviates more than a fraction of a tick). The logic in this crates was made to be able to handle this.
I've added comments on the Tsc struct.

@raoulstrackx raoulstrackx force-pushed the raoul/rte-204-insecure_time_through_rdtscp branch from f5643ac to e7f9251 Compare November 21, 2024 15:47
@raoulstrackx
Copy link
Contributor Author

I've addressed the PR comments, but more work was needed to the runner. I've split up the work in two parts. I'll close this PR, and open up two new ones. Sorry for the mess.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants