Search code examples
scons

Override an SCons builder


I want to do some post-processing on all .o files (e.g. those generated by the Object or StaticObject Builders), no matter what Builder is used by the user.

I'm trying to "override" or "hook" the base environment's builders like so, but I can't come up with anything that works:

old = env['BUILDERS']['StaticObject']
env['BUILDERS']['StaticObject'] = something_that_calls(old)

Is there a prescribed way to hook or override something like the StaticObject builder?

I've seen the question about a Nested SCons Builder, but it doesn't tell me how to replace an existing builder, only supplementing its behavior.


Solution

  • I don't know if there is a blessed way to replace a Builder, but I think you're on the right track. The following (admittedly trivial) example works for me:

    def wrap_builder(bld):    
        return Builder(action = [bld.action, 'echo $TARGET'],
                       suffix = bld.suffix,
                       src_suffix = bld.src_suffix)
    
    obj_bld = env['BUILDERS']['Object']
    env['BUILDERS']['Object'] = wrap_builder(obj_bld)
    
    env.Program('test', ['test.c'])
    

    with output:

    scons: Reading SConscript files ...
    scons: done reading SConscript files.
    scons: Building targets ...
    gcc -o test.o -c -std=c99 test.c
    echo test.o
    test.o
    gcc -o test test.o
    scons: done building targets.
    

    As you can see, the additional (echo) action is performed after building the object file.