Skip to content

Commit d02f7bf

Browse files
committed
[PATCH] tests: Add Rust basic testcase
Add Rust-lang abc test for rust supports. Signed-off-by: Michelle Jin <[email protected]> Co-authored-by: Paran Lee <[email protected]>
1 parent f962a2c commit d02f7bf

File tree

4 files changed

+149
-1
lines changed

4 files changed

+149
-1
lines changed

README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ Features
6565
uftrace traces each function in the executable and shows time durations.
6666

6767
Usually, for this to be possible, the program needs to be compiled with
68-
`-pg` or `-fpatchable-function-entry=5` (`=2` is enough on aarch64).
68+
`-pg` or `-fpatchable-function-entry=5` (`=2` is enough on aarch64 and riscv64).
6969
With full dynamic tracing (`-P.`|`--patch=.`), uftrace works on all executables (as
7070
long they are not stripped, or symbol information is available from a separate file).
7171

tests/r001_basic.py

+56
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
#!/usr/bin/env python
2+
3+
from runtest import RustTestBase
4+
5+
class TestCase(RustTestBase):
6+
def __init__(self):
7+
RustTestBase.__init__(self, 'abc', """
8+
# DURATION TID FUNCTION
9+
1.852 us [1008471] | getauxval();
10+
0.204 us [1008471] | getauxval();
11+
0.203 us [1008471] | getauxval();
12+
[1008471] | std::rt::lang_start() {
13+
14.260 us [1008471] | poll();
14+
5.056 us [1008471] | signal();
15+
2.759 us [1008471] | sigaction();
16+
2.426 us [1008471] | sigaction();
17+
2.537 us [1008471] | sigaction();
18+
2.722 us [1008471] | sigaltstack();
19+
0.408 us [1008471] | sysconf();
20+
13.907 us [1008471] | mmap64();
21+
0.260 us [1008471] | sysconf();
22+
26.444 us [1008471] | mprotect();
23+
0.296 us [1008471] | sysconf();
24+
2.019 us [1008471] | sigaltstack();
25+
0.185 us [1008471] | sysconf();
26+
0.278 us [1008471] | pthread_self();
27+
618.405 us [1008471] | pthread_getattr_np();
28+
0.389 us [1008471] | pthread_attr_getstack();
29+
0.371 us [1008471] | pthread_attr_destroy();
30+
0.166 us [1008471] | malloc();
31+
0.389 us [1008471] | malloc();
32+
4.241 us [1008471] | __cxa_thread_atexit_impl();
33+
[1008471] | std::rt::lang_start::_{{closure}}() {
34+
[1008471] | std::sys_common::backtrace::__rust_begin_short_backtrace() {
35+
[1008471] | core::ops::function::FnOnce::call_once() {
36+
[1008471] | s_abc::main() {
37+
[1008471] | s_abc::a() {
38+
[1008471] | s_abc::b() {
39+
[1008471] | s_abc::c() {
40+
2.389 us [1008471] | getpid();
41+
4.630 us [1008471] | } /* s_abc::c */
42+
5.148 us [1008471] | } /* s_abc::b */
43+
5.500 us [1008471] | } /* s_abc::a */
44+
5.889 us [1008471] | } /* s_abc::main */
45+
6.426 us [1008471] | } /* core::ops::function::FnOnce::call_once */
46+
6.908 us [1008471] | } /* std::sys_common::backtrace::__rust_begin_short_backtrace */
47+
0.111 us [1008471] | _<()>::report();
48+
8.037 us [1008471] | } /* std::rt::lang_start::_{{closure}} */
49+
2.408 us [1008471] | sigaltstack();
50+
0.259 us [1008471] | sysconf();
51+
0.167 us [1008471] | sysconf();
52+
41.648 us [1008471] | munmap();
53+
780.960 us [1008471] | } /* std::rt::lang_start */
54+
0.259 us [1008471] | free();
55+
0.166 us [1008471] | free();
56+
""")

tests/runtest.py

+74
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,8 @@ class TestBase:
6969
supported_lang = {
7070
'C': { 'cc': 'gcc', 'flags': 'CFLAGS', 'ext': '.c' },
7171
'C++': { 'cc': 'g++', 'flags': 'CXXFLAGS', 'ext': '.cpp' },
72+
# https://github.com/emosenkis/esp-rs/issues/10
73+
'Rust': { 'cc': 'rustc', 'flags': "+nightly -Z instrument-mcount", 'ext': '.rs' },
7274
}
7375

7476
TEST_SUCCESS = 0
@@ -573,6 +575,8 @@ def prerun(self, timeout):
573575
self.exearg = 't-' + self.name
574576
if self.lang == 'Python':
575577
self.exearg = TestBase.srcdir + '/tests/' + 's-' + self.name + '.py'
578+
elif self.lang == 'Rust':
579+
self.exearg = TestBase.srcdir + '/tests/' + 's-' + self.name
576580

577581
cmd = self.prepare()
578582
if cmd == '':
@@ -714,6 +718,22 @@ def __init__(self, name, result, lang='Python', cflags='', ldflags='', sort='sim
714718
if orig_path != "":
715719
os.environ["PYTHONPATH"] += ':' + orig_path
716720

721+
class RustTestBase(TestBase):
722+
def __init__(self, name, result, lang='Rust', cflags='', ldflags='', sort='simple', serial=False):
723+
TestBase.__init__(self, name, result, lang, cflags, ldflags, sort, serial)
724+
725+
def build(self, name, rflags='', ldflags=''):
726+
727+
prog = 's-' + name
728+
src = 's-' + name + ".rs"
729+
rflags = self.supported_lang['Rust']['flags']
730+
731+
build_cmd = '%s %s %s' % \
732+
('rustc', rflags, src)
733+
734+
self.pr_debug("build command: %s" % build_cmd)
735+
return self.build_it(build_cmd)
736+
717737
RED = '\033[1;31m'
718738
GREEN = '\033[1;32m'
719739
YELLOW = '\033[1;33m'
@@ -780,6 +800,19 @@ def run_python_case(T, case, timeout):
780800
ret = tc.postrun(ret)
781801
return (ret, dif)
782802

803+
def run_rust_case(T, case, timeout):
804+
tc = T.TestCase()
805+
tc.set_debug(arg.debug)
806+
tc.set_keep(arg.keep)
807+
808+
ret = tc.build(tc.name, "")
809+
ret = tc.prerun(timeout)
810+
dif = ''
811+
if ret == TestBase.TEST_SUCCESS:
812+
ret, dif = tc.run(case, "", arg.diff, timeout)
813+
ret = tc.postrun(ret)
814+
return (ret, dif)
815+
783816
def run_single_case(case, flags, opts, arg, compilers):
784817
result = []
785818
timeout = int(arg.timeout)
@@ -795,6 +828,11 @@ def run_single_case(case, flags, opts, arg, compilers):
795828
result.append((ret, dif))
796829
continue
797830

831+
if compiler == 'rustc':
832+
ret, dif = run_rust_case(T, case, timeout)
833+
result.append((ret, dif))
834+
continue
835+
798836
for flag in flags:
799837
for opt in opts:
800838
tc = T.TestCase()
@@ -910,6 +948,30 @@ def print_python_test_header(ftests):
910948
ftests.write(header2 + '\n')
911949
ftests.flush()
912950

951+
def print_rust_test_header(flags, ftests, compilers):
952+
header1 = '%-24s ' % 'Compiler'
953+
header2 = '%-24s ' % 'Runtime test case'
954+
header3 = '-' * 24 + ':'
955+
empty = ' ' * 100
956+
957+
for i, compiler in enumerate(compilers):
958+
if i != 0:
959+
header1 += ' '
960+
header2 += ' '
961+
header3 += ' '
962+
for flag in flags:
963+
# align with optimization flags
964+
header2 += ' ' + flag
965+
header1 += ' ' + compiler
966+
967+
print("")
968+
print(header1)
969+
print(header2)
970+
print(header3)
971+
ftests.write(header1 + '\n')
972+
ftests.write(header2 + '\n')
973+
ftests.write(header3 + '\n')
974+
ftests.flush()
913975

914976
def print_test_report(color, shared):
915977
success = shared.stats[TestBase.TEST_SUCCESS] + shared.stats[TestBase.TEST_SUCCESS_FIXED]
@@ -962,6 +1024,8 @@ def parse_argument():
9621024
help="Hide normal results and print only abnormal results.")
9631025
parser.add_argument("-P", "--python", dest='python', action='store_true',
9641026
help="Run python test cases instead")
1027+
parser.add_argument("-R", "--rust", dest='rust', action='store_true',
1028+
help="Run rust test cases instead")
9651029

9661030
return parser.parse_args()
9671031

@@ -976,6 +1040,8 @@ def parse_argument():
9761040
if arg.cases == 'all':
9771041
if arg.python:
9781042
testcases = glob.glob('p???_*.py')
1043+
elif arg.rust:
1044+
testcases = glob.glob('r???_*.py')
9791045
else:
9801046
testcases = glob.glob('t???_*.py')
9811047
else:
@@ -984,6 +1050,8 @@ def parse_argument():
9841050
for case in cases:
9851051
if arg.python:
9861052
testcases.extend(glob.glob('p*' + case + '*.py'))
1053+
elif arg.rust:
1054+
testcases.extend(glob.glob('r*' + case + '*.py'))
9871055
else:
9881056
testcases.extend(glob.glob('t*' + case + '*.py'))
9891057
arg.worker = min(arg.worker, len(testcases))
@@ -1000,6 +1068,7 @@ def parse_argument():
10001068
patch_size = {
10011069
'x86_64' : 5,
10021070
'aarch64' : 2,
1071+
'riscv' : 2,
10031072
}
10041073

10051074
m = os.uname()[-1] # machine
@@ -1029,6 +1098,9 @@ def has_compiler(compiler):
10291098
compilers = []
10301099
if arg.python:
10311100
compilers.append('python')
1101+
elif arg.rust:
1102+
if has_compiler('rustc') and os.system('rustup default nightly > /dev/null') == 0:
1103+
compilers.append('rustc')
10321104
elif arg.compiler == 'all':
10331105
for compiler in ['gcc', 'clang']:
10341106
if has_compiler(compiler):
@@ -1083,6 +1155,8 @@ class dotdict(dict):
10831155

10841156
if arg.python:
10851157
print_python_test_header(ftests)
1158+
elif arg.rust:
1159+
print_rust_test_header(flags, ftests, ['rustc'])
10861160
else:
10871161
print_test_header(opts, flags, ftests, compilers)
10881162

tests/s-abc.rs

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
use std::process;
2+
3+
fn a() -> u32 {
4+
return b();
5+
}
6+
7+
fn b() -> u32 {
8+
return c();
9+
}
10+
11+
fn c() -> u32 {
12+
return process::id();
13+
}
14+
15+
fn main() {
16+
// println!("Result: {}", a());
17+
a();
18+
}

0 commit comments

Comments
 (0)