How to implement !Send or !Sync for a type?

Viewed 1411

Is it possible to explicitly mark a type with unimplemented Send or Sync marker traits without some redundant fields? This can be an alternative:

struct T {
    _marker: PhantomData<*const ()>,
}

but again, it has a redundant field, is super cryptic (you need to remember that a pointer is !Send + !Sync) and might be nontrivial to get a proper combination (consider !Sync + Send). I believe negative trait might be a solution, but they are not available at stable yet:

// error[E0658]: negative trait bounds are not yet fully implemented
impl !Send for T {}

Playground

1 Answers

Your PhantomData solution is generally the way to do this. I was sort of surprised to see that there's no PhantomUnsend or PhantomUnsync types in std::marker, in the same way that there's a PhantomPinned; my advice would be to add, in a util.rs module, something resembling:

pub type PhantomUnsync = PhantomData<Cell<()>>;
pub type PhantomUnsend = PhantomData<MutexGuard<'static, ()>>;

These typedefs make it clear that they exist to force !Send or !Sync in types that contain them, in the same way that PhantomPinned forces !Unpin.

Related