diff --git a/cactuscore/uhal/tools/scripts/gen_ipbus_addr_decode b/cactuscore/uhal/tools/scripts/gen_ipbus_addr_decode index f396ff0ac..3db485e9a 100755 --- a/cactuscore/uhal/tools/scripts/gen_ipbus_addr_decode +++ b/cactuscore/uhal/tools/scripts/gen_ipbus_addr_decode @@ -123,8 +123,13 @@ class nodetree(object): s = s + prefix + i.name + " " + hex(i.ref.getAddress()) + " " + hex(i.width) + " " + str(i.flag) + "\n" if i.desc: s = s + self.dump(i, prefix + " ") return s - + def assign_width(self, n): + errors = [] + self._assign_width(n, errors) + return len(errors) == 0 + + def _assign_width(self, n, errors_detected): n.sort() if n.ref is not None: addr = n.ref.getAddress() @@ -142,11 +147,14 @@ class nodetree(object): saddr = i.ref.getAddress() if saddr < max_addr: log.error("Overlap between nodes detected: " + i.name + " " + hex(saddr) + " "+ hex(max_addr)) - max_addr = saddr + pow(2, self.assign_width(i)) - if max_addr > top_addr: top_addr = max_addr + errors_detected.append(i.name) + max_addr = saddr + pow(2, self._assign_width(i, errors_detected)) + if max_addr > top_addr: + top_addr = max_addr n.width = int(math.ceil(math.log(top_addr - addr,2))) if addr % pow(2, n.width) != 0: - log.error("Non-aligned base address detected: " + n.name + " " + hex(addr) + " " + hex(n.width)) + log.error("Node '" + n.name + "' at " + hex(addr) + ": Width, " + hex(n.width) + ", produces address mask " + hex(pow(2,n.width)) + " that is not aligned with node's base address") + errors_detected.append(n.name) return n.width def get_nodes(self, n): @@ -160,6 +168,9 @@ class nodetree(object): #=========================================================================================== +EXIT_CODE_INCORRECT_ARGUMENTS = 1 +EXIT_CODE_ARG_PARSING_ERROR = 2 +EXIT_CODE_NODE_ADDRESS_ERRORS = 3 def main(): @@ -180,7 +191,7 @@ def main(): opts, args = getopt.getopt(sys.argv[1:], "vdnht:", ["verbose","debug","dry-run","help","template="]) except getopt.GetoptError, err: log.critical(__doc__) - sys.exit(2) + sys.exit(EXIT_CODE_ARG_PARSING_ERROR) for o, a in opts: if o in ("-v", "--verbose"): log.setLevel(logging.INFO) @@ -199,7 +210,7 @@ def main(): # make sure that exactly one argument was given, later assumed to be the xml file name if len(args) != 1: log.critical("Incorrect usage - invalid number of arguments! Make sure that options come before argument.\n" + __doc__) - sys.exit(1) + sys.exit(EXIT_CODE_INCORRECT_ARGUMENTS) try: device = uhal.getDevice("dummy","ipbusudp-1.3://localhost:12345","file://" + args[0]) @@ -212,7 +223,11 @@ def main(): f = d.getFirmwareInfo() p = "type" in f and f["type"] == "endpoint" t.add(node(i,d,p)) - t.assign_width(t.root) + node_address_errors_detected = False + if not t.assign_width(t.root): + log.error("Node errors detected (e.g. non-aligned addresses, or address overlaps); exiting early before writing output") + sys.exit(EXIT_CODE_NODE_ADDRESS_ERRORS) + uhal_slaves = t.get_nodes(t.root) moduleName = os.path.splitext(os.path.basename(args[0]))[0]