[Scons-users] Modifying the provided environment in an emitter?

Bill Deegan bill at baddogconsulting.com
Mon Apr 24 13:07:15 EDT 2017


Marc,

Why not use a Value() node as the source for your symlink builder?

-Bill


On Mon, Apr 24, 2017 at 8:38 AM, Marc Branchaud <marcnarc at xiplink.com>
wrote:

> On 2017-04-21 05:29 PM, Andrew C. Morrow wrote:
>
>>
>> Hi all -
>>
>> Is it legit to modify the passed in env in an emitter?
>>
>
> I dunno about "legit" but we do this all the time when we want to pass
> info calculated in the emitter to the builder.
>
> Here's a simple example:  One of the things we build is a complete OS
> image in a variant subdir (which we then bundle into a tarball).  The OS
> image contains symlinks to absolute paths, which are legitimate when the
> image is written onto a root partition, but which are "dead" (the symlink's
> source doesn't exist) when they are in the image's variant subdir.
>
> So we have a SymLink Builder that lets us create these symlinks:
>
>         SymLink(target="name/of/symlink/in/os/image",
>                 source="/absolute/path/of/symlink/source")
>
> Since the Builder's source isn't an actual file, the emitter sets the
> source to None, so that SCons ignores it.  But we need to save that source
> path to create the actual symlink, so we store it in a dict in the
> environment.  The dict is keyed by the target's variant-dependent absolute
> path.  (This emitter also works with non-absolute-path symlink sources, by
> stripping the path that SCons prepends to such things.)
>
>         def emitter(target, source, env):
>             if '__SymLinkSources' not in env.Dictionary():
>                 env['__SymLinkSources'] = {}
>             # The source of a symlink is just an arbitrary
>             # string, but SCons thinks it's a file and so
>             # prepends it with the path to the SConscript
>             # that uses the SymLink builder.  Undo this.
>             path = env.Dir('.').srcnode().abspath
>             src = str(source[0])
>             if src.startswith(path):
>                 src = src[len(path)+1:]
>             env['__SymLinkSources'][target[0].abspath] = src
>             return (target, None)
>
> Then the builder simply extracts the source path from the dict:
>
>         def builder(target, source, env):
>             # SCons can't tell the difference between a
>             # symlink that points to an non-existent file
>             # and a symlink that doesn't even exist.
>             # So we need to be smart here, because we
>             # might be asked to re-create a symlink that's
>             # already there.
>             tgt = target[0].abspath
>             if os.path.lexists(tgt):
>                 # If the target already exists, just remove it.
>                 os.unlink(tgt)
>             os.symlink(env['__SymLinkSources'][tgt], tgt)
>
> Several of our Builders do this sort of thing.  Works great!
>
>                 M.
>
>
>     def add_lib_foo_emitter(target, source, env):
>>         libs = env.get('LIBS', [])
>>         libs.append('foo')
>>         env['LIBS'] = libs
>>         return (target, source)
>>
>>     def add_emitter(builder):
>>         base_emitter = builder.emitter
>>         new_emitter = SCons.Builder.ListEmitter([add_lib_foo_emitter,
>> base_emitter])
>>         builder.emitter = new_emitter
>>
>>     target_builders = ['Program', 'SharedLibrary', 'LoadableModule',
>> 'StaticLibrary']
>>     for builder in target_builders:
>>         add_emitter(env['BUILDERS'][builder])
>>
>> I've found myself wanting to do this with increasing frequency, but am
>> unclear on whether this is acceptable. It appears to work, but the
>> documentation doesn't seem to offer any clear guidance that I've found
>> on whether it is guaranteed to work. If so (which would be great!), am I
>> guaranteed that the modification of env is scoped only to the passed in
>> targets?
>>
>> Thanks,
>> Andrew
>>
>>
>>
>> _______________________________________________
>> Scons-users mailing list
>> Scons-users at scons.org
>> https://pairlist4.pair.net/mailman/listinfo/scons-users
>>
>> _______________________________________________
> Scons-users mailing list
> Scons-users at scons.org
> https://pairlist4.pair.net/mailman/listinfo/scons-users
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://pairlist4.pair.net/pipermail/scons-users/attachments/20170424/cb00f7b1/attachment.html>


More information about the Scons-users mailing list