def check_intermodule_field(obj: OrderedDict, prefix: str = "") -> int: error = 0 # type check if obj["type"] not in IM_TYPES: log.error("{prefix} Inter_signal {name} " "type {type} is incorrect.".format(prefix=prefix, name=obj["name"], type=obj["type"])) error += 1 if obj["act"] not in IM_ACTS: log.error("{prefix} Inter_signal {name} " "act {act} is incorrect.".format(prefix=prefix, name=obj["name"], act=obj["act"])) error += 1 # Check 'width' field width = 1 if "width" not in obj: obj["width"] = 1 elif not isinstance(obj["width"], int): width, err = check_int(obj["width"], obj["name"]) if err: log.error("{prefix} Inter-module {inst}.{sig} 'width' " "should be int type.".format(prefix=prefix, inst=obj["inst_name"], sig=obj["name"])) error += 1 else: # convert to int value obj["width"] = width return error
def check_intermodule_field(obj: Union[InterSignal, OrderedDict], prefix: str = "") -> Tuple[int, OrderedDict]: error = 0 if isinstance(obj, InterSignal): sig = obj.as_dict() else: sig = obj # type check if sig["type"] not in IM_TYPES: log.error("{prefix} Inter_signal {name} " "type {type} is incorrect.".format(prefix=prefix, name=sig["name"], type=sig["type"])) error += 1 if sig["act"] not in IM_ACTS: log.error("{prefix} Inter_signal {name} " "act {act} is incorrect.".format(prefix=prefix, name=sig["name"], act=sig["act"])) error += 1 # Check if type and act are matched if error == 0: if sig["act"] not in IM_VALID_TYPEACT[sig['type']]: log.error("{type} and {act} of {name} are not a valid pair." "".format(type=sig['type'], act=sig['act'], name=sig['name'])) error += 1 # Check 'width' field width = 1 if "width" not in sig: sig["width"] = 1 elif not isinstance(sig["width"], int): width, err = check_int(sig["width"], sig["name"]) if err: log.error("{prefix} Inter-module {inst}.{sig} 'width' " "should be int type.".format(prefix=prefix, inst=sig["inst_name"], sig=sig["name"])) error += 1 else: # convert to int value sig["width"] = width # Add empty string if no explicit default for dangling pins is given. # In that case, dangling pins of type struct will be tied to the default # parameter in the corresponding package, and dangling pins of type logic # will be tied off to '0. if "default" not in sig: sig["default"] = "" return error, sig
def check_keys(obj, control, prefix=""): """ Check the keys recursively. The control parameter is a control group to check obj data structure. """ error = 0 # required for k, v in control["required"].items(): if not k in obj: error += 1 log.error(prefix + " missing required key " + k) # Check every fields' correctness for k, v in obj.items(): checker = ['', ''] prefix_name = prefix + " " + k if k in control["required"]: checker = control["required"][k] elif k in control["optional"]: checker = control["optional"][k] elif k in control["added"]: log.warning(prefix + " contains generated key " + k) checker = control["added"][k] else: log.warning(prefix + " contains extra key " + k) continue # Type and value check if not checker[0] in val_types: log.error(prefix + " field {} is undefined type. Check val_types {}".format( k, checker[0])) if checker[0] == 'lg': # List of subgroup error += sum( map( partial(check_keys, control=checker[1], prefix=prefix_name), obj[k])) elif checker[0] == 'g': # if second entry isn't string type, call recursively if isinstance(checker[1], str): log.info( "Skipping {} as no further control group is given".format( prefix_name)) continue error += check_keys(obj=obj[k], control=checker[1], prefix=prefix_name) elif checker[0] == 'd': int_v, err = check_int(obj[k], prefix_name) if err: error += 1 elif checker[0] == 's' or checker[0] == 't': # don't care the string pass elif checker[0] == 'pb': b_v, err = check_bool(obj[k], prefix_name) if err: error += 1 elif checker[0] == 'l': if not isinstance(obj[k], list): error += 1 else: log.error(prefix_name + " is not supported in this configuration format") return error
def check_intermodule(topcfg: Dict, prefix: str) -> int: if "inter_module" not in topcfg: return 0 total_error = 0 for req, rsps in topcfg["inter_module"].items(): error = 0 # checking the key, value are in correct format # Allowed format # 1. module.signal # 2. module.signal[index] // Remember array is not yet supported # // But allow in format checker # # Example: # inter_module: { # 'flash_ctrl.flash': ['eflash.flash_ctrl'], # 'life_cycle.provision': ['debug_tap.dbg_en', 'dft_ctrl.en'], # 'otp.pwr_hold': ['pwrmgr.peri[0]'], # 'flash_ctrl.pwr_hold': ['pwrmgr.peri[1]'], # } # # If length of value list is > 1, then key should be array (width need to match) # If key is format #2, then lenght of value list shall be 1 # If one of the value is format #2, then the key should be 1 bit width and # entries of value list should be 1 req_m, req_s, req_i = filter_index(req) if req_s is "": log.error( "Cannot parse the inter-module signal key '{req}'".format( req=req)) error += 1 # Check rsps signal format is list if not isinstance(rsps, list): log.error("Value of key '{req}' should be a list".format(req=req)) error += 1 continue req_struct = find_intermodule_signal(topcfg["inter_signal"]["signals"], req_m, req_s) # Check 'width' field if "width" not in req_struct: req_struct["width"] = 1 elif not isinstance(req_struct["width"], int): width, err = check_int(req_struct["width"], req_struct["name"]) if err: log.error( "Inter-module {inst}.{sig} 'width' should be int type.". format(inst=req_struct["inst_name"], sig=req_struct["name"])) error += 1 else: # convert to int value req_struct["width"] = width if req_i != -1 and len(rsps) != 1: # Array format should have one entry log.error( "If key {req} has index, only one entry is allowed.".format( req=req)) error += 1 # Check rsp format for i, rsp in enumerate(rsps): rsp_m, rsp_s, rsp_i = filter_index(rsp) if rsp_s is "": log.error( "Cannot parse the inter-module signal key '{req}->{rsp}'". format(req=req, rsp=rsp)) error += 1 rsp_struct = find_intermodule_signal( topcfg["inter_signal"]["signals"], rsp_m, rsp_s) # Check 'width' field width = 1 if "width" not in rsp_struct: rsp_struct["width"] = 1 elif not isinstance(rsp_struct["width"], int): width, err = check_int(rsp_struct["width"], rsp_struct["name"]) if err: log.error( "Inter-module {inst}.{sig} 'width' should be int type." .format(inst=rsp_struct["inst_name"], sig=rsp_struct["name"])) error += 1 else: # convert to int value rsp_struct["width"] = width if rsp_i != -1 and req_struct["width"] != 1: # If rsp has index, req should be width 1 log.error( "If rsp {rsp} has an array index, only one-to-one map is allowed." .format(rsp=rsp)) error += 1 # All rsps are checked, check the total width to req width # If req is array, it is not allowed to have partial connections. # Doing for loop again here: Make code separate from other checker # for easier maintenance total_error += error if error != 0: # Skip the check continue rsps_width = 0 for rsp in rsps: rsp_m, rsp_s, rsp_i = filter_index(rsp) rsp_struct = find_intermodule_signal( topcfg["inter_signal"]["signals"], rsp_m, rsp_s) # Update total responses width rsps_width += rsp_struct["width"] if req_struct["width"] != rsps_width: log.error( "Request {} width is not matched with total responses width {}" .format(req_struct["width"], rsps_width)) error += 1 return total_error