예제 #1
0
 def levta(self, node: KeyValue) -> str:
     level = node.get_value("LEVEL")
     in_use = node.get_value("INUSE") if node.get_value(
         "INUSE") else node.fall_down
     not_used = node.get_value("NOTUSED") if node.get_value(
         "NOTUSED") else node.fall_down
     return in_use if self._is_level_present(level) else not_used
예제 #2
0
 def error_check(self, node: KeyValue) -> str:
     if self.is_error(node.label):
         field_name = node.get_value("FIELD")
         reg = Register(node.get_value("BASE"))
         address = self.regs.get_unsigned_value(reg) + self.seg.evaluate(
             field_name)
         byte_array = DataType("X",
                               input=node.get_value("XVALUE")).to_bytes()
         self.vm.set_bytes(byte_array, address, len(byte_array))
     return node.fall_down
예제 #3
0
 def sysra(self, node: KeyValue) -> Optional[str]:
     return_code = node.get_value("P1")
     dump = node.get_value("P2")
     self.dumps.append(dump)
     if return_code == "R":
         return node.fall_down
     elif return_code == "E":
         return None
     else:
         raise DumpExecutionError
예제 #4
0
 def mhinf(self, node: KeyValue) -> str:
     if node.keys[0] != "ECB":
         raise MhinfExecutionError
     reg = Register(node.get_value("REG"))
     if not reg.is_valid():
         raise MhinfExecutionError
     option = node.get_value("INPTR")
     if option == "NAME":
         airline_code = self.vm.get_bytes(self.regs.get_value(reg), 2)
         self.set_partition(DataType("X", bytes=airline_code).decode)
     else:
         raise MhinfExecutionError
     return node.fall_down
예제 #5
0
 def dbifb(self, node: KeyValue) -> str:
     self._base_sw00sr()
     error_label = node.get_value("ERRORA")
     if node.get_value("FILE") == "PR001W":
         if error_label and self.is_error(node.label):
             self.regs.R3 = 0
             return error_label
         return node.fall_down
     if node.get_value("REF") not in self.tpfdf_ref:
         self.regs.R3 = 0
         if error_label:
             return error_label
     return node.fall_down
예제 #6
0
    def dbred(self, node: KeyValue) -> str:
        self._base_sw00sr()

        # Setup KEY1 Primary key
        pky = node.get_sub_value("KEY1", "PKY")
        if pky is not None:
            key = f"{self.seg.evaluate(pky):02X}"
        else:
            key = f"{self.seg.evaluate(node.get_sub_value('KEY1', 'S')):02X}"

        # Set up KEY2 to KEY6
        other_keys = dict()
        for key_number in range(2, 7):
            key_n = f"KEY{key_number}"
            if node.get_value(key_n) is None:
                break
            df_field_name = node.get_sub_value(key_n, "R")
            condition = node.get_sub_value(key_n, "C")
            sign = self.C[condition] if condition is not None else "=="
            field: FieldBaseDsp = node.get_sub_value(key_n, "S")
            if field is None:
                # TODO For M, D, L types
                raise DbredError
            base_address = self.regs.get_value(field.base)
            length = self.seg.lookup(df_field_name).length
            byte_array = self.vm.get_bytes(base_address + field.dsp, length)
            other_keys[df_field_name] = (f"{sign} {byte_array}", length)

        # Get the lrec
        ref_name = node.get_value("REF")
        item_number = 0 if node.get_value(
            "BEGIN") else self.tpfdf_ref[ref_name]
        item_number += 1
        lrec, item_number = Tpfdf.get_lrec(ref_name, key, item_number,
                                           other_keys)
        self.tpfdf_ref[ref_name] = item_number

        # Update error_code and REG=
        if lrec is None or self.is_error(node.label):
            error_code = self.seg.evaluate("#TPFDBER")
        else:
            error_code = self.seg.evaluate("#TPFDBOK")
            data_address = self.regs.R3 + self.seg.evaluate("SW00KL1")
            self.vm.set_bytes(lrec, data_address, len(lrec))
            reg = Register(node.get_value("REG"))
            if reg.is_valid():
                self.regs.set_value(data_address, reg)
        self.vm.set_byte(error_code,
                         self.regs.R3 + self.seg.evaluate("SW00RTN"))

        # ERROR=
        error_label = node.get_value("ERRORA")
        if error_label and self.is_error(node.label):
            return error_label

        return node.fall_down
예제 #7
0
 def dbcls(self, node: KeyValue) -> str:
     if any(key not in ["FILE", "REF"] for key in node.keys):
         raise TpfdfExecutionError(node)
     file_value = node.get_value("FILE")
     ref_value = node.get_value("REF")
     if file_value and file_value != "PR001W":
         raise TpfdfExecutionError(node)
     if file_value == "PR001W":
         return node.fall_down
     if ref_value not in self.tpfdf_ref and ref_value != "ALL":
         raise TpfdfExecutionError(node)
     if ref_value == "ALL":
         self.tpfdf_ref.clear()
     else:
         del self.tpfdf_ref[ref_value]
     return node.fall_down
예제 #8
0
 def aaget(self, node: KeyValue) -> str:
     address = self.vm.allocate()
     ecb_address = self.get_ecb_address("D1", "CE1CR")
     self.vm.set_value(address, ecb_address)
     reg = Register(node.get_value("BASEREG"))
     if reg.is_valid():
         self.regs.set_value(address, reg)
     return node.fall_down
예제 #9
0
 def crusa(self, node: KeyValue) -> str:
     for index in range(16):
         level = node.get_value(f"S{index}")
         if level is None:
             break
         control_address = self.get_ecb_address(f"D{level}", "CE1CT")
         size_address = self.get_ecb_address(f"D{level}", "CE1CC")
         self.vm.set_value(0x01, control_address, 2)
         self.vm.set_value(0, size_address, 2)
     return node.fall_down
예제 #10
0
 def senda(self, node: KeyValue) -> str:
     message: str = node.get_value("MSG")
     if message:
         self.messages.append(message.replace("'", ""))
         return node.fall_down
     can: str = node.get_value("CAN")
     if not can:
         raise UserDefinedMacroExecutionError(node)
     canned_number = macros["UI2PF"].evaluate(can)
     if node.get_value("SEC") == "YES":
         canned_number += 256
     message_string = next(
         (canned["message"]
          for canned in UI2CNN if int(canned["number"]) == canned_number),
         None)
     if not message_string:
         raise UserDefinedMacroExecutionError(node)
     self.messages.append(message_string)
     return node.fall_down
예제 #11
0
 def aacpy(self, node: KeyValue) -> str:
     to_level = node.get_value("TO")
     if to_level not in config.ECB_LEVELS or to_level == "1":
         raise UserDefinedMacroExecutionError(node)
     core_reference = self.get_ecb_address(f"D{to_level}", "CE1CR")
     aaa_copy = self.vm.allocate()
     self.vm.set_value(aaa_copy, core_reference)
     aaa_bytes = copy(self.vm.frames[self.vm.base_key(config.AAA)])
     self.vm.set_bytes(aaa_bytes, aaa_copy, len(aaa_bytes))
     return node.fall_down
예제 #12
0
 def pnrcc(self, node: KeyValue) -> str:
     action = node.get_value("ACTION")
     reg = Register(node.get_value("REG"))
     if not reg.is_valid():
         raise RegisterInvalidError
     pnrcm_base = self.regs.get_value(reg)
     self.seg.load_macro("PNRCM")
     if self.is_error(node.label):
         error_code = self.seg.evaluate("#PM1ER5")
         self.vm.set_value(error_code,
                           pnrcm_base + self.seg.evaluate("PM1ERR"), 1)
         return node.fall_down
     if action in ["CRLON"]:
         pnr_locator_bytes = self.vm.get_bytes(
             pnrcm_base + self.seg.evaluate("PM1LOC"), 6)
         pnr_locator = DataType("X", bytes=pnr_locator_bytes).decode
         ordinal = PnrLocator.to_ordinal(pnr_locator)
         self.vm.set_value(ordinal,
                           pnrcm_base + self.seg.evaluate("PM1ORN"))
         self.vm.set_value(ordinal,
                           pnrcm_base + self.seg.evaluate("PM1FAD"))
     return node.fall_down
예제 #13
0
    def heapa(self, node: KeyValue) -> str:
        # REG, REF and SREF
        reg = Register(node.get_value("REG"))
        ref = node.get_value("REF")
        if ref is None:
            sref = node.get_value("SREF")
            if sref is None:
                raise HeapaExecutionError
            ref_bytes = self.seg.get_constant_bytes(sref, 8)
            ref = DataType("X", bytes=ref_bytes).decode

        # ERROR= for forced errors
        error_label = node.get_value("ERROR")
        if error_label and self.is_error(node.label):
            if reg.is_valid():
                self.regs.set_value(0, reg)
            return error_label

        # HEAPA / CFCMA / EHEAPA command types
        command = node.keys[0]
        heap = self.heap["new"] if node.command == "EHEAPA" else self.heap[
            "old"]
        if command == "ALLOCATE":
            address = self.vm.allocate()
            heap[ref] = address
            if reg.is_valid():
                self.regs.set_value(address, reg)
        elif command == "LOADADD":
            address = heap[ref] if ref in heap else 0
            if reg.is_valid():
                self.regs.set_value(address, reg)
            if address == 0 and error_label:
                return error_label
        elif command == "FREE":
            heap.pop(ref, None)
        else:
            raise HeapaExecutionError
        return node.fall_down
예제 #14
0
 def mcpck(self, node: KeyValue) -> str:
     match_label = node.get_value("YES") if node.get_value(
         "YES") else node.fall_down
     not_match_label = node.get_value("NO") if node.get_value(
         "NO") else node.fall_down
     if node.get_value("GROUP") == "LAN":
         return match_label if self.get_partition() in {
             "LA", "4M", "XL"
         } else not_match_label
     if node.get_value("PP"):
         not_mcp_label = node.get_value("NOTMCP")
         if not_mcp_label and self.get_partition() not in {
                 "LA", "4M", "XL"
         }:
             return not_mcp_label
         return match_label if self.get_partition() in {
             "LA"
         } else not_match_label
     raise McpckExecutionError
예제 #15
0
 def _pd0_base(self, node: KeyValue) -> Optional[int]:
     workarea = node.get_value("WORKAREA")
     if workarea is None:
         raise Pd0BaseError
     if workarea[0] == "LEV":
         lev_parameter = workarea[1]
         level = lev_parameter[1] if len(
             lev_parameter
         ) == 2 and lev_parameter[0] == "D" else lev_parameter
         if not self._is_level_present(level):
             self._core_block(self.vm.allocate(), level)
         level = f"D{level}"
         level_address = self.get_ecb_address(level, "CE1CR")
         pd0_base = self.vm.get_value(level_address)
     elif workarea[0] == "REG":
         reg = Register(workarea[1])
         if not reg.is_valid():
             raise RegisterInvalidError
         pd0_base = self.regs.get_value(reg)
     else:
         raise Pd0BaseError
     return pd0_base
예제 #16
0
 def prima(self, node: KeyValue) -> str:
     if "PNR" not in node.keys and "AAA" not in node.keys:
         raise PrimaExecutionError
     if node.get_value("MODE") != "CHECK":
         raise PrimaExecutionError
     if node.get_value("PNRLEV") or node.get_value("PRDATA"):
         raise PrimaExecutionError
     match_label = node.get_value("YES") if node.get_value(
         "YES") else node.fall_down
     not_match_label = node.get_value("NO") if node.get_value(
         "NO") else node.fall_down
     prime_host = self.vm.get_value(
         config.AAA + macros["WA0AA"].evaluate("WA0PHA"), 1) & 0x0F
     input_type = node.get_value("PH")
     if prime_host == 0:
         return not_match_label
     elif prime_host == 2:
         return match_label if input_type in ("1F",
                                              "ANY") else not_match_label
     elif prime_host == 3:
         return match_label if input_type in ("1B",
                                              "ANY") else not_match_label
     else:
         raise PrimaExecutionError
예제 #17
0
    def pdred(self, node: KeyValue) -> str:
        # Get the key from FIELD= or INDEX=
        self.seg.load_macro("PDEQU")
        self.seg.load_macro("PD0WRK")
        key_label = f"#PD_{node.get_value('FIELD')}_K"
        try:
            key_number = self.seg.evaluate(key_label)
            key = f"{key_number:2X}"
        except KeyError:
            # TODO Code for INDEX= Not in ETA5
            raise PdredFieldError

        # ERROR=
        error_label = node.get_value("ERROR")
        if error_label and self.is_error(node.label):
            return error_label

        # ACTION=VERIFY
        if node.get_value("ACTION") == "VERIFY":
            not_found_label = node.get_value("NOTFOUND") if node.get_value(
                "NOTFOUND") else node.fall_down
            found_label = node.get_value("FOUND") if node.get_value(
                "FOUND") else node.fall_down
            data, _ = Pnr.get_pnr_data(self._get_pnr_locator(),
                                       key,
                                       item_number=1)
            return not_found_label if data is None else found_label

        # Get the base of PD0WRK
        pd0_base = self._pd0_base(node)
        if pd0_base == 0:
            raise TPFServerMemoryError

        # Get the item number to read (Item numbers start from 1)
        pd0_ctl_key: LabelReference = self.seg.lookup("PD0_CTL_KEY")
        pd0_mc_cin: LabelReference = self.seg.lookup("PD0_MC_CIN")
        last_key = self.vm.get_unsigned_value(pd0_base + pd0_ctl_key.dsp,
                                              pd0_ctl_key.length)
        item_number = self.vm.get_value(pd0_base + pd0_mc_cin.dsp, pd0_mc_cin.length) + 1 \
            if last_key == key_number else 1
        self.vm.set_value(key_number, pd0_base + pd0_ctl_key.dsp,
                          pd0_ctl_key.length)

        # SEARCH-n parameters
        starts_with: Optional[str] = None
        for index in range(1, 7):
            search = node.get_value(f"SEARCH{index}")
            if search is None:
                break
            if search[0] == "START":
                if len(search) != 2:
                    raise PdredSearchError
                if search[1].startswith("'") and search[1].endswith("'"):
                    starts_with = search[1][1:-1]
                elif search[1].startswith("(") and search[1].endswith(")"):
                    reg = search[1][1:-1]
                    base_address = self.regs.get_unsigned_value(reg)
                    length = self.vm.get_unsigned_value(base_address, 1)
                    char_bytes = self.vm.get_bytes(base_address + 1, length)
                    starts_with = DataType("X", bytes=char_bytes).decode

        # Get the data
        pnr_locator = self._get_pnr_locator()
        packed = node.get_value("FORMATOUT") == "PACKED"
        if key == "20":  # PNR Header
            data, item_number = Pnr.get_pnr_data(pnr_locator,
                                                 "20",
                                                 1,
                                                 packed=True)
        else:
            data, item_number = Pnr.get_pnr_data(pnr_locator,
                                                 key,
                                                 item_number,
                                                 packed=packed,
                                                 starts_with=starts_with)
            self.vm.set_value(item_number, pd0_base + pd0_mc_cin.dsp,
                              pd0_mc_cin.length)

        # NOTFOUND & last item
        if data is None:
            not_found = node.get_value("NOTFOUND")
            if not_found is None:
                raise PdredNotFoundError
            return not_found
        elif item_number == Pnr.get_len(pnr_locator, key):
            last_item_bit: int = self.seg.evaluate("#PD0_RT_LST")
            pd0_rt_id1: LabelReference = self.seg.lookup("PD0_RT_ID1")
            self.vm.or_bit(pd0_base + pd0_rt_id1.dsp, last_item_bit)

        # Update the data in PD0WRK
        pd0_itm: LabelReference = self.seg.lookup(
            "PD0_P_DATA") if packed else self.seg.lookup("PD0_C_ITM")
        pd0_rt_adr: LabelReference = self.seg.lookup("PD0_RT_ADR")
        if len(data) > pd0_itm.length:
            raise PdredPd0Error
        self.vm.set_bytes(data, pd0_base + pd0_itm.dsp, len(data))
        pd0_rt_adr_value = pd0_base + pd0_itm.dsp
        if node.get_value("POINT") == "YES":
            attribute = Pnr.get_attribute_by_key(key)
            if packed:
                pd0_rt_adr_value += (len(Pnr.STD_PREFIX_BYTES) +
                                     len(attribute.std_fix))
            pd0_rt_adr_value += len(attribute.std_var)
        self.vm.set_value(pd0_rt_adr_value, pd0_base + pd0_rt_adr.dsp,
                          pd0_rt_adr.length)
        return node.fall_down
예제 #18
0
 def realtima(self, node: KeyValue) -> str:
     realtime_label = node.get_value("YES") if node.get_value(
         "YES") else node.fall_down
     return realtime_label
예제 #19
0
 def dbopn(self, node: KeyValue) -> str:
     self.tpfdf_ref[node.get_value("REF")] = 0
     return node.fall_down
예제 #20
0
 def nmsea(node: KeyValue) -> str:
     # TODO Finish NMSEA when data on NM0ID or WGL1 is available
     error = node.get_value("ERROR")
     return error if error else node.fall_down
예제 #21
0
 def tkdna(node: KeyValue) -> str:
     error = node.get_value("ERROR")
     if not error:
         raise NotImplementedExecutionError
     return error
예제 #22
0
 def pnamc(self, node: KeyValue) -> str:
     field: FieldBaseDsp = node.get_value("FIELD")
     self.vm.set_bytes(self.fields["CE3ENTPGM"],
                       self.regs.get_value(field.base) + field.dsp, 4)
     return node.fall_down