Skip to content

extern "C" fn with zero-sized argument? #342

Open
@madsmtm

Description

@madsmtm

C and C++ have a hard time with zero-sized types, they're basically not possible without special compiler extensions as far as I can tell? However, the following Rust code compiles fine without any warnings:

#[repr(C)]
pub struct X([u8; 0]);

extern "C" {
    fn my_fn1(_x: X);
}

pub extern "C" fn my_fn2(_x: X) {}

fn main() {
    my_fn1(X([]));
    my_fn2(X([]));
}

How do we currently handle this (as far as I can tell, they're just ignored)? Do we want to make any guarantees about how they work? Are there any calling conventions that reserve "space" for zero-sized arguments?

(I have a little bit of a use-case for this: In objc2, it would make the API slightly nicer to be able to "act" as-if a function took a specific zero-sized marker type MainThreadMarker).

If this is UB, I think we should at least extend the improper_c_types lint to warn on zero-sized arguments.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions