[Scons-users] Handling of dependencies using Scanner()

Marc Joliet marcec at gmx.de
Sat Oct 12 10:45:47 EDT 2013


Am Sat, 12 Oct 2013 11:04:11 +0100
schrieb Henry Gomersall <heng at cantab.net>:


> On 11/10/13 22:30, Marc Joliet wrote:

> >> I assumed that the scanner would automatically handle a new node that

> >> >was added to the dependency tree if the suffix agreed with what the

> >> >scanner already had - apparently not. Can someone confirm this?

> > I think you overlooked the "recursive" option to the Scanner(). From the man

> > page:

> >

> > "recursive

> > An optional flag that specifies whether this scanner should be re-invoked on

> > the dependency files returned by the scanner. When this flag is not set, the

> > Node subsystem will only invoke the scanner on the file being scanned, and

> > not (for example) also on the files specified by the #include lines in the

> > file being scanned. recursive may be a callable function, in which case it

> > will be called with a list of Nodes found and should return a list of Nodes

> > that should be scanned recursively; this can be used to select a specific

> > subset of Nodes for additional scanning."

> >

> > HTH

> Thanks it does - I hadn't seen that.


You're welcome.


> Does it offer resilience to infinite recursion? My cursory perusal of

> Scanner would suggest the logic isn't in there, but I'm happy to assume

> that SCons takes care of it at another level.


I was originally going to say "I don't know" (and wait for an SCons dev to
reply), but then I decided to check the SCons sources and found this, in
SCons/Node/__init__.py:

def get_implicit_deps(self, env, scanner, path):
"""Return a list of implicit dependencies for this node.

This method exists to handle recursive invocation of the scanner
on the implicit dependencies returned by the scanner, if the
scanner's recursive flag says that we should.
"""
if not scanner:
return []

# Give the scanner a chance to select a more specific scanner
# for this Node.
#scanner = scanner.select(self)

nodes = [self]
seen = {}
seen[self] = 1
deps = []
while nodes:
n = nodes.pop(0)
d = [x for x in n.get_found_includes(env, scanner, path) if x not in seen]
if d:
deps.extend(d)
for n in d:
seen[n] = 1
nodes.extend(scanner.recurse_nodes(d))

return deps

It appears that the Node keeps track of which scanner results it has already
seen and skips them if they appear again.

So yeah, SCons does take care of it at another level :) .

In fact, I tried it out with a tiny C test project with two headers that
include each other, and SCons handled it just fine.


> Cheers,

>

> Henry


Cheers
--
Marc Joliet
--
"People who think they know everything really annoy those of us who know we
don't" - Bjarne Stroustrup
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 198 bytes
Desc: not available
Url : http://four.pairlist.net/pipermail/scons-users/attachments/20131012/c94bd077/attachment-0001.pgp


More information about the Scons-users mailing list