slight refactor

This commit is contained in:
Dominic Höglinger 2022-11-21 16:57:41 +01:00
parent aad9547029
commit 210a40e4fa
3 changed files with 84 additions and 71 deletions

View File

@ -1,16 +1,11 @@
from __future__ import print_function
import argparse
import sys
import re
from pycparser import parse_file, c_ast, CParser
import graphviz as gv
from modelbuilder import *
func_table = {}
enum_table = {}
assign_table = []
state_enums = []
from utils import *
class FuncDefVisitor(c_ast.NodeVisitor):
def __init__(self):
@ -58,14 +53,19 @@ class EnumDefVisitor(c_ast.NodeVisitor):
def __init__(self, name):
super().__init__()
self._name = name
self.enums = {}
def visit_Enum(self, node):
enum_table[self._name] = node
self.enums[self._name] = node
class EnumTypedefVisitor(c_ast.NodeVisitor):
def __init__(self):
self.enums = {}
class TypedefVisitor(c_ast.NodeVisitor):
def visit_Typedef(self, node):
ev = EnumDefVisitor(node.name)
ev.visit(node)
self.enums = {**self.enums, **ev.enums}
class EnumVisitor(c_ast.NodeVisitor):
@ -76,45 +76,6 @@ class EnumVisitor(c_ast.NodeVisitor):
def visit_Enumerator(self, node):
self.enum_names.append(node.name)
def find_longest_path(paths):
ms = 0
mp = None
for path in paths:
s = len(path)
if s > ms:
ms = s
mp = path
return mp
def find_shortest_path(paths):
ms = float('inf')
mp = None
for path in paths:
s = len(path)
if s < ms:
ms = s
mp = path
return mp
def find_common_ancestor(paths):
shortest_path = find_shortest_path(paths)
last_common = None
for gen_i,_ in enumerate(shortest_path):
common = True
last_node = paths[0][gen_i]
for path in paths:
if last_node == path[gen_i]:
common = True
last_node = path[gen_i]
else:
common = False
if common:
last_common = last_node
return last_common
class SwitchCaseTermVisitor(c_ast.NodeVisitor):
def __init__(self, asm_node):
super().__init__()
@ -160,7 +121,6 @@ class SwitchCaseCodePropertyVisitor(c_ast.NodeVisitor):
self._sas = state_asmts
self.properties = []
def visit_Case(self, node):
label = node.children()[0][1]
block = node
@ -169,27 +129,11 @@ class SwitchCaseCodePropertyVisitor(c_ast.NodeVisitor):
scpv.visit(block)
self.properties += scpv.properties
def comment_remover(text):
def replacer(match):
s = match.group(0)
if s.startswith('/'):
return ""
else:
return s
pattern = re.compile(
r'//.*?$|/\*.*?\*/|\'(?:\\.|[^\\\'])*\'|"(?:\\.|[^\\"])*"',
re.DOTALL | re.MULTILINE
)
return re.sub(pattern, replacer, text)
if __name__ == "__main__":
argparser = argparse.ArgumentParser('Create a Kripke Structure Model from C Code')
argparser.add_argument('filename',
nargs='?',
help='name of file to parse')
argparser.add_argument('--coord', help='show coordinates in the dump',
action='store_true')
argparser.add_argument('--func', help='process function')
argparser.add_argument('--enum', help='state enum')
argparser.add_argument('--initial', help='initial state')
@ -207,12 +151,18 @@ if __name__ == "__main__":
ast = parser.parse(comment_remover(source))
#ast = parse_file(args.filename, use_cpp=False)
assign_table = []
state_enums = []
func_table = {}
enum_table = {}
fdv = FuncDefVisitor()
fdv.visit(ast)
func_table = fdv.func_table
enumvis = TypedefVisitor()
enumvis.visit(ast)
etv = EnumTypedefVisitor()
etv.visit(ast)
enum_table = etv.enums
state_asmts = []
@ -297,7 +247,6 @@ if __name__ == "__main__":
print("-------------------")
print(nusmv)
if args.dot is not None:
g = gv.Digraph('G')

11
test.c
View File

@ -17,7 +17,14 @@ typedef struct
bool m_b;
} testfsm_t;
void process(testfsm_t *p_fsm, const bool input)
typedef struct
{
bool m_i;
bool m_oa;
bool m_ob
} testfsm_pd_t;
void process_internal(testfsm_t *p_fsm, const bool input)
{
testfsm_state_t nextState = p_fsm->m_state;
@ -56,6 +63,8 @@ void process(testfsm_t *p_fsm, const bool input)
p_fsm->m_state = nextState;
}
void process_outputs(testfsm_t *p_fsm, const bool input
bool randbool(int throws)
{
bool stillTrue = true;

55
utils.py Normal file
View File

@ -0,0 +1,55 @@
import re
def find_longest_path(paths):
ms = 0
mp = None
for path in paths:
s = len(path)
if s > ms:
ms = s
mp = path
return mp
def find_shortest_path(paths):
ms = float('inf')
mp = None
for path in paths:
s = len(path)
if s < ms:
ms = s
mp = path
return mp
def find_common_ancestor(paths):
if len(paths) == 0:
return None
shortest_path = find_shortest_path(paths)
last_common = None
for gen_i,_ in enumerate(shortest_path):
common = True
last_node = paths[0][gen_i]
for path in paths:
if last_node == path[gen_i]:
common = True
last_node = path[gen_i]
else:
common = False
if common:
last_common = last_node
return last_common
def comment_remover(text):
def replacer(match):
s = match.group(0)
if s.startswith('/'):
return ""
else:
return s
pattern = re.compile(
r'//.*?$|/\*.*?\*/|\'(?:\\.|[^\\\'])*\'|"(?:\\.|[^\\"])*"',
re.DOTALL | re.MULTILINE
)
return re.sub(pattern, replacer, text)