waf vs enrionment CPPFLAGS and LDFLAGS

Ralph Böhme rb at sernet.de
Mon Oct 27 11:25:28 MDT 2014


Hi all,

I think I've come across a behaviour in waf which I'd consider a bug [1]:

when building the C compiler invocation for compiling or linking, waf
places the environment varialbles CPPFLAGS and LDFLAGS *before* all
internal flags computed at the configuration stage.

The templates come from buildtools/wafadmin/Tools/cc.py:

cc_str = '${CC} ${CCFLAGS} ${CPPFLAGS} ${_CCINCFLAGS} ${_CCDEFFLAGS} ${CC_SRC_F}${SRC} ${CC_TGT_F}${TGT}'
link_str = '${LINK_CC} ${CCLNK_SRC_F}${SRC} ${CCLNK_TGT_F}${TGT[0].abspath(env)} ${LINKFLAGS}'

As a result, a Samba build will erroneously pick up headers or
libraries from the paths specified in the environment variables, no
matter what the waf build script intention is.

This manifested in a broken build of Samba 4.1.12 with Macport on OS
X. Macports passed CPPFLAGS=-I/some/path to waf configure where in
/some/path happened to exist GSSAPI headers. The internal heimdal
build then picked up those headers instead of the internal copies,
because -I/some/path was put infront of the internal include.

Note that this is NOT specifically related to our GSSAPI/Heimdal
build, it's a general waf bug. The immediate fix is:

<http://git.samba.org/?p=slow/samba.git;a=commitdiff;h=2429a9f65c0da893c5e843fa52568a913b388bfc>

I have a testcase in my waf branch:
<http://git.samba.org/?p=slow/samba.git;a=shortlog;h=refs/heads/waf>

Regardless of environment variables the compiled binary should output:

$ /bin/app
foo: INTERNAL
in mylib
$

But without the top commit, if configured with

  CPPFLAGS=-I/foo/bar/include LDFLAGS="-L/foo/bar/lib -Wl,-rpath,/foo/bar/lib"

(after extracting attached and compiling attached archive too /foo/bar)

the output is

foo: EXTERNAL
in extlib

which means the build picked up the header from /foo/bar/include
instead of the internal version and the library from /foo/bar/lib.

The same project structure when implemented with automake doesn't
exhibit this problem, because automake gets the ordering right [2].

Fwiw, this bug is still present in upstream waf.

I wasn't able to come up with a proper fix that doesn't directly modify
wafadmin/* stuff, I'd highly appreciate if a better Python hacker then
I am could take a look. :)

Thoughts?
-Ralph

[1] <https://bugzilla.samba.org/show_bug.cgi?id=10877>
[2] <http://www.gnu.org/software/automake/manual/html_node/Flag-Variables-Ordering.html>
    "Automake always uses two of these variables when compiling C
    sources files. When compiling an object file for the mumble
    target, the first variable will be mumble_CPPFLAGS if it is
    defined, or AM_CPPFLAGS otherwise. The second variable is always
    CPPFLAGS."
-------------- next part --------------
A non-text attachment was scrubbed...
Name: foobar_mylib.tgz
Type: application/gzip
Size: 529 bytes
Desc: not available
URL: <http://lists.samba.org/pipermail/samba-technical/attachments/20141027/49f5cf9e/attachment.bin>


More information about the samba-technical mailing list