translate-c misstranslates #define based floating-point constants:
// input.h
#define BROKEN 3.1415
zig translate-c input.h | grep BROKEN > output.zig
// output.zig
pub const BROKEN = -nan;
Zig Version: 0.5.0+26c8930b9
So I am seeing this bug in the version I get from my package manager (snap), but I am not seeing the bug with a local build, even with the same exact sha as the one I get from snap.
I am seeing a related bug where long double constants are getting truncated (because we parse them as double), but I suspect that's a different issue, especially in the case of 3.1415.
@kavika13 does the snap version come with its own LLVM/clang libs?
I cannot replicate this on 5d82744f1
@dimenus the packaging scripts for the snap version are here: https://github.com/jayschwa/snapcraft-zig
I don't know without investigating what the snap build system has inside it or what it references, but snap packages are supposed to be "system independent" and the zig binary it distributes is statically linked and returns nothing when running lld on it.
But yeah. This doesn't repro on any recent local build for me either.
Edit: See the snap package issue where I referenced this issue, just below this post.
Edit2: The version in snap is apparently basically the one from the download page. The one from the download page repros the problem on my system, too: https://ziglang.org/download/ - I'm on Pop!_OS 19.10 (which is more or less basically Ubuntu 19.10), in case that's relevant.
@kavika13 one difference is the build mode. The default build mode when building from source is Debug, but the download pages use -DCMAKE_BUILD_TYPE=Release.
You can see how the CI service builds here: https://github.com/ziglang/zig/tree/master/ci and here: https://github.com/ziglang/zig/wiki (all the "how to build xyz from source")
cd ~/dev/zig
mkdir build-release
cd build-release
cmake .. -DCMAKE_BUILD_TYPE=Release
make -j8 install
cd ~/tmp/zig-3838-repro
~/dev/zig/build/bin/zig translate-c input.h | grep BROKEN
pub const BROKEN = 3.141500;
Still not reproing on a local Release build for me. Maybe something weird is up with the CI environment? I will see if I can repro the rest of the toolchain environment (since that script is longer than just cmake .. -DCMAKE_BUILD_TYPE=Release) and see if I can find out more that way.
If it is an issue with LLVM/Clang, then one possible explanation could be that your distro has it patched but the CI is using the 9.0.0 release tarball.
It's also possible that the code in question is invoking undefined behavior. In which case running with a tool like Valgrind could be helpful.
It's also possible that the code in question is invoking undefined behavior. In which case running with a tool like Valgrind could be helpful.
I tried valgrind (with no flags) on my local build with this .h file. Nothing super notable. Some leaks, but that's not important.
I tried it on the downloaded build, and got errors galore. Thousands of them. Stuff like:
Conditional jump or move depends on uninitialised value(s)
Use of uninitialised value of size 8
md5-1e161aa61eec9bad90ecc2f97615d420
==9700== Conditional jump or move depends on uninitialised value(s)
==9700== at 0x52258F4: mal0_clear (malloc.c:346)
==9700== by 0x52258F4: calloc (malloc.c:364)
==9700== by 0x51451ED: llvm::StringMapImpl::RehashTable(unsigned int) (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x50EACA7: (anonymous namespace)::CommandLineParser::addOption(llvm::cl::Option*, llvm::cl::SubCommand*) (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x50EC08E: llvm::cl::Option::addArgument() (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x86EC15: __static_initialization_and_destruction_0(int, int) [clone .constprop.0] (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x5224108: libc_start_init (__libc_start_main.c:64)
==9700== by 0x522412D: libc_start_main_stage2 (__libc_start_main.c:91)
==9700== by 0x8F0F0C: ??? (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x2: ???
==9700== by 0x1FFF000116: ???
==9700== by 0x1FFF000152: ???
==9700== by 0x1FFF00015E: ???
==9700== Uninitialised value was created
==9700== at 0x5232C5B: __expand_heap (expand_heap.c:57)
==9700== by 0x52255C7: expand_heap (malloc.c:140)
==9700== by 0x52255C7: malloc (malloc.c:306)
==9700== by 0x522589D: calloc (malloc.c:358)
==9700== by 0x51451ED: llvm::StringMapImpl::RehashTable(unsigned int) (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x50EACA7: (anonymous namespace)::CommandLineParser::addOption(llvm::cl::Option*, llvm::cl::SubCommand*) (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x50EC08E: llvm::cl::Option::addArgument() (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x86EC15: __static_initialization_and_destruction_0(int, int) [clone .constprop.0] (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x5224108: libc_start_init (__libc_start_main.c:64)
==9700== by 0x522412D: libc_start_main_stage2 (__libc_start_main.c:91)
==9700== by 0x8F0F0C: ??? (in /home/<my username>Downloads/zig-linux-x86_64-0.5.0+5874cb04b/zig)
==9700== by 0x2: ???
==9700== by 0x1FFF000116: ???
All the errors I am seeing are sourced in memory that comes out of __expand_heap.
Not sure if this is spurious errors, or if there is something wrong with the CRT implementation on the CI environment?
FYI I tried the Windows versions from CI (5.0, master) and those don't exhibit the problem.
I tried a local release build, and a build with all-debug sources (including building llvm and clang from source), and those also didn't repro the problem on Windows.
This seems like it might just be a Linux issue. I will try building clang/llvm from source on Linux and post an update.
This cannot happen in self-hosted translate-c.
I have verified this is no longer happening in the current CI build on the same Linux distro I was trying before.
Other stuff is broken:
pub const __INTMAX_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINTMAX_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __PTRDIFF_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INTPTR_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __SIZE_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __WINT_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __CHAR16_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __CHAR32_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINTPTR_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT16_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT32_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT_LEAST8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_LEAST8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_LEAST16_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_LEAST32_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT_LEAST64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_LEAST64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT_FAST8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_FAST8_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_FAST16_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_FAST32_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __INT_FAST64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
pub const __UINT_FAST64_TYPE__ = @compileError("unable to translate C expr: unexpected token Id.Identifier");
but BROKEN isn't broken ;)
pub const BROKEN = 3.1415;
I think this issue can be closed now.