
On Sat, Feb 01, 2020 at 11:36:19AM +0100, Merijn Verstraaten wrote:
On 1 Feb 2020, at 10:01, Viktor Dukhovni
wrote: The package developer. Neither GHC nor Clang are at-fault for invalid CPP macro syntax.
This isn't the package developers fault. Standard Haskell just cannot be properly preprocessed by an ISO C preprocessor. As the definition of valid tokens just aren't compatible.
Well, my take was the package developer using "CPP" is expected to produce CPP-compatible input. But if Haskell is expected to provide a more liberal dialect of CPP, then indeed perhaps the issue is with the Haskell build using Clang's CPP.
GHC's use of the CPP has long (maybe since forever?) been incompatible with CPP as standardised in the ISO C spec, and its relies on the -traditional flag to make GCC use it's pre-ISO C implementations. This flag isn't necessarily portable across C compilers and I recall this breaking things in the past.
Indeed the -traditional flag shows the difference, only GCC's "cpp" tolerates the C-incompatible tokens, Clang does not. $ for cpp in gcc{7,8,9} clang{37,39,60,70}; do printf "--- CPP: %s\n" "$cpp"; printf "#define foo a' = b\nfoo\n" | $cpp -traditional -Werror -E - 2>&1; printf "EXIT: $?\n"; done | egrep -v '^# [0-9]|^$' --- CPP: gcc7 a' = b EXIT: 0 --- CPP: gcc8 a' = b EXIT: 0 --- CPP: gcc9 a' = b EXIT: 0 --- CPP: clang37 <stdin>:1:14: error: missing terminating ' character [-Werror,-Winvalid-pp-token] #define foo a' = b ^ a' = b 1 error generated. EXIT: 1 --- CPP: clang39 <stdin>:1:14: error: missing terminating ' character [-Werror,-Winvalid-pp-token] #define foo a' = b ^ a' = b 1 error generated. EXIT: 1 --- CPP: clang60 <stdin>:1:14: error: missing terminating ' character [-Werror,-Winvalid-pp-token] #define foo a' = b ^ a' = b 1 error generated. EXIT: 1 --- CPP: clang70 <stdin>:1:14: error: missing terminating ' character [-Werror,-Winvalid-pp-token] #define foo a' = b ^ a' = b 1 error generated. EXIT: 1 My own build of GHC for FreeBSD has settings: [("GCC extra via C opts", " -fwrapv -fno-builtin"), ("C compiler command", "gcc"), ("C compiler flags", ""), ("C compiler link flags", " -fuse-ld=lld"), ("C compiler supports -no-pie", "YES"), ("Haskell CPP command","gcc"), ("Haskell CPP flags","-E -undef -traditional"), ... ] It seems that the ports system elects clang, leading to the reported issue. I see that FreeBSD ports also include: hs-cpphs-1.20.8_7 Liberalised re-implementation of cpp, the C pre-processor Which means that either hs-cpphs needs to be a pre-requisite (built by the boostrap GHC compiler?), a co-requisite (assuming GHC itself does not break with clang's CPP), or the configuration needs be tweaked to use "gcc" as the Haskell CPP preprocessor, even when clang is the compiler. -- Viktor.