diff options
Diffstat (limited to 'bitbake/lib/bb/build.py')
| -rw-r--r-- | bitbake/lib/bb/build.py | 208 |
1 files changed, 56 insertions, 152 deletions
diff --git a/bitbake/lib/bb/build.py b/bitbake/lib/bb/build.py index 1c015fe9a3..25c03a0a4e 100644 --- a/bitbake/lib/bb/build.py +++ b/bitbake/lib/bb/build.py | |||
| @@ -74,12 +74,21 @@ def exec_func(func, d, dirs = None): | |||
| 74 | if not body: | 74 | if not body: |
| 75 | return | 75 | return |
| 76 | 76 | ||
| 77 | cleandirs = (data.expand(data.getVarFlag(func, 'cleandirs', d), d) or "").split() | 77 | flags = data.getVarFlags(func, d) |
| 78 | for item in ['deps', 'check', 'interactive', 'python', 'cleandirs', 'dirs', 'lockfiles', 'fakeroot']: | ||
| 79 | if not item in flags: | ||
| 80 | flags[item] = None | ||
| 81 | |||
| 82 | ispython = flags['python'] | ||
| 83 | |||
| 84 | cleandirs = (data.expand(flags['cleandirs'], d) or "").split() | ||
| 78 | for cdir in cleandirs: | 85 | for cdir in cleandirs: |
| 79 | os.system("rm -rf %s" % cdir) | 86 | os.system("rm -rf %s" % cdir) |
| 80 | 87 | ||
| 81 | if not dirs: | 88 | if dirs: |
| 82 | dirs = (data.expand(data.getVarFlag(func, 'dirs', d), d) or "").split() | 89 | dirs = data.expand(dirs, d) |
| 90 | else: | ||
| 91 | dirs = (data.expand(flags['dirs'], d) or "").split() | ||
| 83 | for adir in dirs: | 92 | for adir in dirs: |
| 84 | mkdirhier(adir) | 93 | mkdirhier(adir) |
| 85 | 94 | ||
| @@ -88,24 +97,22 @@ def exec_func(func, d, dirs = None): | |||
| 88 | else: | 97 | else: |
| 89 | adir = data.getVar('B', d, 1) | 98 | adir = data.getVar('B', d, 1) |
| 90 | 99 | ||
| 91 | adir = data.expand(adir, d) | ||
| 92 | |||
| 93 | try: | 100 | try: |
| 94 | prevdir = os.getcwd() | 101 | prevdir = os.getcwd() |
| 95 | except OSError: | 102 | except OSError: |
| 96 | prevdir = data.expand('${TOPDIR}', d) | 103 | prevdir = data.getVar('TOPDIR', d, True) |
| 97 | if adir and os.access(adir, os.F_OK): | 104 | if adir and os.access(adir, os.F_OK): |
| 98 | os.chdir(adir) | 105 | os.chdir(adir) |
| 99 | 106 | ||
| 100 | locks = [] | 107 | locks = [] |
| 101 | lockfiles = (data.expand(data.getVarFlag(func, 'lockfiles', d), d) or "").split() | 108 | lockfiles = (data.expand(flags['lockfiles'], d) or "").split() |
| 102 | for lock in lockfiles: | 109 | for lock in lockfiles: |
| 103 | locks.append(bb.utils.lockfile(lock)) | 110 | locks.append(bb.utils.lockfile(lock)) |
| 104 | 111 | ||
| 105 | if data.getVarFlag(func, "python", d): | 112 | if flags['python']: |
| 106 | exec_func_python(func, d) | 113 | exec_func_python(func, d) |
| 107 | else: | 114 | else: |
| 108 | exec_func_shell(func, d) | 115 | exec_func_shell(func, d, flags) |
| 109 | 116 | ||
| 110 | for lock in locks: | 117 | for lock in locks: |
| 111 | bb.utils.unlockfile(lock) | 118 | bb.utils.unlockfile(lock) |
| @@ -117,19 +124,20 @@ def exec_func_python(func, d): | |||
| 117 | """Execute a python BB 'function'""" | 124 | """Execute a python BB 'function'""" |
| 118 | import re, os | 125 | import re, os |
| 119 | 126 | ||
| 127 | bbfile = bb.data.getVar('FILE', d, 1) | ||
| 120 | tmp = "def " + func + "():\n%s" % data.getVar(func, d) | 128 | tmp = "def " + func + "():\n%s" % data.getVar(func, d) |
| 121 | tmp += '\n' + func + '()' | 129 | tmp += '\n' + func + '()' |
| 122 | comp = utils.better_compile(tmp, func, bb.data.getVar('FILE', d, 1) ) | 130 | comp = utils.better_compile(tmp, func, bbfile) |
| 123 | prevdir = os.getcwd() | 131 | prevdir = os.getcwd() |
| 124 | g = {} # globals | 132 | g = {} # globals |
| 125 | g['bb'] = bb | 133 | g['bb'] = bb |
| 126 | g['os'] = os | 134 | g['os'] = os |
| 127 | g['d'] = d | 135 | g['d'] = d |
| 128 | utils.better_exec(comp,g,tmp, bb.data.getVar('FILE',d,1)) | 136 | utils.better_exec(comp, g, tmp, bbfile) |
| 129 | if os.path.exists(prevdir): | 137 | if os.path.exists(prevdir): |
| 130 | os.chdir(prevdir) | 138 | os.chdir(prevdir) |
| 131 | 139 | ||
| 132 | def exec_func_shell(func, d): | 140 | def exec_func_shell(func, d, flags): |
| 133 | """Execute a shell BB 'function' Returns true if execution was successful. | 141 | """Execute a shell BB 'function' Returns true if execution was successful. |
| 134 | 142 | ||
| 135 | For this, it creates a bash shell script in the tmp dectory, writes the local | 143 | For this, it creates a bash shell script in the tmp dectory, writes the local |
| @@ -141,9 +149,9 @@ def exec_func_shell(func, d): | |||
| 141 | """ | 149 | """ |
| 142 | import sys | 150 | import sys |
| 143 | 151 | ||
| 144 | deps = data.getVarFlag(func, 'deps', d) | 152 | deps = flags['deps'] |
| 145 | check = data.getVarFlag(func, 'check', d) | 153 | check = flags['check'] |
| 146 | interact = data.getVarFlag(func, 'interactive', d) | 154 | interact = flags['interactive'] |
| 147 | if check in globals(): | 155 | if check in globals(): |
| 148 | if globals()[check](func, deps): | 156 | if globals()[check](func, deps): |
| 149 | return | 157 | return |
| @@ -195,7 +203,7 @@ def exec_func_shell(func, d): | |||
| 195 | 203 | ||
| 196 | # execute function | 204 | # execute function |
| 197 | prevdir = os.getcwd() | 205 | prevdir = os.getcwd() |
| 198 | if data.getVarFlag(func, "fakeroot", d): | 206 | if flags['fakeroot']: |
| 199 | maybe_fakeroot = "PATH=\"%s\" fakeroot " % bb.data.getVar("PATH", d, 1) | 207 | maybe_fakeroot = "PATH=\"%s\" fakeroot " % bb.data.getVar("PATH", d, 1) |
| 200 | else: | 208 | else: |
| 201 | maybe_fakeroot = '' | 209 | maybe_fakeroot = '' |
| @@ -255,72 +263,29 @@ def exec_task(task, d): | |||
| 255 | a function is that a task exists in the task digraph, and therefore | 263 | a function is that a task exists in the task digraph, and therefore |
| 256 | has dependencies amongst other tasks.""" | 264 | has dependencies amongst other tasks.""" |
| 257 | 265 | ||
| 258 | # check if the task is in the graph.. | 266 | # Check whther this is a valid task |
| 259 | task_graph = data.getVar('_task_graph', d) | 267 | if not data.getVarFlag(task, 'task', d): |
| 260 | if not task_graph: | 268 | raise EventException("No such task", InvalidTask(task, d)) |
| 261 | task_graph = bb.digraph() | 269 | |
| 262 | data.setVar('_task_graph', task_graph, d) | 270 | try: |
| 263 | task_cache = data.getVar('_task_cache', d) | 271 | bb.msg.debug(1, bb.msg.domain.Build, "Executing task %s" % task) |
| 264 | if not task_cache: | 272 | old_overrides = data.getVar('OVERRIDES', d, 0) |
| 265 | task_cache = [] | 273 | localdata = data.createCopy(d) |
| 266 | data.setVar('_task_cache', task_cache, d) | 274 | data.setVar('OVERRIDES', 'task_%s:%s' % (task, old_overrides), localdata) |
| 267 | if not task_graph.hasnode(task): | 275 | data.update_data(localdata) |
| 268 | raise EventException("Missing node in task graph", InvalidTask(task, d)) | 276 | event.fire(TaskStarted(task, localdata)) |
| 269 | 277 | exec_func(task, localdata) | |
| 270 | # check whether this task needs executing.. | 278 | event.fire(TaskSucceeded(task, localdata)) |
| 271 | if stamp_is_current(task, d): | 279 | except FuncFailed, reason: |
| 272 | return 1 | 280 | bb.msg.note(1, bb.msg.domain.Build, "Task failed: %s" % reason ) |
| 273 | 281 | failedevent = TaskFailed(task, d) | |
| 274 | # follow digraph path up, then execute our way back down | 282 | event.fire(failedevent) |
| 275 | def execute(graph, item): | 283 | raise EventException("Function failed in task: %s" % reason, failedevent) |
| 276 | if data.getVarFlag(item, 'task', d): | ||
| 277 | if item in task_cache: | ||
| 278 | return 1 | ||
| 279 | |||
| 280 | if task != item: | ||
| 281 | # deeper than toplevel, exec w/ deps | ||
| 282 | exec_task(item, d) | ||
| 283 | return 1 | ||
| 284 | |||
| 285 | try: | ||
| 286 | bb.msg.debug(1, bb.msg.domain.Build, "Executing task %s" % item) | ||
| 287 | old_overrides = data.getVar('OVERRIDES', d, 0) | ||
| 288 | localdata = data.createCopy(d) | ||
| 289 | data.setVar('OVERRIDES', 'task_%s:%s' % (item, old_overrides), localdata) | ||
| 290 | data.update_data(localdata) | ||
| 291 | event.fire(TaskStarted(item, localdata)) | ||
| 292 | exec_func(item, localdata) | ||
| 293 | event.fire(TaskSucceeded(item, localdata)) | ||
| 294 | task_cache.append(item) | ||
| 295 | data.setVar('_task_cache', task_cache, d) | ||
| 296 | except FuncFailed, reason: | ||
| 297 | bb.msg.note(1, bb.msg.domain.Build, "Task failed: %s" % reason ) | ||
| 298 | failedevent = TaskFailed(item, d) | ||
| 299 | event.fire(failedevent) | ||
| 300 | raise EventException("Function failed in task: %s" % reason, failedevent) | ||
| 301 | |||
| 302 | if data.getVarFlag(task, 'dontrundeps', d): | ||
| 303 | execute(None, task) | ||
| 304 | else: | ||
| 305 | task_graph.walkdown(task, execute) | ||
| 306 | 284 | ||
| 307 | # make stamp, or cause event and raise exception | 285 | # make stamp, or cause event and raise exception |
| 308 | if not data.getVarFlag(task, 'nostamp', d) and not data.getVarFlag(task, 'selfstamp', d): | 286 | if not data.getVarFlag(task, 'nostamp', d) and not data.getVarFlag(task, 'selfstamp', d): |
| 309 | make_stamp(task, d) | 287 | make_stamp(task, d) |
| 310 | 288 | ||
| 311 | def extract_stamp_data(d, fn): | ||
| 312 | """ | ||
| 313 | Extracts stamp data from d which is either a data dictonary (fn unset) | ||
| 314 | or a dataCache entry (fn set). | ||
| 315 | """ | ||
| 316 | if fn: | ||
| 317 | return (d.task_queues[fn], d.stamp[fn], d.task_deps[fn]) | ||
| 318 | task_graph = data.getVar('_task_graph', d) | ||
| 319 | if not task_graph: | ||
| 320 | task_graph = bb.digraph() | ||
| 321 | data.setVar('_task_graph', task_graph, d) | ||
| 322 | return (task_graph, data.getVar('STAMP', d, 1), None) | ||
| 323 | |||
| 324 | def extract_stamp(d, fn): | 289 | def extract_stamp(d, fn): |
| 325 | """ | 290 | """ |
| 326 | Extracts stamp format which is either a data dictonary (fn unset) | 291 | Extracts stamp format which is either a data dictonary (fn unset) |
| @@ -330,49 +295,6 @@ def extract_stamp(d, fn): | |||
| 330 | return d.stamp[fn] | 295 | return d.stamp[fn] |
| 331 | return data.getVar('STAMP', d, 1) | 296 | return data.getVar('STAMP', d, 1) |
| 332 | 297 | ||
| 333 | def stamp_is_current(task, d, file_name = None, checkdeps = 1): | ||
| 334 | """ | ||
| 335 | Check status of a given task's stamp. | ||
| 336 | Returns 0 if it is not current and needs updating. | ||
| 337 | (d can be a data dict or dataCache) | ||
| 338 | """ | ||
| 339 | |||
| 340 | (task_graph, stampfn, taskdep) = extract_stamp_data(d, file_name) | ||
| 341 | |||
| 342 | if not stampfn: | ||
| 343 | return 0 | ||
| 344 | |||
| 345 | stampfile = "%s.%s" % (stampfn, task) | ||
| 346 | if not os.access(stampfile, os.F_OK): | ||
| 347 | return 0 | ||
| 348 | |||
| 349 | if checkdeps == 0: | ||
| 350 | return 1 | ||
| 351 | |||
| 352 | import stat | ||
| 353 | tasktime = os.stat(stampfile)[stat.ST_MTIME] | ||
| 354 | |||
| 355 | _deps = [] | ||
| 356 | def checkStamp(graph, task): | ||
| 357 | # check for existance | ||
| 358 | if file_name: | ||
| 359 | if 'nostamp' in taskdep and task in taskdep['nostamp']: | ||
| 360 | return 1 | ||
| 361 | else: | ||
| 362 | if data.getVarFlag(task, 'nostamp', d): | ||
| 363 | return 1 | ||
| 364 | |||
| 365 | if not stamp_is_current(task, d, file_name, 0 ): | ||
| 366 | return 0 | ||
| 367 | |||
| 368 | depfile = "%s.%s" % (stampfn, task) | ||
| 369 | deptime = os.stat(depfile)[stat.ST_MTIME] | ||
| 370 | if deptime > tasktime: | ||
| 371 | return 0 | ||
| 372 | return 1 | ||
| 373 | |||
| 374 | return task_graph.walkdown(task, checkStamp) | ||
| 375 | |||
| 376 | def stamp_internal(task, d, file_name): | 298 | def stamp_internal(task, d, file_name): |
| 377 | """ | 299 | """ |
| 378 | Internal stamp helper function | 300 | Internal stamp helper function |
| @@ -409,40 +331,39 @@ def del_stamp(task, d, file_name = None): | |||
| 409 | stamp_internal(task, d, file_name) | 331 | stamp_internal(task, d, file_name) |
| 410 | 332 | ||
| 411 | def add_tasks(tasklist, d): | 333 | def add_tasks(tasklist, d): |
| 412 | task_graph = data.getVar('_task_graph', d) | ||
| 413 | task_deps = data.getVar('_task_deps', d) | 334 | task_deps = data.getVar('_task_deps', d) |
| 414 | if not task_graph: | ||
| 415 | task_graph = bb.digraph() | ||
| 416 | if not task_deps: | 335 | if not task_deps: |
| 417 | task_deps = {} | 336 | task_deps = {} |
| 337 | if not 'tasks' in task_deps: | ||
| 338 | task_deps['tasks'] = [] | ||
| 339 | if not 'parents' in task_deps: | ||
| 340 | task_deps['parents'] = {} | ||
| 418 | 341 | ||
| 419 | for task in tasklist: | 342 | for task in tasklist: |
| 420 | deps = tasklist[task] | ||
| 421 | task = data.expand(task, d) | 343 | task = data.expand(task, d) |
| 422 | |||
| 423 | data.setVarFlag(task, 'task', 1, d) | 344 | data.setVarFlag(task, 'task', 1, d) |
| 424 | task_graph.addnode(task, None) | 345 | |
| 425 | for dep in deps: | 346 | if not task in task_deps['tasks']: |
| 426 | dep = data.expand(dep, d) | 347 | task_deps['tasks'].append(task) |
| 427 | if not task_graph.hasnode(dep): | ||
| 428 | task_graph.addnode(dep, None) | ||
| 429 | task_graph.addnode(task, dep) | ||
| 430 | 348 | ||
| 431 | flags = data.getVarFlags(task, d) | 349 | flags = data.getVarFlags(task, d) |
| 432 | def getTask(name): | 350 | def getTask(name): |
| 351 | if not name in task_deps: | ||
| 352 | task_deps[name] = {} | ||
| 433 | if name in flags: | 353 | if name in flags: |
| 434 | deptask = data.expand(flags[name], d) | 354 | deptask = data.expand(flags[name], d) |
| 435 | if not name in task_deps: | ||
| 436 | task_deps[name] = {} | ||
| 437 | task_deps[name][task] = deptask | 355 | task_deps[name][task] = deptask |
| 438 | getTask('depends') | 356 | getTask('depends') |
| 439 | getTask('deptask') | 357 | getTask('deptask') |
| 440 | getTask('rdeptask') | 358 | getTask('rdeptask') |
| 441 | getTask('recrdeptask') | 359 | getTask('recrdeptask') |
| 442 | getTask('nostamp') | 360 | getTask('nostamp') |
| 361 | task_deps['parents'][task] = [] | ||
| 362 | for dep in flags['deps']: | ||
| 363 | dep = data.expand(dep, d) | ||
| 364 | task_deps['parents'][task].append(dep) | ||
| 443 | 365 | ||
| 444 | # don't assume holding a reference | 366 | # don't assume holding a reference |
| 445 | data.setVar('_task_graph', task_graph, d) | ||
| 446 | data.setVar('_task_deps', task_deps, d) | 367 | data.setVar('_task_deps', task_deps, d) |
| 447 | 368 | ||
| 448 | def remove_task(task, kill, d): | 369 | def remove_task(task, kill, d): |
| @@ -450,22 +371,5 @@ def remove_task(task, kill, d): | |||
| 450 | 371 | ||
| 451 | If kill is 1, also remove tasks that depend on this task.""" | 372 | If kill is 1, also remove tasks that depend on this task.""" |
| 452 | 373 | ||
| 453 | task_graph = data.getVar('_task_graph', d) | ||
| 454 | if not task_graph: | ||
| 455 | task_graph = bb.digraph() | ||
| 456 | if not task_graph.hasnode(task): | ||
| 457 | return | ||
| 458 | |||
| 459 | data.delVarFlag(task, 'task', d) | 374 | data.delVarFlag(task, 'task', d) |
| 460 | ref = 1 | 375 | |
| 461 | if kill == 1: | ||
| 462 | ref = 2 | ||
| 463 | task_graph.delnode(task, ref) | ||
| 464 | data.setVar('_task_graph', task_graph, d) | ||
| 465 | |||
| 466 | def task_exists(task, d): | ||
| 467 | task_graph = data.getVar('_task_graph', d) | ||
| 468 | if not task_graph: | ||
| 469 | task_graph = bb.digraph() | ||
| 470 | data.setVar('_task_graph', task_graph, d) | ||
| 471 | return task_graph.hasnode(task) | ||
