From 5e3327e456714d84b1cabdd698e7aad07e9ea7d4 Mon Sep 17 00:00:00 2001 From: Peter Wu Date: Fri, 2 Dec 2011 09:10:46 +0000 Subject: Support automatic processing through cpp --- README | 19 +++++++++++++++++-- pp2cc.py | 42 +++++++++++++++++++++++++++--------------- 2 files changed, 44 insertions(+), 17 deletions(-) diff --git a/README b/README index 08fa293..3d3a774 100644 --- a/README +++ b/README @@ -8,6 +8,9 @@ Dependencies: - pycparser - http://code.google.com/p/pycparser/ - PLY (Python Lex-Yacc) - http://www.dabeaz.com/ply/ +Recommended: +- cpp - a C preprocessor + Python is often installed by default on Linux distributions. For Windows, you probably need to run the installer from the above link. Extract the pycparser ZIP file (see link above) and copy the pycparser subdirectory to the directory @@ -16,7 +19,15 @@ the ply/ directory into the directory containing pp2cc. pp2cc is a console program, you need to open a terminal (or cmd on Windows) to see compiler messages. -Usage: python pp2cc.py [options] filename.. +The cpp program is installed on most Linux distributions. If not, install a +conforming cpp, say gcc (GNU C Compiler). On Windows, you might want to +download mcpp from http://mcpp.sourceforge.net/. Put it in your %PATH% (or the +directory containing pp2cc) and rename it to "cpp.exe". If you do not install +a C preprocessor, you need to pass the --no-cpp option in order to skip the +processing through cpp. You will not be able to use comments or macros in this +case. + +Usage: pp2cc.py [options] filename.. Multiple input files can be specified, options can be specified before and after filenames. Options: @@ -25,6 +36,10 @@ Options: added. --tree Instead of compiling the file into assembly, show the parse tree. + -D name + -D name=definition This option is passed to the cpp program, and acts like + adding #define name or #define name definition respectively + --no-cpp Disable the use of the C Preprocessor Conformance with the K&R interpretation of C and feature support ================================================================ @@ -118,4 +133,4 @@ Not supported by parser, use a dedicated preprocessor like cpp and enable removal of comments. Example: cpp -P file.c A13 Grammar -Not checked \ No newline at end of file +Not checked diff --git a/pp2cc.py b/pp2cc.py index c50bff2..a76cb7f 100755 --- a/pp2cc.py +++ b/pp2cc.py @@ -11,7 +11,7 @@ this license. """ import sys, re, os, operator -from pycparser import c_parser, c_ast +from pycparser import c_parser, c_ast, parse_file from Asm import Asm from Registers import Registers from LinkedNode import LinkedNode @@ -45,7 +45,6 @@ class Logger(object): class Parse(object): def __init__(self): - self.parser = c_parser.CParser() self.logger = Logger() self.node = None @@ -90,12 +89,9 @@ class Parse(object): self.asm = Asm() # watches which registers are used and which are not self.registers = Registers() - def loadFile(self, filename): + def loadFile(self, filename, use_cpp=True, cpp_args=[]): """Loads a file and parses the contents of it""" - file = open(filename, 'r') - source = file.read() - file.close() - self.node = self.parser.parse(source, filename=filename); + self.node = parse_file(filename, use_cpp=use_cpp, cpp_args=cpp_args); def show(self): self.node.show(showcoord=True) def uniqLbl(self, labelname): @@ -1274,7 +1270,9 @@ if __name__ == "__main__": settings = { "input_files": [], "dump_parsed_files": False, - "output_filename": "" + "output_filename": "", + "cpp_args": [], + "use_cpp": True } set_arg = None @@ -1282,7 +1280,7 @@ if __name__ == "__main__": class ArgumentError(Exception): pass def usage(): - print """Usage: python pp2cc.py [options] filename.. + print """Usage: pp2cc.py [options] filename.. Multiple input files can be specified, options can be specified before and after filenames. Options: @@ -1290,7 +1288,12 @@ Options: input file from which the extension is removed, and .asm is added. --tree Instead of compiling the file into assembly, show the parse - tree.""" + tree. + -D name + -D name=definition This option is passed to the cpp program, and acts like + adding #define name or #define name definition respectively + --no-cpp Disable the use of the C Preprocessor + """ try: for arg in sys.argv[1:]: if not set_arg is None: @@ -1298,10 +1301,13 @@ Options: setting = settings[set_arg] if isinstance(setting, str): settings[set_arg] = arg - elif isinstance(arg, list): - settings.append(arg) - elif isinstance(arg, bool): + elif isinstance(setting, list): + setting.append(arg) + elif isinstance(setting, bool): raise NotImplementedError("Booleans cannot be set in options") + else: + raise ArgumentError("Invalid type for command line setting" + " '{}'".format(type(setting).__name__)) set_arg = None elif len(arg): # if the argument is an option @@ -1310,6 +1316,11 @@ Options: set_arg = "output_filename" elif arg == "--tree": settings["dump_parsed_files"] = True + elif arg == "-D": + settings["cpp_args"].append("-D") + set_arg = "cpp_args" + elif arg == "--no-cpp": + settings["use_cpp"] = False elif arg == "-h" or arg == "--help" or arg == "--usage": usage() sys.exit(0) @@ -1335,7 +1346,8 @@ Options: parse = Parse() for filename in settings["input_files"]: - parse.loadFile(filename) + parse.loadFile(filename, use_cpp=settings["use_cpp"], + cpp_args=settings["cpp_args"]) if settings["dump_parsed_files"]: parse.show() else: @@ -1350,5 +1362,5 @@ Options: print "The output is written to", settings["output_filename"] except c_parser.ParseError: e = sys.exc_info()[1] - print "Parse error:", str(e) + print "A fatal (syntax) error was found during parsing:", str(e) sys.exit(1) -- cgit v1.2.1