Skip to content

Commit 2af7dca

Browse files
committed
c-variadic: bpf and spirv do not support c-variadic definitions
1 parent 23f7081 commit 2af7dca

File tree

5 files changed

+48
-1
lines changed

5 files changed

+48
-1
lines changed

compiler/rustc_ast_passes/messages.ftl

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,8 @@ ast_passes_c_variadic_must_be_unsafe =
8080
ast_passes_c_variadic_no_extern = `...` is not supported for non-extern functions
8181
.help = only `extern "C"` and `extern "C-unwind"` functions may have a C variable argument list
8282
83+
ast_passes_c_variadic_not_supported = the `{$target}` target does not support c-variadic functions
84+
8385
ast_passes_const_and_c_variadic = functions cannot be both `const` and C-variadic
8486
.const = `const` because of this
8587
.variadic = C-variadic because of this

compiler/rustc_ast_passes/src/ast_validation.rs

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ use rustc_session::lint::builtin::{
3737
};
3838
use rustc_session::parse::feature_err;
3939
use rustc_span::{Ident, Span, kw, sym};
40-
use rustc_target::spec::{AbiMap, AbiMapping};
40+
use rustc_target::spec::{AbiMap, AbiMapping, Arch};
4141
use thin_vec::thin_vec;
4242

4343
use crate::errors::{self, TildeConstReason};
@@ -707,6 +707,15 @@ impl<'a> AstValidator<'a> {
707707
});
708708
}
709709

710+
// Some targets just do not allow c-variadic definitions.
711+
let target = &self.sess.target;
712+
if matches!(target.arch, Arch::SpirV | Arch::Bpf) {
713+
self.dcx().emit_err(errors::CVariadicNotSupported {
714+
variadic_span: variadic_param.span,
715+
target: &*target.llvm_target,
716+
});
717+
}
718+
710719
match fn_ctxt {
711720
FnCtxt::Foreign => return,
712721
FnCtxt::Free | FnCtxt::Assoc(_) => {

compiler/rustc_ast_passes/src/errors.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -725,6 +725,14 @@ pub(crate) struct CoroutineAndCVariadic {
725725
pub variadic_span: Span,
726726
}
727727

728+
#[derive(Diagnostic)]
729+
#[diag(ast_passes_c_variadic_not_supported)]
730+
pub(crate) struct CVariadicNotSupported<'a> {
731+
#[primary_span]
732+
pub variadic_span: Span,
733+
pub target: &'a str,
734+
}
735+
728736
#[derive(Diagnostic)]
729737
#[diag(ast_passes_pattern_in_foreign, code = E0130)]
730738
// FIXME: deduplicate with rustc_lint (`BuiltinLintDiag::PatternsInFnsWithoutBody`)
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
error: the `bpfel` target does not support c-variadic functions
2+
--> $DIR/not-supported.rs:19:31
3+
|
4+
LL | unsafe extern "C" fn variadic(_: ...) {}
5+
| ^^^^^^
6+
7+
error: aborting due to 1 previous error
8+
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
//@ add-minicore
2+
//@ revisions: bpf
3+
//@ [bpf] compile-flags: --target=bpfel-unknown-none
4+
//@ [bpf] needs-llvm-components: bpf
5+
//@ ignore-backends: gcc
6+
#![no_core]
7+
#![feature(no_core, lang_items, c_variadic)]
8+
#![crate_type = "lib"]
9+
10+
// Some targets do not support c-variadic definitions. Examples are bpf and spirv.
11+
12+
extern crate minicore;
13+
use minicore::*;
14+
15+
#[lang = "va_list"]
16+
struct VaList(*mut i32);
17+
18+
#[unsafe(no_mangle)]
19+
unsafe extern "C" fn variadic(_: ...) {}
20+
//~^ ERROR the `bpfel` target does not support c-variadic functions

0 commit comments

Comments
 (0)