Permalink
Cannot retrieve contributors at this time
Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign up
Fetching contributors…
| #!/usr/bin/env python | |
| # Script to check the assembly generated | |
| import os | |
| import os.path | |
| from subprocess import Popen, PIPE | |
| import argparse | |
| asm_dir = './asm' | |
| files = set() | |
| verbose = False | |
| def arm_triplet(arch) : | |
| triples = { 'armv7' : 'armv7-unknown-linux-gnueabihf', | |
| 'armv8' : 'aarch64-unknown-linux-gnu' } | |
| return triples[arch] | |
| class File(object): | |
| def __init__(self, path_rs): | |
| self.path_rs = path_rs | |
| self.path_asm_should = os.path.join(os.path.splitext(path_rs)[0] + ".asm") | |
| self.path_asm_output = os.path.join(os.path.splitext(path_rs)[0] + "_output.asm") | |
| self.path_llvmir_output = os.path.join(os.path.splitext(path_rs)[0] + "_ir.ll") | |
| self.name = os.path.splitext(os.path.basename(path_rs))[0] | |
| self.feature = self.name.split("_")[1] | |
| self.arch = self.name.split("_")[0] | |
| if self.feature == "none": | |
| self.feature = None | |
| def __str__(self): | |
| return "name: " + self.name + ", path-rs: " + self.path_rs + ", path-asm: " + self.path_asm_should + ', arch: ' + self.arch + ", feature: " + str(self.feature) | |
| def __hash__(self): | |
| return hash(self.name) | |
| def find_files(): | |
| for dirpath, dirnames, filenames in os.walk(asm_dir): | |
| for filename in [f for f in filenames if f.endswith(".rs")]: | |
| files.add(File(os.path.join(dirpath, filename))) | |
| def call(args): | |
| if verbose: | |
| print "command: " + str(args) | |
| p = Popen(args, stdin=PIPE, stdout=PIPE, stderr=PIPE, shell=True) | |
| output, err = p.communicate(b"input data that is passed to subprocess' stdin") | |
| rc = p.returncode | |
| if verbose: | |
| print output | |
| print err | |
| def compile_file(file): | |
| if verbose: | |
| print "Checking: " + str(file) + "..." | |
| cargo_args = 'cargo rustc --verbose --release --features unstable -- -C panic=abort -C codegen-units=1 -C lto=fat ' | |
| if file.feature: | |
| cargo_args = cargo_args + '-C target-feature=+{}'.format(file.feature) | |
| if file.arch == 'armv7' or file.arch == 'armv8': | |
| cargo_args = cargo_args + '--target={}'.format(arm_triplet(file.arch)) | |
| call(str(cargo_args)) | |
| rustc_args = 'rustc --verbose -C opt-level=3 -C codegen-units=1 -C lto=fat -C panic="abort" --cfg \'feature="unstable"\' --extern bitintr=target/release/libbitintr.rlib --crate-type lib'; | |
| if file.feature: | |
| rustc_args = rustc_args + ' -C target-feature=+{}'.format(file.feature) | |
| if file.arch == 'armv7' or file.arch == 'armv8': | |
| rustc_args = rustc_args + ' --target={}'.format(arm_triplet(file.arch)) | |
| rustc_args_asm = rustc_args + ' --emit asm {} -o {}'.format(file.path_rs, file.path_asm_output) | |
| call(rustc_args_asm) | |
| rustc_args_ll = rustc_args + ' --emit llvm-ir {} -o {}'.format(file.path_rs, file.path_llvmir_output) | |
| call(rustc_args_ll) | |
| if verbose: | |
| print "...done!" | |
| def diff_files(rustc_output, asm_snippet): | |
| with open(rustc_output, 'r') as rustc_output_file: | |
| rustc_output_lines = rustc_output_file.readlines() | |
| with open(asm_snippet, 'r') as asm_snippet_file: | |
| asm_snippet_lines = asm_snippet_file.readlines() | |
| # remove all empty lines and lines starting with "." | |
| rustc_output_lines = [l.strip() for l in rustc_output_lines] | |
| rustc_output_lines = [l for l in rustc_output_lines if not l.startswith(".") and not len(l) == 0] | |
| asm_snippet_lines = [l.strip() for l in asm_snippet_lines] | |
| asm_snippet_lines = [l for l in asm_snippet_lines if not l.startswith(".") and not len(l) == 0] | |
| results_differ = False | |
| if len(rustc_output_lines) != len(asm_snippet_lines): | |
| results_differ = True | |
| for line_is, line_should in zip(rustc_output_lines, asm_snippet_lines): | |
| if line_is != line_should: | |
| results_differ = True | |
| if results_differ: | |
| print "Error: results differ" | |
| print "Is:" | |
| print rustc_output_lines | |
| print "Should:" | |
| print asm_snippet_lines | |
| return False | |
| return True | |
| def check_file(file): | |
| compile_file(file) | |
| return diff_files(file.path_asm_output, file.path_asm_should) | |
| def main(): | |
| parser = argparse.ArgumentParser(description='Checks ASM code') | |
| parser.add_argument('-verbose', action="store_true", default=False) | |
| results = parser.parse_args() | |
| global verbose | |
| if results.verbose: | |
| verbose = True | |
| find_files() | |
| if verbose: | |
| for f in files: | |
| print f | |
| error = False | |
| for f in files: | |
| result = check_file(f) | |
| if not result: | |
| error = True | |
| if error == True: | |
| exit(1) | |
| else: | |
| exit(0) | |
| if __name__ == "__main__": | |
| main() |