Skip to content

Commit

Permalink
[build] Generate ninja.sh for test actions
Browse files Browse the repository at this point in the history
This is like to build.ninja, but it doesn't write files.

TODO: the function names are kind of long.  So it would be nice to set
up autocomplete.

[soil] Fix to account for new ninja _test/ structure
  • Loading branch information
Andy C committed Jun 28, 2022
1 parent df2fa29 commit e671fc9
Show file tree
Hide file tree
Showing 5 changed files with 109 additions and 20 deletions.
5 changes: 4 additions & 1 deletion .gitignore
Expand Up @@ -14,8 +14,11 @@ _release/
_test/
_tmp/
!opy/_regtest/src/_devbuild/
*.ninja

build.ninja
ninja.sh
.ninja_*

fanos.so
fastlex.so
libc.so
Expand Down
87 changes: 84 additions & 3 deletions build/NINJA_config.py
Expand Up @@ -124,7 +124,7 @@ def log(msg, *args):
BUILD_NINJA = 'build.ninja'


def NinjaGraph(n):
def NinjaGraph(n, u):

n.comment('Build oil-native')
n.comment('Generated by %s.' % __file__)
Expand Down Expand Up @@ -341,6 +341,74 @@ def ShellFunctions(f, argv0):
''', file =f)


class UnitTestWriter(object):

def __init__(self, f):
self.f = f
self.func_names = []

def comment(self, s):
self.f.write('# %s\n' % s)

def newline(self):
self.f.write('\n')

def unit_test(self, func_name, ninja_target):
"""
Args:
name: function name in u.sh
ninja_target: the file that should be built first, and then run
"""
self.f.write("""\
%s() {
ninja %s
run-test %s
}
""" % (func_name, ninja_target, ninja_target))

self.func_names.append(func_name)

def header(self):
self.f.write("""
#!/usr/bin/env bash
#
# Generated by %s
set -o errexit
set -o nounset
set -o pipefail
run-test() {
echo ' ---'
echo " $0 running $@"
echo ' ---'
"$@"
}
""" % __file__)

def footer(self):
all_lines = '\n'.join(self.func_names)

self.f.write("""\
list() {
### list tests to run
echo '
%s
'
}
all-serial() {
%s
}
""" % (all_lines, all_lines))

self.f.write("""\
"$@"
""")


def main(argv):
try:
action = argv[1]
Expand All @@ -349,15 +417,28 @@ def main(argv):

if action == 'ninja':
n = ninja_syntax.Writer(open(BUILD_NINJA, 'w'))
NinjaGraph(n)

NINJA_SH = 'ninja.sh'

u_file = open(NINJA_SH, 'w')
u = UnitTestWriter(u_file)
u.header()

NinjaGraph(n, u)

n.newline()
n.newline()

mycpp_subgraph.NinjaGraph(n)
mycpp_subgraph.NinjaGraph(n, u)

u.footer()

u_file.close()
os.chmod(NINJA_SH, 0o755)

log('%s: Wrote %s', argv[0], BUILD_NINJA)


elif action == 'shell':
out = '_build/oil-native.sh'
with open(out, 'w') as f:
Expand Down
33 changes: 19 additions & 14 deletions mycpp/NINJA_subgraph.py
Expand Up @@ -148,14 +148,13 @@ def ShouldSkipBenchmark(name):
RUNTIME = ['mycpp/my_runtime.cc', 'mycpp/mylib2.cc', 'mycpp/gc_heap.cc']

UNIT_TESTS = {
'mylib_test': ['mycpp/mylib.cc'],
'gc_heap_test': ['mycpp/gc_heap.cc'],
'gc_stress_test': RUNTIME,
'my_runtime_test': RUNTIME,
'mylib2_test': RUNTIME,
'mycpp/mylib_test': ['mycpp/mylib.cc'],
'mycpp/gc_heap_test': ['mycpp/gc_heap.cc'],
'mycpp/gc_stress_test': RUNTIME,
'mycpp/my_runtime_test': RUNTIME,
'mycpp/mylib2_test': RUNTIME,

# lives in demo/target_lang.cc
'target_lang': ['cpp/dumb_alloc.cc', 'mycpp/gc_heap.cc'],
'mycpp/demo/target_lang': ['cpp/dumb_alloc.cc', 'mycpp/gc_heap.cc'],

# there is also demo/{gc_heap,square_heap}.cc
}
Expand All @@ -172,12 +171,15 @@ def ShouldSkipBenchmark(name):
'parse': ['_test/asdl/expr_asdl.gc.cc', 'asdl/runtime.gc.cc'],
}

def NinjaGraph(n):
def NinjaGraph(n, u):

n.comment('Translate, compile, and test mycpp examples.')
n.comment('Generated by %s.' % __name__)
n.newline()

u.comment('Build and run mycpp unit tests')
u.newline()

n.rule('touch',
command='touch $out',
description='touch $out')
Expand Down Expand Up @@ -252,17 +254,17 @@ def NinjaGraph(n):
# Build and run unit tests
#

for test_name in sorted(UNIT_TESTS):
cc_files = UNIT_TESTS[test_name]
for test_path in sorted(UNIT_TESTS):
cc_files = UNIT_TESTS[test_path]

# assume names are unique
test_name = os.path.basename(test_path)

# TODO: doesn't run under pure 'asan' because of -D GC_DEBUG, etc.
for variant in ['gc_debug']: # , 'asan', 'opt']:
b = '_test/bin/unit/%s.%s' % (test_name, variant)

if test_name == 'target_lang': # SPECIAL CASE
main_cc = 'mycpp/demo/target_lang.cc'
else:
main_cc = 'mycpp/%s.cc' % test_name
main_cc = '%s.cc' % test_path

n.build([b], 'compile', [main_cc] + cc_files,
variables=[('variant', variant), ('more_cxx_flags', "''")])
Expand All @@ -276,6 +278,9 @@ def NinjaGraph(n):

phony['mycpp-unit'].append(task_out)

u.unit_test('%s.%s' % (test_path.replace('/', '-'), variant), b)
u.newline()

#
# ASDL schema that examples/parse.py depends on
#
Expand Down
2 changes: 1 addition & 1 deletion soil/web-remote.sh
Expand Up @@ -200,7 +200,7 @@ make-job-wwz() {
zip -r $wwz \
index.html _tmp/soil _tmp/spec _tmp/stateful \
_tmp/syscall _tmp/benchmark-data _tmp/metrics \
mycpp/_test/*.{html,txt,tsv} mycpp/_test/{tasks,gen} \
_test/*.{html,txt,tsv} _test/{tasks,gen} \
web/{base,spec-code,spec-tests,spec-cpp,line-counts}.css web/ajax.js \
web/table/table-sort.{css,js} \
_release/oil.tar _release/VERSION/doc
Expand Down
2 changes: 1 addition & 1 deletion soil/web.py
Expand Up @@ -2,7 +2,7 @@
"""
soil/web.py
Each job assigned an ID. THe job generates:
Each job is assigned an ID. The job generates:
- $ID.json # metadata
- $ID.tsv # benchmarks/time.py output. Success/failure for each task.
Expand Down

0 comments on commit e671fc9

Please sign in to comment.