-
Notifications
You must be signed in to change notification settings - Fork 12.8k
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
#[deny(unsafe_op_in_unsafe_fn)]
in sys/wasm
#74477
#[deny(unsafe_op_in_unsafe_fn)]
in sys/wasm
#74477
Conversation
(rust_highfive has picked a reviewer for you, use r? to override) |
// SAFETY: The caller must gurantee that the argument of `fetch_add()` is valid | ||
// to describe memory ordering. | ||
unsafe { | ||
self.cnt.fetch_add(1, SeqCst); |
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.
This is not an unsafe operation.
self.cnt.fetch_add(1, SeqCst); | ||
} | ||
unsafe { | ||
wasm32::atomic_notify(self.ptr(), 1); |
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.
My guess is that the unsafety here is basically just from the raw pointer, so we can say something like "ptr() is always valid"
@@ -60,7 +72,7 @@ impl Condvar { | |||
// thread. Incrementing the counter after we unlock the mutex will | |||
// prevent us from sleeping and otherwise the call to `wake` will | |||
// wake us up once we're asleep. | |||
let ticket = self.cnt.load(SeqCst) as i32; | |||
let ticket = unsafe { self.cnt.load(SeqCst) as i32 }; |
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.
This is also not an unsafe operation.
src/libstd/sys/wasm/mutex_atomics.rs
Outdated
1, // we expect our mutex is locked | ||
-1, // wait infinitely | ||
); | ||
// SAFETY: the caller must uphold the safety contract for `i32_atomic_wait`. |
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.
This seems... odd. @alexcrichton, can you recall why lock() here is unsafe? It seems like it could be safe.
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.
The intrinsic has a *mut i32
in the signature which it modifies, so the intrinsic is unsafe.
src/libstd/sys/wasm/mutex_atomics.rs
Outdated
// we should have either woke up (0) or got a not-equal due to a | ||
// race (1). We should never time out (2) | ||
debug_assert!(val == 0 || val == 1); | ||
} | ||
} | ||
|
||
pub unsafe fn unlock(&self) { | ||
let prev = self.locked.swap(0, SeqCst); | ||
// SAFETY: the caller must uphold the safety contract for `swap`. | ||
let prev = unsafe { self.locked.swap(0, SeqCst) }; |
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.
Atomic operations are safe.
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.
Thank you for the review
☔ The latest upstream changes (presumably #74569) made this pull request unmergeable. Please resolve the merge conflicts. |
0054eb3
to
90d4625
Compare
☔ The latest upstream changes (presumably #73265) made this pull request unmergeable. Please resolve the merge conflicts. |
440f06c
to
c0accca
Compare
This hasn't got any response for a while, r? @Mark-Simulacrum as you left some reviews. |
// to describe memory ordering. | ||
unsafe { | ||
self.cnt.fetch_add(1, SeqCst); | ||
} |
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.
Not an unsafe operation (please also fix the other atomics).
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.
ok
c0accca
to
fa379b4
Compare
@chansuke Ping from triage! What's the current status on this? i assume this is ready for review again? |
); | ||
// SAFETY: the caller must uphold the safety contract for `i32_atomic_wait`. | ||
let val = unsafe { | ||
wasm32::i32_atomic_wait( |
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 think this is a rebase failure -- this function seems to have been renamed to memory_atomic_wait32 on master. (I think there's one or two more cases where you have that).
} | ||
|
||
#[inline] | ||
unsafe fn _try_lock(&self, id: u32) -> Result<(), u32> { | ||
let id = id.checked_add(1).unwrap(); // make sure `id` isn't 0 | ||
// SAFETY: the caller must gurantee that `id` isn't 0 | ||
let id = unsafe { id.checked_add(1).unwrap() }; |
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.
This is also not an unsafe operation.
self.owner.swap(0, SeqCst); | ||
wasm32::memory_atomic_notify(self.ptr() as *mut i32, 1); // wake up one waiter, if any | ||
unsafe { | ||
self.owner.swap(0, SeqCst); |
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.
This is not an unsafe operation.
self.cnt.fetch_add(1, SeqCst); | ||
wasm32::memory_atomic_notify(self.ptr(), u32::MAX); // -1 == "wake everyone" | ||
unsafe { | ||
wasm32::atomic_notify(self.ptr(), u32::MAX); // -1 == "wake everyone" |
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.
This also lost the right name.
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.
Sorry, I fixed...
fa379b4
to
353727b
Compare
@crlf0710 Sorry for the late reply. I fixed and now it's ready for the review. |
wasm32::memory_atomic_notify(self.ptr(), 1); | ||
// SAFETY: ptr() is always valid | ||
unsafe { | ||
wasm32::atomic_notify(self.ptr(), 1); |
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 think this is still the wrong name, it should be memory_atomic_notify.
wasm32::memory_atomic_notify(self.ptr() as *mut i32, 1); // wake up one waiter, if any | ||
unsafe { | ||
wasm32::atomic_notify(self.ptr() as *mut i32, 1); | ||
} // wake up one waiter, if any |
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.
Can you put this comment above the unsafe block instead?
I think I likely approved the SGX changes a bit earlier than was warranted (sgx is also less critical in some sense as it's not to my knowledge something readily used by consumers, though I could be wrong). lock::lock() is defined in the alloc.rs file and is just taking a global lock if std is compiled with atomics enabled. We need the locks with multithreading because the allocator is called with |
4a17d19
to
2ff5965
Compare
let _lock = lock::lock(); | ||
DLMALLOC.malloc(layout.size(), layout.align()) | ||
unsafe { DLMALLOC.malloc(layout.size(), layout.align()) } |
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.
There are two preconditions that we need to document for these calls:
- DLMALLOC access is safe: this is true because the lock gives us unique and non-reentrant access.
- Calling the function itself is safe: Preconditions on these functions match the trait method preconditions, so this is safe.
The comments so far only sort of talk about the first, but should address both. I think basically copy/pasting my two bullet points makes sense.
self.cnt.fetch_add(1, SeqCst); | ||
wasm32::memory_atomic_notify(self.ptr(), u32::MAX); // -1 == "wake everyone" | ||
unsafe { | ||
self.cnt.fetch_add(1, SeqCst); |
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.
This is not an unsafe operation and should not be inside the unsafe block. It also looks like are missing a safety comment about the first argument to memory_atomic_notify being a valid pointer.
@@ -47,7 +50,7 @@ impl Mutex { | |||
|
|||
#[inline] | |||
pub unsafe fn try_lock(&self) -> bool { | |||
self.locked.compare_exchange(0, 1, SeqCst, SeqCst).is_ok() | |||
unsafe { self.locked.compare_exchange(0, 1, SeqCst, SeqCst).is_ok() } |
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.
This is not an unsafe operation.
@@ -83,7 +86,7 @@ unsafe impl Sync for ReentrantMutex {} | |||
|
|||
impl ReentrantMutex { | |||
pub const unsafe fn uninitialized() -> ReentrantMutex { | |||
ReentrantMutex { owner: AtomicU32::new(0), recursions: UnsafeCell::new(0) } | |||
unsafe { ReentrantMutex { owner: AtomicU32::new(0), recursions: UnsafeCell::new(0) } } |
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 believe there are any unsafe operations here.
2ff5965
to
d37b8cf
Compare
@rustbot modify labels: +S-waiting-on-review -S-waiting-on-author |
@bors r+ rollup |
📌 Commit d37b8cf has been approved by |
…fe-fn, r=Mark-Simulacrum `#[deny(unsafe_op_in_unsafe_fn)]` in sys/wasm This is part of rust-lang#73904. This encloses unsafe operations in unsafe fn in `libstd/sys/wasm`. @rustbot modify labels: F-unsafe-block-in-unsafe-fn
…fe-fn, r=Mark-Simulacrum `#[deny(unsafe_op_in_unsafe_fn)]` in sys/wasm This is part of rust-lang#73904. This encloses unsafe operations in unsafe fn in `libstd/sys/wasm`. @rustbot modify labels: F-unsafe-block-in-unsafe-fn
Rollup of 10 pull requests Successful merges: - rust-lang#74477 (`#[deny(unsafe_op_in_unsafe_fn)]` in sys/wasm) - rust-lang#77836 (transmute_copy: explain that alignment is handled correctly) - rust-lang#78126 (Properly define va_arg and va_list for aarch64-apple-darwin) - rust-lang#78137 (Initialize tracing subscriber in compiletest tool) - rust-lang#78161 (Add issue template link to IRLO) - rust-lang#78214 (Tweak match arm semicolon removal suggestion to account for futures) - rust-lang#78247 (Fix rust-lang#78192) - rust-lang#78252 (Add codegen test for rust-lang#45964) - rust-lang#78268 (Do not try to report on closures to avoid ICE) - rust-lang#78295 (Add some regression tests) Failed merges: r? `@ghost`
This is part of #73904.
This encloses unsafe operations in unsafe fn in
libstd/sys/wasm
.@rustbot modify labels: F-unsafe-block-in-unsafe-fn