From e54a16cffce0ecea2954b5af51247f7b4179900b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Thu, 5 Mar 2020 00:00:00 +0000 Subject: [PATCH 1/3] Change DIBuilderCreateEnumerator signature to match LLVM 9 No functional changes intended. --- src/librustc_codegen_llvm/debuginfo/metadata.rs | 16 ++++++++++------ src/librustc_codegen_llvm/llvm/ffi.rs | 4 +++- src/rustllvm/RustWrapper.cpp | 8 ++++---- 3 files changed, 17 insertions(+), 11 deletions(-) diff --git a/src/librustc_codegen_llvm/debuginfo/metadata.rs b/src/librustc_codegen_llvm/debuginfo/metadata.rs index 3916653eb1d76..7beaf134e6ba1 100644 --- a/src/librustc_codegen_llvm/debuginfo/metadata.rs +++ b/src/librustc_codegen_llvm/debuginfo/metadata.rs @@ -1779,13 +1779,15 @@ fn prepare_enum_metadata( .discriminants(cx.tcx) .zip(&def.variants) .map(|((_, discr), v)| { - let name = SmallCStr::new(&v.ident.as_str()); + let name = v.ident.as_str(); unsafe { Some(llvm::LLVMRustDIBuilderCreateEnumerator( DIB(cx), - name.as_ptr(), + name.as_ptr().cast(), + name.len(), // FIXME: what if enumeration has i128 discriminant? - discr.val as u64, + discr.val as i64, + false, // FIXME: IsUnsigned. )) } }) @@ -1794,13 +1796,15 @@ fn prepare_enum_metadata( .as_generator() .variant_range(enum_def_id, cx.tcx) .map(|variant_index| { - let name = SmallCStr::new(&substs.as_generator().variant_name(variant_index)); + let name = substs.as_generator().variant_name(variant_index); unsafe { Some(llvm::LLVMRustDIBuilderCreateEnumerator( DIB(cx), - name.as_ptr(), + name.as_ptr().cast(), + name.len(), // FIXME: what if enumeration has i128 discriminant? - variant_index.as_usize() as u64, + variant_index.as_usize() as i64, + false, // FIXME: IsUnsigned. )) } }) diff --git a/src/librustc_codegen_llvm/llvm/ffi.rs b/src/librustc_codegen_llvm/llvm/ffi.rs index f56647044e08b..8b796e0423b13 100644 --- a/src/librustc_codegen_llvm/llvm/ffi.rs +++ b/src/librustc_codegen_llvm/llvm/ffi.rs @@ -1776,7 +1776,9 @@ extern "C" { pub fn LLVMRustDIBuilderCreateEnumerator( Builder: &DIBuilder<'a>, Name: *const c_char, - Val: u64, + NameLen: size_t, + Value: i64, + IsUnsigned: bool, ) -> &'a DIEnumerator; pub fn LLVMRustDIBuilderCreateEnumerationType( diff --git a/src/rustllvm/RustWrapper.cpp b/src/rustllvm/RustWrapper.cpp index 49b6e1bfec38d..0e430d3881e60 100644 --- a/src/rustllvm/RustWrapper.cpp +++ b/src/rustllvm/RustWrapper.cpp @@ -891,10 +891,10 @@ extern "C" LLVMValueRef LLVMRustDIBuilderInsertDeclareAtEnd( unwrap(InsertAtEnd))); } -extern "C" LLVMMetadataRef -LLVMRustDIBuilderCreateEnumerator(LLVMRustDIBuilderRef Builder, - const char *Name, uint64_t Val) { - return wrap(Builder->createEnumerator(Name, Val)); +extern "C" LLVMMetadataRef LLVMRustDIBuilderCreateEnumerator( + LLVMRustDIBuilderRef Builder, const char *Name, size_t NameLen, + int64_t Value, bool IsUnsigned) { + return wrap(Builder->createEnumerator({Name, NameLen}, Value, IsUnsigned)); } extern "C" LLVMMetadataRef LLVMRustDIBuilderCreateEnumerationType( From ebd941b890e4731aed0ea1f76f056c8a6394f251 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Thu, 5 Mar 2020 00:00:00 +0000 Subject: [PATCH 2/3] debuginfo: Generators use u32 as discriminant type repr --- src/librustc_codegen_llvm/debuginfo/metadata.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/librustc_codegen_llvm/debuginfo/metadata.rs b/src/librustc_codegen_llvm/debuginfo/metadata.rs index 7beaf134e6ba1..095330a2e4b55 100644 --- a/src/librustc_codegen_llvm/debuginfo/metadata.rs +++ b/src/librustc_codegen_llvm/debuginfo/metadata.rs @@ -1802,9 +1802,9 @@ fn prepare_enum_metadata( DIB(cx), name.as_ptr().cast(), name.len(), - // FIXME: what if enumeration has i128 discriminant? - variant_index.as_usize() as i64, - false, // FIXME: IsUnsigned. + // Generators use u32 as discriminant type. + variant_index.as_u32().into(), + true, // IsUnsigned )) } }) From 30650f867bb0a94b3378942487e78f3eb7eb868f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Thu, 5 Mar 2020 00:00:00 +0000 Subject: [PATCH 3/3] debuginfo: Use is unsigned flag when emitting enumerators --- .../debuginfo/metadata.rs | 7 ++++- src/test/codegen/enum-discriminant-value.rs | 27 +++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) create mode 100644 src/test/codegen/enum-discriminant-value.rs diff --git a/src/librustc_codegen_llvm/debuginfo/metadata.rs b/src/librustc_codegen_llvm/debuginfo/metadata.rs index 095330a2e4b55..67529a82532ce 100644 --- a/src/librustc_codegen_llvm/debuginfo/metadata.rs +++ b/src/librustc_codegen_llvm/debuginfo/metadata.rs @@ -1780,6 +1780,11 @@ fn prepare_enum_metadata( .zip(&def.variants) .map(|((_, discr), v)| { let name = v.ident.as_str(); + let is_unsigned = match discr.ty.kind { + ty::Int(_) => false, + ty::Uint(_) => true, + _ => bug!("non integer discriminant"), + }; unsafe { Some(llvm::LLVMRustDIBuilderCreateEnumerator( DIB(cx), @@ -1787,7 +1792,7 @@ fn prepare_enum_metadata( name.len(), // FIXME: what if enumeration has i128 discriminant? discr.val as i64, - false, // FIXME: IsUnsigned. + is_unsigned, )) } }) diff --git a/src/test/codegen/enum-discriminant-value.rs b/src/test/codegen/enum-discriminant-value.rs new file mode 100644 index 0000000000000..f9da987765f9c --- /dev/null +++ b/src/test/codegen/enum-discriminant-value.rs @@ -0,0 +1,27 @@ +// Verify that DIEnumerator uses isUnsigned flag when appropriate. +// +// compile-flags: -g -C no-prepopulate-passes + +#[repr(i64)] +pub enum I64 { + I64Min = std::i64::MIN, + I64Max = std::i64::MAX, +} + +#[repr(u64)] +pub enum U64 { + U64Min = std::u64::MIN, + U64Max = std::u64::MAX, +} + +fn main() { + let _a = I64::I64Min; + let _b = I64::I64Max; + let _c = U64::U64Min; + let _d = U64::U64Max; +} + +// CHECK: !DIEnumerator(name: "I64Min", value: -9223372036854775808) +// CHECK: !DIEnumerator(name: "I64Max", value: 9223372036854775807) +// CHECK: !DIEnumerator(name: "U64Min", value: 0, isUnsigned: true) +// CHECK: !DIEnumerator(name: "U64Max", value: 18446744073709551615, isUnsigned: true)