- return {
- Codegen.PPC_SVP64_H: ppc_svp64_h,
- Codegen.PPC_SVP64_OPC_C: ppc_svp64_opc_c,
- }[self](entries)
-
-
-def regex_enum(enum):
- assert issubclass(enum, _enum.Enum)
- return "|".join(item.name for item in enum)
-
-
-PATTERN_VHDL_BINARY = r"(?:2#[01]+#)"
-PATTERN_DECIMAL = r"(?:[0-9]+)"
-PATTERN_PARTIAL_BINARY = r"(?:[01-]+)"
-
-# Examples of the entries to be caught by the pattern below:
-# 2 => (P2, EXTRA3, RA_OR_ZERO, NONE, NONE, RT, NONE, NONE, NONE, Idx1, NONE, NONE, Idx0, NONE, NONE, NONE), -- lwz
-# -----10110 => (P2, EXTRA3, NONE, FRB, NONE, FRT, NONE, NONE, CR1, NONE, Idx1, NONE, Idx0, NONE, NONE, Idx0), -- fsqrts
-# 2#0000000000# => (P2, EXTRA3, NONE, NONE, NONE, NONE, NONE, BFA, BF, NONE, NONE, NONE, NONE, NONE, Idx1, Idx0), -- mcrf
-PATTERN = "".join((
- r"^\s*",
- rf"(?P<opcode>{PATTERN_VHDL_BINARY}|{PATTERN_DECIMAL}|{PATTERN_PARTIAL_BINARY})",
- r"\s?=>\s?",
- r"\(",
- r",\s".join((
- rf"(?P<ptype>{regex_enum(_SVPtype)})",
- rf"(?P<etype>{regex_enum(_SVEtype)})",
- rf"(?P<in1>{regex_enum(_In1Sel)})",
- rf"(?P<in2>{regex_enum(_In2Sel)})",
- rf"(?P<in3>{regex_enum(_In3Sel)})",
- rf"(?P<out>{regex_enum(_OutSel)})",
- rf"(?P<out2>{regex_enum(_OutSel)})",
- rf"(?P<cr_in>{regex_enum(_CRInSel)})",
- rf"(?P<cr_out>{regex_enum(_CROutSel)})",
- rf"(?P<sv_in1>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_in2>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_in3>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_out>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_out2>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_cr_in>{regex_enum(_SVEXTRA)})",
- rf"(?P<sv_cr_out>{regex_enum(_SVEXTRA)})",
- )),
- r"\)",
- r",",
- r"\s?--\s?",
- r"(?P<name>[A-Za-z0-9_\./]+)",
- r"\s*$",
-))
-REGEX = _re.compile(PATTERN)
-
-
-ISA = _SVP64RM()
-FIELDS = {field.name:field for field in _dataclasses.fields(Record)}
-FIELDS.update({field.name:field for field in _dataclasses.fields(Entry)})
-def parse(path, opcode_cls):
- for record in ISA.get_svp64_csv(path):
- opcode = opcode_cls(record.pop("opcode"))
- names = record.pop("comment").split("=")[-1]
- for name in map(Name, names.split("/")):
- if name.startswith("l") and name.endswith("br"):
- continue
- if name in {"mcrxr", "mcrxrx", "darn"}:
- continue
- if name in {"bctar", "bcctr"}:
- continue
- if "rfid" in name:
- continue
- if name in {"setvl"}:
- continue
-
- record = {key.lower().replace(" ", "_"):value for (key, value) in record.items()}
- for (key, value) in tuple(record.items()):
- key = key.lower().replace(" ", "_")
- if key not in FIELDS:
- record.pop(key)
- continue
-
- field = FIELDS[key]
- if not isinstance(value, field.type):
- if issubclass(field.type, _enum.Enum):
- value = {item.name:item for item in field.type}[value]
- else:
- value = field.type(value)
-
- record[key] = value
-
- yield Entry(name=name, record=Record(**record))
+ num_regs = Size("(sizeof (svp64_regs) / sizeof (svp64_regs[0]))")
+ yield Size.c_var("svp64_num_regs",
+ prefix="const ", suffix=" = \\")
+ yield from indent(num_regs.c_value(suffix=";"))
+
+ opcodes = Array[Opcode, ...](opcodes)
+ nr_opcodes = Size("(sizeof (svp64_opcodes) / sizeof (svp64_opcodes[0]))")
+
+ records = Array[Record, ...](records)
+ nr_records = Size("(sizeof (svp64_records) / sizeof (svp64_records[0]))")
+
+ yield from {
+ Codegen.PPC_SVP64_GEN_H: ppc_svp64_h,
+ Codegen.PPC_SVP64_OPC_GEN_C: ppc_svp64_opc_c,
+ }[self](opcodes, nr_opcodes, records, nr_records)
+
+
+def collect(db):
+ opcodes = []
+ records = []
+ fields = {field.name:field.type for field in _dataclasses.fields(Desc)}
+
+ for insn in filter(lambda insn: insn.svp64 is not None, db):
+ desc = {}
+
+ for (key, cls) in fields.items():
+ value = getattr(insn, key)
+
+ if (((cls is EType) and (value is _SVEType.NONE)) or
+ ((cls is Extra) and (value is _SVExtra.Idx_1_2))):
+ desc = None
+ break
+
+ if issubclass(cls, Boolean):
+ value = Boolean(value)
+ elif issubclass(cls, _enum.Enum):
+ value = cls[value.name]
+ else:
+ value = cls(value)
+ desc[key] = value
+
+ if desc is None:
+ continue
+
+ name = Name(f"sv.{insn.name}")
+ offset = len(opcodes)
+ for opcode in insn.opcodes:
+ value = Opcode.Value(opcode.value)
+ mask = Opcode.Mask(opcode.mask)
+ opcode = Opcode(value=value, mask=mask)
+ opcodes.append(opcode)
+ desc = Desc(**desc)
+
+ record = Record(name=name, desc=desc,
+ opcodes=Opcodes(offset), nr_opcodes=Size(len(insn.opcodes)))
+ records.append(record)
+
+ return (opcodes, records)