Major refactoring milestone: actions are now inherited by module_pool

parent 57ddf6de
......@@ -92,17 +92,11 @@ def main():
# logging.info("To see some help, type hdlmake --help")
# sys.exit("Exiting")
_action_runner(modules_pool)
def _action_runner(modules_pool):
from .action import (CheckCondition, CleanModules, FetchModules, ListFiles,
ListModules, MergeCores, Tree, GenerateSimulationMakefile,
GenerateSynthesisMakefile, GenerateRemoteSynthesisMakefile, GenerateSynthesisProject,
QsysHwTclUpdate,)
# #
# DECODE THE COMMANDS/ACTIONS HERE #
......@@ -126,67 +120,37 @@ def _action_runner(modules_pool):
"Otherwise hdlmake doesn't know how to handle the project.")
quit()
if top_mod.action == "simulation":
if not top_mod.manifest_dict["sim_tool"]:
logging.error("`sim_tool' manifest variable has to be specified. "
"Otherwise hdlmake doesn't know how to simulate the project.")
quit()
top_mod.top_entity = top_mod.manifest_dict["sim_top"]
action = [
GenerateSimulationMakefile,
]
modules_pool.simulation_makefile()
elif top_mod.action == "synthesis":
if not top_mod.manifest_dict["syn_tool"]:
logging.error("`syn_tool' manifest variable has to be specified. "
"Otherwise hdlmake doesn't know how to synthesize the project.")
quit()
top_mod.top_entity = top_mod.manifest_dict["syn_top"]
action = [
GenerateSynthesisProject,
GenerateSynthesisMakefile,
GenerateRemoteSynthesisMakefile
]
modules_pool.synthesis_project()
modules_pool.synthesis_makefile()
modules_pool.remote_synthesis()
elif top_mod.action == "qsys_hw_tcl_update":
if not top_mod.manifest_dict["hw_tcl_filename"]:
logging.error("'hw_tcl_filename' manifest variable has to be specified. "
"Otherwise hdlmake doesn't know which file to update.")
quit()
action = [
QsysHwTclUpdate,
]
modules_pool.qsys_hw_tcl_update()
elif options.command == "make-simulation":
action = [ GenerateSimulationMakefile ]
modules_pool.simulation_makefile()
elif options.command == "make-synthesis":
action = [ GenerateSynthesisMakefile ]
modules_pool.synthesis_makefile()
elif options.command == "make-remote":
action = [ GenerateRemoteSynthesisMakefile ]
modules_pool.remote_synthesis()
elif options.command == "fetch":
action = [ FetchModules ]
modules_pool.fetch()
elif options.command == "clean":
action = [ CleanModules ]
modules_pool.clean()
elif options.command == "list-mods":
action = [ ListModules ]
modules_pool.list_modules()
elif options.command == "list-files":
action = [ ListFiles ]
modules_pool.list_files()
elif options.command == "merge-cores":
action = [ MergeCores ]
modules_pool.merge_cores()
elif options.command == "project":
action = [ GenerateSynthesisProject ]
modules_pool.synthesis_project()
elif options.command == "tree":
action = [ Tree ]
# #
# EXECUTE THE COMMAND SEQUENCE #
# #
try:
for command in action:
action_instance = command(modules_pool)
action_instance.run()
except Exception as e:
import traceback
logging.error(e)
print("Trace:")
traceback.print_exc()
sys.exit("Exiting in failure because exception occurred.")
modules_pool.generate_tree()
def _get_parser():
......
......@@ -23,36 +23,13 @@ import sys
import logging
class Action(object):
def __init__(self, modules_pool):
self.modules_pool = modules_pool
self.env = modules_pool.env
self._check_manifest()
self._check_env()
self._check_options()
@property
def top_module(self):
return self.modules_pool.get_top_module()
def _check_manifest(self):
pass
def _check_env(self):
pass
def _check_options(self):
pass
def run(self):
raise NotImplementedError()
def _check_all_fetched_or_quit(self):
pool = self.modules_pool
if not pool.is_everything_fetched():
if not self.is_everything_fetched():
logging.error("At least one module remains unfetched. "
"Fetching must be done before makefile generation.")
print("\nUnfetched modules:")
print('\n'.join([str(m) for m in self.modules_pool if not m.isfetched]))
print('\n'.join([str(m) for m in self if not m.isfetched]))
sys.exit("\nExiting.")
def _check_manifest_variable_is_set(self, name):
......
......@@ -42,7 +42,7 @@ class CheckCondition(Action):
else:
sys.exit(1)
def run(self):
def check_condition(self):
tool = self.env.options.tool
if tool == "ise":
ver = self.env["ise_version"]
......
......@@ -29,7 +29,7 @@ class CheckManifest(Action):
if not self.env.options.top:
logging.info("--top is not specified. Current manifest will be treated as the top manifest")
def run(self):
def check_manifest(self):
###
### THIS IS JUST A STUB
###
......
......@@ -24,9 +24,9 @@ import hdlmake.fetch as fetch
from .action import Action
class CleanModules(Action):
def run(self):
def clean(self):
logging.info("Removing fetched modules..")
remove_list = [m for m in self.modules_pool if m.source in [fetch.GIT, fetch.SVN] and m.isfetched]
remove_list = [m for m in self if m.source in [fetch.GIT, fetch.SVN] and m.isfetched]
remove_list.reverse() # we will remove modules in backward order
if len(remove_list):
for m in remove_list:
......
......@@ -28,10 +28,10 @@ from .action import Action
class FetchModules(Action):
def run(self):
top_module = self.modules_pool.get_top_module()
def fetch(self):
top_module = self.get_top_module()
logging.info("Fetching needed modules.")
os.system(top_module.manifest_dict["fetch_pre_cmd"])
self.modules_pool.fetch_all()
self.fetch_all()
os.system(top_module.manifest_dict["fetch_post_cmd"])
logging.info("All modules fetched.")
......@@ -24,11 +24,11 @@ import logging
import hdlmake.new_dep_solver as dep_solver
class ListFiles(Action):
def run(self):
unfetched_modules = [m for m in self.modules_pool if not m.isfetched]
def list_files(self):
unfetched_modules = [m for m in self if not m.isfetched]
for m in unfetched_modules:
logging.warning("List incomplete, module %s has not been fetched!", m)
file_set = self.modules_pool.build_file_set()
file_set = self.build_file_set()
file_list = dep_solver.make_dependency_sorted_list(file_set)
files_str = [f.path for f in file_list]
if self.env.options.delimiter == None:
......
......@@ -41,9 +41,9 @@ def _convert_to_source_name(source_code):
class ListModules(Action):
def run(self):
def list_modules(self):
terse = self.env.options.terse
for m in self.modules_pool:
for m in self:
if not m.isfetched:
logging.warning("Module not fetched: %s" % m.url)
if not terse: print("# MODULE UNFETCHED! -> %s" % m.url)
......@@ -51,8 +51,6 @@ class ListModules(Action):
if not terse: print("# MODULE START -> %s" % m.url)
if m.source in [fetch.SVN, fetch.GIT]:
if not terse: print("# * URL: "+m.url)
elif m.source == fetch.GITSUBMODULE:
if not terse: print("# * This is a submodule of: %s" % m.parent.url)
if m.source in [fetch.SVN, fetch.GIT, fetch.LOCAL] and m.parent:
if not terse: print("# * The parent for this module is: %s" % m.parent.url)
else:
......
......@@ -33,20 +33,18 @@ from .action import Action
class MergeCores(Action):
def _check_manifest(self):
self._check_manifest_variable_is_equal_to("action", "synthesis")
def _check_options(self):
def _check_merge_cores(self):
self._check_manifest_variable_is_equal_to("action", "synthesis")
if not self.env.options.dest:
logging.error("--dest must be given for merge-cores")
sys.exit("Exiting")
def run(self):
pool = self.modules_pool
def merge_cores(self):
self._check_all_fetched_or_quit()
self._check_merge_cores()
logging.info("Merging all cores into one source file per language.")
flist = pool.build_file_set()
flist = self.build_file_set()
base = self.env.options.dest
f_out = open(base+".vhd", "w")
......
......@@ -27,8 +27,8 @@ import logging
class QsysHwTclUpdate(Action):
def run(self):
file_set = self.modules_pool.build_file_set()
def qsys_hw_tcl_update(self):
file_set = self.build_file_set(self.get_top_module().manifest_dict["syn_top"])
file_list = dep_solver.make_dependency_sorted_list(file_set)
files_str = [os.path.relpath(f.path) for f in file_list]
......@@ -41,7 +41,7 @@ class QsysHwTclUpdate(Action):
file_tcl[-1] += " TOP_LEVEL_FILE"
file_tcl.append("\n")
hw_tcl_filename = self.modules_pool.get_top_module().manifest_dict["hw_tcl_filename"]
hw_tcl_filename = self.get_top_module().manifest_dict["hw_tcl_filename"]
infile = open(hw_tcl_filename,"r")
inserted = True
......
......@@ -32,7 +32,7 @@ from .action import Action
class GenerateRemoteSynthesisMakefile(Action):
def _check_manifest(self):
def _check_remote_synthesis(self):
if not self.top_module.action == "synthesis":
logging.error("action must be equal to \"synthesis\"")
sys.exit("Exiting")
......@@ -42,23 +42,24 @@ class GenerateRemoteSynthesisMakefile(Action):
sys.exit("Exiting")
def run(self):
def remote_synthesis(self):
self._check_all_fetched_or_quit()
self._check_remote_synthesis()
self._generate_remote_synthesis_makefile()
def _generate_remote_synthesis_makefile(self):
tool_name = self.modules_pool.get_top_module().manifest_dict["syn_tool"]
tool_name = self.get_top_module().manifest_dict["syn_tool"]
tool_module = importlib.import_module("hdlmake.tools.%s.%s" % (tool_name, tool_name))
tool_object = tool_module.ToolControls()
logging.info("Generating makefile for remote synthesis.")
top_mod = self.modules_pool.get_top_module()
top_mod = self.get_top_module()
self.env.check_remote_tool(tool_object)
self.env.check_general()
files = self.modules_pool.build_file_set()
files = self.build_file_set(self.get_top_module().manifest_dict["syn_top"])
sff = SourceFileFactory()
files.add(sff.new(top_mod.manifest_dict["syn_project"], module=self.top_module))
......
......@@ -35,25 +35,21 @@ from .action import Action
class GenerateSimulationMakefile(Action):
"""This class contains the simulation specific methods"""
def _check_manifest(self):
def _check_simulation_makefile(self):
"""Check if the simulation keys are provided by the top manifest"""
if not self.modules_pool.get_top_module().manifest_dict["sim_top"]:
if not self.get_top_module().manifest_dict["sim_top"]:
logging.error("sim_top variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["sim_tool"]:
if not self.get_top_module().manifest_dict["sim_tool"]:
logging.error("sim_tool variable must be set in the top manifest.")
sys.exit("Exiting")
def run(self):
def simulation_makefile(self):
"""Execute the simulation action"""
self._check_all_fetched_or_quit()
self._generate_simulation_makefile()
def _generate_simulation_makefile(self):
"""Private method that performs the simulation stuff"""
tool_name = self.modules_pool.get_top_module().manifest_dict["sim_tool"]
self._check_simulation_makefile()
tool_name = self.get_top_module().manifest_dict["sim_tool"]
tool_module = importlib.import_module("hdlmake.tools.%s.%s" % (tool_name, tool_name))
tool_object = tool_module.ToolControls()
tool_info = tool_object.get_keys()
......@@ -76,10 +72,9 @@ class GenerateSimulationMakefile(Action):
logging.info("Generating " + name + " makefile for simulation.")
pool = self.modules_pool
top_module = pool.get_top_module()
top_module = self.get_top_module()
fset = pool.build_file_set()
fset = self.build_file_set(self.get_top_module().manifest_dict["sim_top"])
dep_files = fset.filter(DepFile)
#dep_solver.solve(dep_files)
......
......@@ -29,23 +29,23 @@ from .action import Action
class GenerateSynthesisMakefile(Action):
def _check_manifest(self):
def _check_synthesis_makefile(self):
# NOTE: top_module is not used in synthesis!!
if not self.modules_pool.get_top_module().manifest_dict["syn_top"]:
if not self.get_top_module().manifest_dict["syn_top"]:
logging.error("syn_top variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["syn_tool"]:
if not self.get_top_module().manifest_dict["syn_tool"]:
logging.error("syn_tool variable must be set in the top manifest.")
sys.exit("Exiting")
def run(self):
def synthesis_makefile(self):
self._check_all_fetched_or_quit()
self._generate_synthesis_makefile()
def _generate_synthesis_makefile(self):
tool_name = self.modules_pool.get_top_module().manifest_dict["syn_tool"]
tool_name = self.get_top_module().manifest_dict["syn_tool"]
tool_module = importlib.import_module("hdlmake.tools.%s.%s" % (tool_name, tool_name))
tool_object = tool_module.ToolControls()
tool_info = tool_object.get_keys()
......@@ -67,7 +67,7 @@ class GenerateSynthesisMakefile(Action):
tool_path = ""
logging.info("Generating synthesis makefile for " + name)
tool_object.generate_synthesis_makefile(top_mod=self.modules_pool.get_top_module(),
tool_object.generate_synthesis_makefile(top_mod=self.get_top_module(),
tool_path=tool_path)
logging.info("Synthesis makefile generated.")
......@@ -33,27 +33,28 @@ from .action import Action
class GenerateSynthesisProject(Action):
def _check_manifest(self):
if not self.modules_pool.get_top_module().manifest_dict["syn_tool"]:
def _check_synthesis_project(self):
manifest = self.get_top_module().manifest_dict
if not manifest["syn_tool"]:
logging.error("syn_tool variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["syn_device"]:
if not manifest["syn_device"]:
logging.error("syn_device variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["syn_grade"]:
if not manifest["syn_grade"]:
logging.error("syn_grade variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["syn_package"]:
if not manifest["syn_package"]:
logging.error("syn_package variable must be set in the top manifest.")
sys.exit("Exiting")
if not self.modules_pool.get_top_module().manifest_dict["syn_top"]:
if not manifest["syn_top"]:
logging.error("syn_top variable must be set in the top manifest.")
sys.exit("Exiting")
def run(self):
def synthesis_project(self):
self._check_all_fetched_or_quit()
self._check_manifest()
self._check_synthesis_project()
self._generate_synthesis_project()
......@@ -128,7 +129,7 @@ end sdb_meta_pkg;""")
def _generate_synthesis_project(self):
tool_name = self.modules_pool.get_top_module().manifest_dict["syn_tool"]
tool_name = self.get_top_module().manifest_dict["syn_tool"]
tool_module = importlib.import_module("hdlmake.tools.%s.%s" % (tool_name, tool_name))
tool_object = tool_module.ToolControls()
tool_info = tool_object.get_keys()
......@@ -164,9 +165,9 @@ end sdb_meta_pkg;""")
logging.info("No previous project: creating a new one...")
update=False
top_mod = self.modules_pool.get_top_module()
fileset = self.modules_pool.build_file_set()
privative_files = tool_object.supported_files(self.modules_pool.build_complete_file_set())
top_mod = self.get_top_module()
fileset = self.build_file_set(top_mod.manifest_dict["syn_top"])
privative_files = tool_object.supported_files(self.build_complete_file_set())
if privative_files:
logging.info("Privative / non-parseable files detected: %s" % len(privative_files))
......@@ -176,12 +177,12 @@ end sdb_meta_pkg;""")
if self.env.options.generate_project_vhd:
self._write_project_vhd(id_value, env[version_key])
fileset.add([sff.new(path=path.rel2abs("project.vhd"),
module=self.modules_pool.get_module_by_path("."))])\
module=self.get_module_by_path("."))])\
tool_object.generate_synthesis_project(update=update,
tool_version=self.env[version_key],
top_mod=self.modules_pool.get_top_module(),
top_mod=self.get_top_module(),
fileset = fileset)
logging.info(name + " project file generated.")
......
......@@ -25,7 +25,7 @@ from hdlmake.util import path
import logging
class Tree(Action):
def run(self):
def generate_tree(self):
try:
import networkx as nx
except Exception as e:
......@@ -39,7 +39,7 @@ class Tree(Action):
if self.env.options.solved:
logging.warning("This is the solved tree")
else:
for m in self.modules_pool:
for m in self:
if not m.isfetched:
unfetched_modules = True
else:
......
......@@ -116,7 +116,6 @@ class ModuleCore(ModuleConfig):
self.pool = None
self.top_module = None
self.manifest_dict = None
self.top_entity = None
super(ModuleCore, self).__init__()
......
......@@ -66,7 +66,6 @@ class Module(ModuleContent):
"""Calculate and initialize the origin attributes: path, source..."""
assert module_args.url is not None
assert module_args.source is not None
self.top_entity = None
super(Module, self).__init__()
self.init_config(module_args)
self.set_pool(pool)
......
......@@ -34,9 +34,16 @@ from . import new_dep_solver as dep_solver
from .util import path as path_mod
from . import fetch
from .env import Env
from .action import (CheckManifest, CheckCondition, CleanModules, FetchModules, ListFiles,
ListModules, MergeCores, Tree, GenerateSimulationMakefile,
GenerateSynthesisMakefile, GenerateRemoteSynthesisMakefile, GenerateSynthesisProject,
QsysHwTclUpdate)
class ModulePool(list):
class ModulePool(list, CheckManifest, CheckCondition, CleanModules, FetchModules, ListFiles,
ListModules, MergeCores, Tree, GenerateSimulationMakefile,
GenerateSynthesisMakefile, GenerateRemoteSynthesisMakefile, GenerateSynthesisProject,
QsysHwTclUpdate):
"""
The ModulePool class acts as the container for the HDLMake modules that
are progressively being added to the design hierarchy.
......@@ -194,9 +201,8 @@ class ModulePool(list):
logging.debug("End build complete file set")
return all_manifested_files
def build_file_set(self):
def build_file_set(self, top_entity=None):
"""Build file set with only those files required by the top entity"""
top_entity = self.top_module.top_entity
logging.debug("Begin build file set for %s", top_entity)
all_files = self.build_complete_file_set()
if not self._deps_solved:
......
......@@ -65,7 +65,7 @@ local: sim_pre_cmd simulation sim_post_cmd
simulation:
""")
makefile_text_1 = makefile_tmplt_1.substitute(
top_module=top_module.top_entity
top_module=top_module.manifest_dict["sim_top"]
)
self.write(makefile_text_1)
......
......@@ -68,7 +68,7 @@ simulation:
""")
makefile_text_1 = makefile_tmplt_1.substitute(
top_module=top_module.top_entity
top_module=top_module.manifest_dict["sim_top"]
)
self.write(makefile_text_1)
......
......@@ -80,7 +80,7 @@ class ToolControls(MakefileWriter):
from hdlmake.srcfile import VerilogFile, VHDLFile
make_preambule_p1 = """## variables #############################
PWD := $(shell pwd)
TOP_MODULE := """ + top_module.top_entity + """
TOP_MODULE := """ + top_module.manifest_dict["sim_top"] + """
FUSE_OUTPUT ?= isim_proj
XILINX_INI_PATH := """ + self.__get_xilinxsim_ini_dir(top_module.pool.env) + """
......
......@@ -86,7 +86,7 @@ simulation:
""")
makefile_text_1 = makefile_tmplt_1.substitute(
top_module=top_module.top_entity
top_module=top_module.manifest_dict["sim_top"]
)
self.write(makefile_text_1)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment