[740] | 1 | #!/usr/bin/env python
|
---|
| 2 | # encoding: utf-8
|
---|
| 3 | # Thomas Nagy, 2008-2010 (ita)
|
---|
| 4 |
|
---|
| 5 | """
|
---|
| 6 | Execute the tasks with gcc -MD, read the dependencies from the .d file
|
---|
| 7 | and prepare the dependency calculation for the next run
|
---|
| 8 | """
|
---|
| 9 |
|
---|
| 10 | import os, re, threading
|
---|
| 11 | import Task, Logs, Utils, preproc
|
---|
| 12 | from TaskGen import before, after, feature
|
---|
| 13 |
|
---|
| 14 | lock = threading.Lock()
|
---|
| 15 |
|
---|
| 16 | preprocessor_flag = '-MD'
|
---|
| 17 |
|
---|
| 18 | @feature('cc')
|
---|
| 19 | @before('apply_core')
|
---|
| 20 | def add_mmd_cc(self):
|
---|
| 21 | if self.env.get_flat('CCFLAGS').find(preprocessor_flag) < 0:
|
---|
| 22 | self.env.append_value('CCFLAGS', preprocessor_flag)
|
---|
| 23 |
|
---|
| 24 | @feature('cxx')
|
---|
| 25 | @before('apply_core')
|
---|
| 26 | def add_mmd_cxx(self):
|
---|
| 27 | if self.env.get_flat('CXXFLAGS').find(preprocessor_flag) < 0:
|
---|
| 28 | self.env.append_value('CXXFLAGS', preprocessor_flag)
|
---|
| 29 |
|
---|
| 30 | def scan(self):
|
---|
| 31 | "the scanner does not do anything initially"
|
---|
| 32 | nodes = self.generator.bld.node_deps.get(self.unique_id(), [])
|
---|
| 33 | names = []
|
---|
| 34 | return (nodes, names)
|
---|
| 35 |
|
---|
| 36 | re_o = re.compile("\.o$")
|
---|
| 37 | re_src = re.compile("^(\.\.)[\\/](.*)$")
|
---|
| 38 |
|
---|
| 39 | def post_run(self):
|
---|
| 40 | # The following code is executed by threads, it is not safe, so a lock is needed...
|
---|
| 41 |
|
---|
| 42 | if getattr(self, 'cached', None):
|
---|
| 43 | return Task.Task.post_run(self)
|
---|
| 44 |
|
---|
| 45 | name = self.outputs[0].abspath(self.env)
|
---|
| 46 | name = re_o.sub('.d', name)
|
---|
| 47 | txt = Utils.readf(name)
|
---|
| 48 | #os.unlink(name)
|
---|
| 49 |
|
---|
| 50 | txt = txt.replace('\\\n', '')
|
---|
| 51 |
|
---|
| 52 | lst = txt.strip().split(':')
|
---|
| 53 | val = ":".join(lst[1:])
|
---|
| 54 | val = val.split()
|
---|
| 55 |
|
---|
| 56 | nodes = []
|
---|
| 57 | bld = self.generator.bld
|
---|
| 58 |
|
---|
| 59 | f = re.compile("^("+self.env.variant()+"|\.\.)[\\/](.*)$")
|
---|
| 60 | for x in val:
|
---|
| 61 | if os.path.isabs(x):
|
---|
| 62 |
|
---|
| 63 | if not preproc.go_absolute:
|
---|
| 64 | continue
|
---|
| 65 |
|
---|
| 66 | lock.acquire()
|
---|
| 67 | try:
|
---|
| 68 | node = bld.root.find_resource(x)
|
---|
| 69 | finally:
|
---|
| 70 | lock.release()
|
---|
| 71 | else:
|
---|
| 72 | g = re.search(re_src, x)
|
---|
| 73 | if g:
|
---|
| 74 | x = g.group(2)
|
---|
| 75 | lock.acquire()
|
---|
| 76 | try:
|
---|
| 77 | node = bld.bldnode.parent.find_resource(x)
|
---|
| 78 | finally:
|
---|
| 79 | lock.release()
|
---|
| 80 | else:
|
---|
| 81 | g = re.search(f, x)
|
---|
| 82 | if g:
|
---|
| 83 | x = g.group(2)
|
---|
| 84 | lock.acquire()
|
---|
| 85 | try:
|
---|
| 86 | node = bld.srcnode.find_resource(x)
|
---|
| 87 | finally:
|
---|
| 88 | lock.release()
|
---|
| 89 |
|
---|
| 90 | if id(node) == id(self.inputs[0]):
|
---|
| 91 | # ignore the source file, it is already in the dependencies
|
---|
| 92 | # this way, successful config tests may be retrieved from the cache
|
---|
| 93 | continue
|
---|
| 94 |
|
---|
| 95 | if not node:
|
---|
| 96 | raise ValueError('could not find %r for %r' % (x, self))
|
---|
| 97 | else:
|
---|
| 98 | nodes.append(node)
|
---|
| 99 |
|
---|
| 100 | Logs.debug('deps: real scanner for %s returned %s' % (str(self), str(nodes)))
|
---|
| 101 |
|
---|
| 102 | bld.node_deps[self.unique_id()] = nodes
|
---|
| 103 | bld.raw_deps[self.unique_id()] = []
|
---|
| 104 |
|
---|
| 105 | try:
|
---|
| 106 | del self.cache_sig
|
---|
| 107 | except:
|
---|
| 108 | pass
|
---|
| 109 |
|
---|
| 110 | Task.Task.post_run(self)
|
---|
| 111 |
|
---|
| 112 | import Constants, Utils
|
---|
| 113 | def sig_implicit_deps(self):
|
---|
| 114 | try:
|
---|
| 115 | return Task.Task.sig_implicit_deps(self)
|
---|
| 116 | except Utils.WafError:
|
---|
| 117 | return Constants.SIG_NIL
|
---|
| 118 |
|
---|
| 119 | for name in 'cc cxx'.split():
|
---|
| 120 | try:
|
---|
| 121 | cls = Task.TaskBase.classes[name]
|
---|
| 122 | except KeyError:
|
---|
| 123 | pass
|
---|
| 124 | else:
|
---|
| 125 | cls.post_run = post_run
|
---|
| 126 | cls.scan = scan
|
---|
| 127 | cls.sig_implicit_deps = sig_implicit_deps
|
---|
| 128 |
|
---|