def test_external_with_interpreter(self): code = get_path_for_data_file("code.py") encoder = get_path_for_data_file("encode.py") decoder = get_path_for_data_file("decode.py") dir_with_spaces = os.path.join(tempfile.gettempdir(), "directory", "with extra space") os.makedirs(dir_with_spaces, exist_ok=True) coder_in_dir_with_spaces = os.path.join(dir_with_spaces, "code.py") encoder_in_dir_with_spaces = os.path.join(dir_with_spaces, "encode.py") decoder_in_dir_with_spaces = os.path.join(dir_with_spaces, "decode.py") shutil.copy(code, coder_in_dir_with_spaces) shutil.copy(encoder, encoder_in_dir_with_spaces) shutil.copy(decoder, decoder_in_dir_with_spaces) coder_in_dir_with_spaces = '{} "{}"'.format(sys.executable, coder_in_dir_with_spaces) e = Encoding(["test external with spaces", constants.DECODING_EXTERNAL, coder_in_dir_with_spaces + " d" + ";" + coder_in_dir_with_spaces + " e"]) data = array.array("B", [1, 0, 1, 0, 0, 1, 1]) encoded = e.encode(data) self.assertEqual(encoded, array.array("B", [1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1])) decoded = e.decode(encoded) self.assertEqual(decoded, data)
def test_external_homematic(self): f = os.readlink(__file__) if os.path.islink(__file__) else __file__ path = os.path.realpath(os.path.join(f, "..", "..")) code = os.path.join(path, "data", "decodings", "homematic_complete") e = Encoding(["test external homematic", constants.DECODING_EXTERNAL, code + " d" + ";" + code + " e"]) data = array.array("B", [1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 1]) decoded = e.decode(data) self.assertEqual(decoded, array.array("B", [1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 0, 0])) encoded = e.encode(decoded) self.assertEqual(encoded, data)
def test_crc(self): # http://depa.usst.edu.cn/chenjq/www2/software/crc/CRC_Javascript/CRCcalculation.htm # CRC-16: polynomial="16_standard", start_value = False, final_xor = False, reverse_polynomial=False, reverse_all=False # CRC-16-CCITT: polynomial="16_ccitt", start_value = False, final_xor = False, reverse_polynomial=False, reverse_all=False # http://www.lammertbies.nl/comm/info/crc-calculation.html <- Fehler # CRC-16: polynomial="16_standard", start_value = False, final_xor = False, reverse_polynomial=False, reverse_all=False c = GenericCRC(polynomial=WSPChecksum.CRC_8_POLYNOMIAL) e = Encoding() bitstr = ["010101010110100111011010111011101110111011100110001011101010001011101110110110101101", "010101010110101001101110111011101110111011100110001011101010001011101110110111100101", "010101010110100111010010111011101110111011100110001011101010001011101110110110100101"] expected = ["78", "c9", "f2"] for value, expect in zip(bitstr, expected): nv = "" for i in range(0, len(value)): if value[i] == "1": nv += "0" else: nv += "1" self.assertEqual(util.bit2hex(c.crc(e.str2bit(value[4:-8]))), expect)
def test_external(self): encoder = get_path_for_data_file("encode.py") decoder = get_path_for_data_file("decode.py") e = Encoding(["test external", constants.DECODING_EXTERNAL, decoder+";"+encoder]) data = array.array("B", [1, 0, 1, 0, 0, 1, 1]) encoded = e.encode(data) self.assertEqual(encoded, array.array("B", [1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1])) decoded = e.decode(encoded) self.assertEqual(decoded, data)
def test_carrier(self): e = Encoding() # Test 1 e.carrier = "----1....1**" # or "....1....101", ... original_inpt = e.str2bit("000010000100111111111100") inpt = copy.copy(original_inpt) #print("\nOriginal:", inpt) output, err, _ = e.code_carrier(True, inpt) #print("Decoded: ", output, err) newinpt, err, _ = e.code_carrier(False, output) #print("Encoded: ", newinpt, err) self.assertEqual(original_inpt, newinpt)
def test_whitening(self): e = Encoding() # Test 1 e.data_whitening_sync = util.hex2bit("67686768") original_inpt = util.hex2bit("aaaaaaaa67686768f9ca03909567ba76a8") + array.array("B", [False]) # Korrektes Signal, bitgenau inpt = copy.copy(original_inpt) #print (util.bit2hex(inpt)) output, err, _ = e.apply_data_whitening(True, inpt) #print (util.bit2hex(output), err) newinpt, err, _ = e.apply_data_whitening(False, output) #print (util.bit2hex(newinpt), newinpt, err) self.assertEqual(original_inpt, newinpt)
def to_xml_tag(self, decodings, participants, tag_name="protocol", include_message_type=False, write_bits=False, messages=None, modulators=None) -> ET.Element: root = ET.Element(tag_name) messages = self.messages if messages is None else messages # Save modulators if modulators is not None: # For protocol analyzer container root.append(Modulator.modulators_to_xml_tag(modulators)) root.append(Encoding.decodings_to_xml_tag(decodings)) root.append(Participant.participants_to_xml_tag(participants)) # Save data data_tag = ET.SubElement(root, "messages") for i, message in enumerate(messages): message_tag = message.to_xml(decoders=decodings, include_message_type=include_message_type, write_bits=write_bits) data_tag.append(message_tag) # Save message types separatively as not saved in messages already if not include_message_type: message_types_tag = ET.SubElement(root, "message_types") for message_type in self.message_types: message_types_tag.append(message_type.to_xml()) return root
def load_from_xml(self, xml_tag: ET.Element, message_types): assert xml_tag.tag == "simulator_config" items = [] modulators_tag = xml_tag.find("modulators") if modulators_tag: self.project_manager.modulators = Modulator.modulators_from_xml_tag(modulators_tag) participants_tag = xml_tag.find("participants") if participants_tag: for participant in Participant.read_participants_from_xml_tag(participants_tag): if participant not in self.project_manager.participants: self.project_manager.participants.append(participant) self.participants_changed.emit() decodings_tag = xml_tag.find("decodings") if decodings_tag: self.project_manager.decodings = Encoding.read_decoders_from_xml_tag(decodings_tag) rx_config_tag = xml_tag.find("simulator_rx_conf") if rx_config_tag: ProjectManager.read_device_conf_dict(rx_config_tag, self.project_manager.simulator_rx_conf) tx_config_tag = xml_tag.find("simulator_tx_conf") if tx_config_tag: ProjectManager.read_device_conf_dict(tx_config_tag, self.project_manager.simulator_tx_conf) for child_tag in xml_tag.find("items"): items.append(self.load_item_from_xml(child_tag, message_types)) self.add_items(items, pos=0, parent_item=None)
def test_enocean_crc8_message(self): e = Encoding() received = util.hex2bit("aacbac4cddd5ddd3bddd5ddcc5ddcddd4c2d5d5c2cdddab200000") preamble, sof, eof = "aa", "9", "b" decoded, err, state = e.code_enocean(decoding=True, inpt=received) self.assertEqual(err, 0) self.assertEqual(state, e.ErrorState.SUCCESS) self.assertIn(preamble, util.bit2hex(decoded)) self.assertIn(sof, util.bit2hex(decoded)) self.assertIn(eof, util.bit2hex(decoded)) reencoded, errors, state = e.code_enocean(decoding=False, inpt=decoded) self.assertEqual(errors, 0) self.assertEqual(state, e.ErrorState.SUCCESS) redecoded, errors, state = e.code_enocean(decoding=True, inpt=reencoded) self.assertEqual(errors, 0) self.assertEqual(state, e.ErrorState.SUCCESS) self.assertEqual(decoded, redecoded)
def test_morse(self): e = Encoding() e.morse_low = 3 e.morse_high = 5 e.morse_wait = 1 msg1 = "1111111000111100011111100100001111111111111111111111011" msg2 = "0111110111011111011101111101110" encoded = e.str2bit(msg1) compare = e.str2bit(msg2) decoded, err, _ = e.code_morse(decoding=True, inpt=encoded) reencoded, _, _ = e.code_morse(decoding=False, inpt=decoded) self.assertEqual(err, 1) self.assertEqual(reencoded, compare)
def test_load_profile(self): filename = os.path.join(tempfile.gettempdir(), "test.fuzz.xml") mod1 = Modulator("mod 1") mod2 = Modulator("mod 2") mod2.param_for_one = 42 decoders = [ Encoding(["NRZ"]), Encoding(["NRZ-I", constants.DECODING_INVERT]) ] pac = ProtocolAnalyzerContainer() pac.messages.append( Message([True, False, False, True], 100, decoder=decoders[0], message_type=pac.default_message_type)) pac.messages.append( Message([False, False, False, False], 200, decoder=decoders[1], message_type=pac.default_message_type)) pac.create_fuzzing_label(1, 10, 0) assert isinstance(self.form, MainController) pac.to_xml_file(filename, decoders=decoders, participants=self.form.project_manager.participants) self.wait_before_new_file() self.form.add_files( [os.path.join(tempfile.gettempdir(), "test.fuzz.xml")]) self.assertEqual(self.form.ui.tabWidget.currentWidget(), self.form.ui.tab_generator) pac = self.form.generator_tab_controller.table_model.protocol self.assertEqual(len(pac.messages), 2) self.assertEqual(pac.messages[1][0], False) self.assertEqual(len(pac.protocol_labels), 1)
def test_substitution(self): e = Encoding() e.src = [array.array("B", [True, True, True, False]), array.array("B", [True, False, False, False])] e.dst = [array.array("B", [True]), array.array("B", [False])] # encoded-string with 3 missing trailing zeroes encoded = e.str2bit( "1000111010001110111011101110111011101110100011101110111011101110111011101000100010001000100010001") compare = e.str2bit( "1000111010001110111011101110111011101110100011101110111011101110111011101000100010001000100010001000") decoded, err, _ = e.code_substitution(decoding=True, inpt=encoded) reencoded, _, _ = e.code_substitution(decoding=False, inpt=decoded) self.assertEqual(err, 3) self.assertEqual(reencoded, compare)
def test_enocean_switch_telegram(self): e = Encoding() received = "010101010110100111101010111011101110111011100110001011101010001011101110110111011101000" # First step is invert the received bits!!! #received = "10101010 1001 011000010101 000100010001 000100011001 110100010101 110100010001 0010001000 1011" preamble = "10101010" sof = "1001" eof = "1011" self.assertIn(preamble, received) self.assertIn(sof, received) self.assertIn(eof, received) # Preamble/SOF/EOF remain unchanged expected_result = preamble + sof + "01100001 00000000 00000010 11000001 11000000 00100100" + eof expected_result2 = preamble + sof + "01010000 00000000 00000010 11000001 11000000 00100010" + eof decoded, err, _ = e.code_enocean(True, e.str2bit(received.replace(" ",""))) self.assertEqual(err, 0) reencoded, err, _ = e.code_enocean(False, decoded) self.assertEqual(err, 0) self.assertEqual(decoded, e.str2bit(expected_result.replace(" ", ""))) self.assertEqual(reencoded, e.str2bit(received))
def __init__(self, plain_bits, pause: int, message_type: MessageType, rssi=0, modulator_index=0, decoder=None, fuzz_created=False, bit_sample_pos=None, bit_len=100, participant=None): """ :param pause: pause AFTER the message in samples :type plain_bits: list[bool|int] :type decoder: Encoding :type bit_alignment_positions: list of int :param bit_alignment_positions: Für Ausrichtung der Hex Darstellung (Leere Liste für Standardverhalten) :param bit_len: Für Übernahme der Bitlänge in Modulator Dialog :param fuzz_created: message was created through fuzzing :return: """ self.__plain_bits = array.array("B", plain_bits) self.pause = pause self.modulator_index = modulator_index self.rssi = rssi self.participant = participant # type: Participant self.message_type = message_type # type: MessageType self.timestamp = time.time() self.absolute_time = 0 # set in Compare Frame self.relative_time = 0 # set in Compare Frame self.__decoder = decoder if decoder else Encoding( ["Non Return To Zero (NRZ)"]) # type: Encoding self.align_labels = True self.fuzz_created = fuzz_created self.__decoded_bits = None self.__encoded_bits = None self.__bit_alignments = [] self.decoding_errors = 0 self.decoding_state = Encoding.ErrorState.SUCCESS self.bit_len = bit_len # Für Übernahme in Modulator if bit_sample_pos is None: self.bit_sample_pos = array.array("L", []) else: self.bit_sample_pos = bit_sample_pos """
def test_external_in_dir_with_spaces(self): encoder = get_path_for_data_file("encode.py") decoder = get_path_for_data_file("decode.py") dir_with_spaces = os.path.join(tempfile.gettempdir(), "directory", "with space") os.makedirs(dir_with_spaces, exist_ok=True) encoder_in_dir_with_spaces = os.path.join(dir_with_spaces, "encode.py") decoder_in_dir_with_spaces = os.path.join(dir_with_spaces, "decode.py") shutil.copy(encoder, encoder_in_dir_with_spaces) shutil.copy(decoder, decoder_in_dir_with_spaces) e = Encoding(["test external with spaces", constants.DECODING_EXTERNAL, decoder_in_dir_with_spaces + ";" + encoder_in_dir_with_spaces]) data = array.array("B", [1, 0, 1, 0, 0, 1, 1]) encoded = e.encode(data) self.assertEqual(encoded, array.array("B", [1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1])) decoded = e.decode(encoded) self.assertEqual(decoded, data)
def __set_wsp_encoding(self): self.form.compare_frame_controller.ui.cbProtoView.setCurrentText("Hex") decoding = Encoding(["WSP", constants.DECODING_ENOCEAN]) self.form.compare_frame_controller.decodings.append(decoding) self.form.compare_frame_controller.fill_decoding_combobox() self.form.compare_frame_controller.ui.tblViewProtocol.selectAll() self.form.compare_frame_controller.ui.cbDecoding.setCurrentText("WSP") model = self.form.compare_frame_controller.protocol_model self.assertEqual(len(model.display_data), 3) msg = "aa9610002c1c024b" for i in range(3): for j, hex_char in enumerate(msg): self.assertEqual(model.data(model.index(i, j)), hex_char)
def __init__(self, signal: Signal): self.messages = [] # type: list[Message] self.signal = signal self.filename = self.signal.filename if self.signal is not None else "" self.__name = "Blank" # Fallback if Signal has no Name self.show = Qt.Checked # Show in Compare Frame? self.qt_signals = ProtocolAnalyzerSignals() self.decoder = Encoding(["Non Return To Zero (NRZ)"]) # For Default Encoding of Protocol self.message_types = [MessageType("default")]
def test_enocean_crc8_message(self): e = Encoding() received = util.hex2bit( "aacbac4cddd5ddd3bddd5ddcc5ddcddd4c2d5d5c2cdddab200000") preamble, sof, eof = "aa", "9", "b" decoded, err, state = e.code_enocean(decoding=True, inpt=received) self.assertEqual(err, 0) self.assertEqual(state, e.ErrorState.SUCCESS) self.assertIn(preamble, util.bit2hex(decoded)) self.assertIn(sof, util.bit2hex(decoded)) self.assertIn(eof, util.bit2hex(decoded)) reencoded, errors, state = e.code_enocean(decoding=False, inpt=decoded) self.assertEqual(errors, 0) self.assertEqual(state, e.ErrorState.SUCCESS) redecoded, errors, state = e.code_enocean(decoding=True, inpt=reencoded) self.assertEqual(errors, 0) self.assertEqual(state, e.ErrorState.SUCCESS) self.assertEqual(decoded, redecoded)
def __set_cc1101_encoding(self): self.form.compare_frame_controller.ui.cbProtoView.setCurrentText("Hex") decoding = Encoding(["CC1101", constants.DECODING_DATAWHITENING, "0x9a7d9a7d;0x21"]) self.form.compare_frame_controller.decodings.append(decoding) self.form.compare_frame_controller.fill_decoding_combobox() self.form.compare_frame_controller.ui.tblViewProtocol.selectAll() self.form.compare_frame_controller.ui.cbDecoding.setCurrentText("CC1101") model = self.form.compare_frame_controller.protocol_model self.assertEqual(len(model.display_data), 1) msg = "aaaaaaaa9a7d9a7d0378e289757e" for j, hex_char in enumerate(msg): self.assertEqual(model.data(model.index(0, j)), hex_char, msg=str(j))
def test_substitution(self): e = Encoding() e.src = [array.array("B", [True, True, True, False]), array.array("B", [True, False, False, False])] e.dst = [array.array("B", [True]), array.array("B", [False])] # encoded-string with 3 missing trailing zeroes encoded = e.str2bit("1000111010001110111011101110111011101110100011101110111011101110111011101000100010001000100010001") compare = e.str2bit("1000111010001110111011101110111011101110100011101110111011101110111011101000100010001000100010001000") decoded, err, _ = e.code_substitution(decoding=True, inpt=encoded) reencoded, _, _ = e.code_substitution(decoding=False, inpt=decoded) self.assertEqual(err, 3) self.assertEqual(reencoded, compare)
def read_decoders_from_xml_tag(root: ET.Element): try: decoders = [] for decoding_tag in root.find("decodings").findall("decoding"): conf = [ d.strip().replace("'", "") for d in decoding_tag.text.split(",") if d.strip().replace("'", "") ] decoders.append(Encoding(conf)) return decoders except AttributeError: logger.error("no decodings found in xml") return []
def test_context_menu(self): self.dialog.ui.combobox_decodings.setCurrentIndex(4) decoding = Encoding(chain=[constants.DECODING_INVERT]) self.dialog.decodings[4] = decoding self.dialog.set_e() self.assertEqual(1, self.dialog.ui.decoderchain.count()) self.dialog.ui.decoderchain.context_menu_pos = QPoint(0, 0) menu = self.dialog.ui.decoderchain.create_context_menu() menu_actions = [ action.text() for action in menu.actions() if action.text() ] self.assertEqual(3, len(menu_actions))
def from_xml_tag(self, root: ET.Element, read_bits=False, participants=None, decodings=None): if not root: return None decoders = Encoding.read_decoders_from_xml_tag( root) if decodings is None else decodings if participants is None: participants = Participant.read_participants_from_xml_tag(root) if read_bits: self.messages[:] = [] try: message_types = [] for message_type_tag in root.find("message_types").findall( "message_type"): message_types.append(MessageType.from_xml(message_type_tag)) except AttributeError: message_types = [] for message_type in message_types: if message_type not in self.message_types: self.message_types.append(message_type) try: message_tags = root.find("messages").findall("message") for i, message_tag in enumerate(message_tags): if read_bits: self.messages.append( Message.new_from_xml(tag=message_tag, participants=participants, decoders=decoders, message_types=self.message_types)) else: try: self.messages[i].from_xml( tag=message_tag, participants=participants, decoders=decoders, message_types=self.message_types) except IndexError: pass # Part of signal was copied in last session but signal was not saved except AttributeError: pass
def saveas(self): # Ask for a name name, ok = QInputDialog.getText(self, self.tr("Save decoding"), self.tr("Please enter a name:"), QLineEdit.Normal, self.e.chain[0]) if ok and name != "": self.e.chain[0] = name self.decoderchainUpdate() # If name is already there, overwrite existing for i in range(0, len(self.decodings)): if name == self.decodings[i].name: self.ui.combobox_decodings.setCurrentIndex(i) self.decodings[i] = Encoding(self.chainstr) self.set_e() self.ui.saveas.setVisible(False) self.save_to_file() return self.decodings.append(Encoding(self.chainstr)) self.ui.combobox_decodings.addItem(self.chainstr[0]) self.ui.combobox_decodings.setCurrentIndex(self.ui.combobox_decodings.count() - 1) self.set_e() self.save_to_file()
def save_to_xml(self, standalone=False) -> ET.Element: result = ET.Element("simulator_config") if standalone: result.append(Modulator.modulators_to_xml_tag(self.project_manager.modulators)) result.append(Encoding.decodings_to_xml_tag(self.project_manager.decodings)) result.append(Participant.participants_to_xml_tag(self.project_manager.participants)) result.append(self.project_manager.simulator_rx_conf_to_xml()) result.append(self.project_manager.simulator_tx_conf_to_xml()) items_tag = ET.SubElement(result, "items") for item in self.rootItem.children: self.__save_item_to_xml(items_tag, item) return result
def save_to_xml(self, standalone=False) -> ET.Element: result = ET.Element("simulator_config") if standalone: result.append(Modulator.modulators_to_xml_tag(self.project_manager.modulators)) result.append(Encoding.decodings_to_xml_tag(self.project_manager.decodings)) result.append(Participant.participants_to_xml_tag(self.project_manager.participants)) result.append(self.project_manager.simulator_rx_conf_to_xml()) result.append(self.project_manager.simulator_tx_conf_to_xml()) items_tag = ET.SubElement(result, "items") for item in self.rootItem.children: self.__save_item_to_xml(items_tag, item) return result
def test_auto_interpretation_enocean(self): enocean_signal = np.fromfile(get_path_for_data_file("enocean.complex"), dtype=np.float32) result = AutoInterpretation.estimate(enocean_signal) mod_type, bit_length = result["modulation_type"], result["bit_length"] center, noise, tolerance = result["center"], result["noise"], result["tolerance"] self.assertEqual(mod_type, "ASK") self.assertGreaterEqual(center, 0.0077) self.assertLessEqual(center, 0.0465) self.assertLessEqual(tolerance, 5) self.assertEqual(bit_length, 40) demod = demodulate(enocean_signal, mod_type, bit_length, center, noise, tolerance, decoding=Encoding(["WSP", settings.DECODING_ENOCEAN])) self.assertEqual(len(demod), 3) self.assertEqual(demod[0], demod[2]) self.assertEqual(demod[0], "aa9610002c1c024b")
def test_morse(self): e = Encoding() e.morse_low = 3 e.morse_high = 5 e.morse_wait = 1 msg1 = "1111111000111100011111100100001111111111111111111111011" msg2 = "0111110111011111011101111101110" encoded = e.str2bit(msg1) compare = e.str2bit(msg2) decoded, err, _ = e.code_morse(decoding=True, inpt=encoded) reencoded, _, _ = e.code_morse(decoding=False, inpt=decoded) self.assertEqual(err, 1) self.assertEqual(reencoded, compare)
def test_enocean_crc_polynomial(self): e = Encoding() msg1 = "aa9a6d201006401009802019e411e8035b" msg2 = "aa9a6d2010000ffdaaf01019e411e8071b" # Remove Preamble + SOF + EOF for CRC calculation msg1 = util.hex2bit("a6d201006401009802019e411e8035") crc1 = util.hex2bit("35") msg2 = util.hex2bit("a6d2010000ffdaaf01019e411e8071") crc2 = util.hex2bit("71") wsp_checker = WSPChecksum() calc_crc1 = wsp_checker.calculate(msg1) calc_crc2 = wsp_checker.calculate(msg2) self.assertTrue(calc_crc1 == crc1) self.assertTrue(calc_crc2 == crc2)
def __init__(self, signal: Signal or None, filename=None): self.messages = [] # type: list[Message] self.signal = signal if filename is None: self.filename = self.signal.filename if self.signal is not None else "" else: assert signal is None self.filename = filename self.__name = urh_util.get_name_from_filename(filename) # Fallback if Signal has no Name self.show = Qt.Checked # Show in Compare Frame? self.qt_signals = ProtocolAnalyzerSignals() self.decoder = Encoding(["Non Return To Zero (NRZ)"]) # For Default Encoding of Protocol self.message_types = [MessageType("Default")]
def setUp(self): self.protocol = ProtocolAnalyzer(None) with open(get_path_for_data_file("decoded_bits.txt")) as f: for line in f: self.protocol.messages.append( Message.from_plain_bits_str(line.replace("\n", ""))) self.protocol.messages[ -1].message_type = self.protocol.default_message_type # Assign participants alice = Participant("Alice", "A") bob = Participant("Bob", "B") alice_indices = { 1, 2, 5, 6, 9, 10, 13, 14, 17, 18, 20, 22, 23, 26, 27, 30, 31, 34, 35, 38, 39, 41 } for i, message in enumerate(self.protocol.messages): if i in alice_indices: message.participant = alice else: message.participant = bob self.assertEqual(self.protocol.num_messages, 42) self.assertEqual(self.protocol.plain_hex_str[0][16:18], "2d") self.decodings = [] self.decodings.append(Encoding(['Non Return To Zero (NRZ)'])) self.decodings.append( Encoding(['Non Return To Zero Inverted (NRZ-I)', 'Invert'])) self.decodings.append(Encoding(['Manchester I', 'Edge Trigger'])) self.decodings.append( Encoding(['Manchester II', 'Edge Trigger', 'Invert'])) self.decodings.append( Encoding([ 'Differential Manchester', 'Edge Trigger', 'Differential Encoding', ])) self.decodings.append( Encoding([ 'DeWhitening Special', constants.DECODING_DATAWHITENING, '0x9a7d9a7d;0x21;0' ])) self.decodings.append( Encoding([ 'DeWhitening', constants.DECODING_DATAWHITENING, '0x67686768;0x21;0' ]))
def test_carrier(self): e = Encoding() # Test 1 e.carrier = "----1....1**" # or "....1....101", ... original_inpt = e.str2bit("000010000100111111111100") inpt = copy.copy(original_inpt) # print("\nOriginal:", inpt) output, err, _ = e.code_carrier(True, inpt) # print("Decoded: ", output, err) newinpt, err, _ = e.code_carrier(False, output) # print("Encoded: ", newinpt, err) self.assertEqual(original_inpt, newinpt)
def protocol(self): if isinstance(self.__itemData, ProtocolAnalyzer): if self.copy_data: if self.__data_copy is None: self.__data_copy = copy.deepcopy( self.__itemData) # type: ProtocolAnalyzer nrz = Encoding([""]) for message in self.__data_copy.messages: # type: Message decoded_bits = message.decoded_bits message.decoder = nrz message.plain_bits = decoded_bits self.__data_copy.qt_signals.show_state_changed.connect( self.__itemData.qt_signals.show_state_changed.emit) return self.__data_copy else: return self.__itemData else: return None
def load_decodings(self): if self.project_file: prefix = os.path.realpath(os.path.dirname(self.project_file)) else: prefix = os.path.realpath( os.path.join(constants.SETTINGS.fileName(), "..")) fallback = [ Encoding(["Non Return To Zero (NRZ)"]), Encoding([ "Non Return To Zero Inverted (NRZ-I)", constants.DECODING_INVERT ]), Encoding(["Manchester I", constants.DECODING_EDGE]), Encoding([ "Manchester II", constants.DECODING_EDGE, constants.DECODING_INVERT ]), Encoding([ "Differential Manchester", constants.DECODING_EDGE, constants.DECODING_DIFFERENTIAL ]) ] try: f = open(os.path.join(prefix, constants.DECODINGS_FILE), "r") except FileNotFoundError: self.decodings = fallback return if not f: self.decodings = fallback return decodings = [] for line in f: tmp_conf = [] for j in line.split(","): tmp = j.strip() tmp = tmp.replace("'", "") if not "\n" in tmp and tmp != "": tmp_conf.append(tmp) decodings.append(Encoding(tmp_conf)) f.close() if decodings: self.decodings = decodings else: self.decodings = fallback
def test_data_whitening(self): e = Encoding() nrz1 = util.string2bits("101010101010101010101010101010101110100111001010111010011100101011110011101011001001010011101110100011001011100111100111101011111110011100101001111111110011000111010000010111010101011100") nrz2 = util.string2bits("101010101010101010101010101010101110100111001010111010011100101011110001101011001011010000011101101101011101101110110011010010011010001010010010000101111001100111000100001001111110000000001000000010011") de_whitened1, err, _ = e.code_data_whitening(True, nrz1) # Decoding de_whitened2, err, _ = e.code_data_whitening(True, nrz2) # Decoding e.cc1101_overwrite_crc = False nrz1_, err, _ = e.code_data_whitening(False, de_whitened1) # Encoding without overwriting CRC nrz2_, err, _ = e.code_data_whitening(False, de_whitened2) # Encoding without overwriting CRC e.cc1101_overwrite_crc = True nrz1__, err, _ = e.code_data_whitening(False, de_whitened1) # Encoding with overwriting CRC nrz2__, err, _ = e.code_data_whitening(False, de_whitened2) # Encoding with overwriting CRC self.assertEqual(nrz1, nrz1_) self.assertEqual(nrz1, nrz1__) self.assertEqual(nrz2, nrz2_) self.assertEqual(nrz2, nrz2__)
def from_xml_tag(self, root: ET.Element, read_bits=False, participants=None, decodings=None): if not root: return None decoders = Encoding.read_decoders_from_xml_tag(root) if decodings is None else decodings if participants is None: participants = Participant.read_participants_from_xml_tag(root) if read_bits: self.messages[:] = [] try: message_types = [] for message_type_tag in root.find("message_types").findall("message_type"): message_types.append(MessageType.from_xml(message_type_tag)) except AttributeError: message_types = [] for message_type in message_types: if message_type not in self.message_types: self.message_types.append(message_type) try: message_tags = root.find("messages").findall("message") for i, message_tag in enumerate(message_tags): if read_bits: self.messages.append(Message.new_from_xml(tag=message_tag, participants=participants, decoders=decoders, message_types=self.message_types)) else: try: self.messages[i].from_xml(tag=message_tag, participants=participants, decoders=decoders, message_types=self.message_types) except IndexError: pass # Part of signal was copied in last session but signal was not saved except AttributeError: pass
def test_build_decoding(self): self.dialog.ui.combobox_decodings.setCurrentIndex(4) chain = [(constants.DECODING_INVERT, ), (constants.DECODING_ENOCEAN, ), (constants.DECODING_DIFFERENTIAL, ), (constants.DECODING_CARRIER, ), (constants.DECODING_BITORDER, ), (constants.DECODING_EDGE, ), (constants.DECODING_DATAWHITENING, ), (constants.DECODING_REDUNDANCY, "2"), (constants.DECODING_MORSE, "1;3;1"), (constants.DECODING_SUBSTITUTION, "0:1;1:0;"), (constants.DECODING_EXTERNAL, "./;./"), (constants.DECODING_CUT, "0;1010")] decoding = Encoding( chain=[c for chain_item in chain for c in chain_item]) self.dialog.decodings[4] = decoding self.dialog.set_e() self.assertEqual(len(chain), self.dialog.ui.decoderchain.count()) for i in range(0, self.dialog.ui.decoderchain.count()): self.dialog.ui.decoderchain.setCurrentRow(i) self.dialog.set_information(2) self.assertIn(chain[i][0], self.dialog.ui.info.text())
def load_from_xml(self, xml_tag: ET.Element, message_types): assert xml_tag.tag == "simulator_config" items = [] modulators_tag = xml_tag.find("modulators") if modulators_tag: self.project_manager.modulators = Modulator.modulators_from_xml_tag( modulators_tag) participants_tag = xml_tag.find("participants") if participants_tag: for participant in Participant.read_participants_from_xml_tag( participants_tag): if participant not in self.project_manager.participants: self.project_manager.participants.append(participant) self.participants_changed.emit() decodings_tag = xml_tag.find("decodings") if decodings_tag: self.project_manager.decodings = Encoding.read_decoders_from_xml_tag( decodings_tag) rx_config_tag = xml_tag.find("simulator_rx_conf") if rx_config_tag: ProjectManager.read_device_conf_dict( rx_config_tag, self.project_manager.simulator_rx_conf) tx_config_tag = xml_tag.find("simulator_tx_conf") if tx_config_tag: ProjectManager.read_device_conf_dict( tx_config_tag, self.project_manager.simulator_tx_conf) for child_tag in xml_tag.find("items"): items.append(self.load_item_from_xml(child_tag, message_types)) self.add_items(items, pos=0, parent_item=None)
def test_data_whitening(self): e = Encoding() nrz1 = util.string2bits("101010101010101010101010101010101110100111001010111010011100101011110011101011001001010011101110100011001011100111100111101011111110011100101001111111110011000111010000010111010101011100") nrz2 = util.string2bits("101010101010101010101010101010101110100111001010111010011100101011110001101011001011010000011101101101011101101110110011010010011010001010010010000101111001100111000100001001111110000000001000000010011") de_whitened1, err, _ = e.code_data_whitening(True, nrz1) # Decoding de_whitened2, err, _ = e.code_data_whitening(True, nrz2) # Decoding e.cc1101_overwrite_crc = False nrz1_, err, _ = e.code_data_whitening(False, de_whitened1) # Encoding without overwriting CRC nrz2_, err, _ = e.code_data_whitening(False, de_whitened2) # Encoding without overwriting CRC e.cc1101_overwrite_crc = True nrz1__, err, _ = e.code_data_whitening(False, de_whitened1) # Encoding with overwriting CRC nrz2__, err, _ = e.code_data_whitening(False, de_whitened2) # Encoding with overwriting CRC self.assertEqual(nrz1, nrz1_) self.assertEqual(nrz1, nrz1__) self.assertEqual(nrz2, nrz2_) self.assertEqual(nrz2, nrz2__)
def load_decodings(self): if self.project_file: return else: prefix = os.path.realpath( os.path.join(settings.get_qt_settings_filename(), "..")) fallback = [ Encoding(["Non Return To Zero (NRZ)"]), Encoding([ "Non Return To Zero Inverted (NRZ-I)", settings.DECODING_INVERT ]), Encoding(["Manchester I", settings.DECODING_EDGE]), Encoding([ "Manchester II", settings.DECODING_EDGE, settings.DECODING_INVERT ]), Encoding([ "Differential Manchester", settings.DECODING_EDGE, settings.DECODING_DIFFERENTIAL ]) ] try: f = open(os.path.join(prefix, settings.DECODINGS_FILE), "r") except FileNotFoundError: self.decodings = fallback return decodings = [] for line in map(str.strip, f): tmp_conf = [] for j in map(str.strip, line.split(",")): tmp_conf.append(j.replace("'", "")) decodings.append(Encoding(tmp_conf)) f.close() self.decodings = decodings if decodings else fallback
def setUp(self): super().setUp() self.add_signal_to_form("steckdose_anlernen.complex") self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxNoiseTreshold.setValue(0.06) self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxNoiseTreshold.editingFinished.emit() self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxCenterOffset.setValue(-0.0127) self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxCenterOffset.editingFinished.emit() self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxInfoLen.setValue(100) self.form.signal_tab_controller.signal_frames[ 0].ui.spinBoxInfoLen.editingFinished.emit() self.gframe = self.form.generator_tab_controller self.gframe.ui.cbViewType.setCurrentIndex(1) # hex view self.gframe.modulators.append( Modulator( "Prevent Modulation bootstrap when adding first protocol")) self.gframe.refresh_modulators() # Dewhitening mit SyncByte 0x9a7d9a7d, Data Whitening Poly 0x21, Compute and apply CRC16 via X0r, # Rest auf False anlegen und setzen self.form.ui.tabWidget.setCurrentIndex(1) self.form.compare_frame_controller.ui.cbProtoView.setCurrentIndex( 1) # Hex decoding = Encoding([ "Data Whitening", constants.DECODING_DATAWHITENING, "0x9a7d9a7d;0x21" ]) self.form.compare_frame_controller.decodings.append(decoding) self.form.compare_frame_controller.ui.cbDecoding.addItem(decoding.name) self.form.compare_frame_controller.set_decoding(decoding) # Serial Part 1: Bits 207-226 (Dezimal: 91412) (20 Bits) self.form.compare_frame_controller.add_protocol_label( start=206, end=225, messagenr=0, proto_view=0, edit_label_name=False) # Zeros: Bits 227-244 (18 Bits) self.form.compare_frame_controller.add_protocol_label( start=226, end=243, messagenr=0, proto_view=0, edit_label_name=False) # Serial Part 2: Bit 245 - 264 (Dezimal: 1034678) (20 Bits) self.form.compare_frame_controller.add_protocol_label( start=244, end=263, messagenr=0, proto_view=0, edit_label_name=False) self.form.ui.tabWidget.setCurrentIndex(2) item = self.gframe.tree_model.rootItem.children[0].children[0] index = self.gframe.tree_model.createIndex(0, 0, item) rect = self.gframe.ui.treeProtocols.visualRect(index) self.assertEqual(len(self.gframe.ui.treeProtocols.selectedIndexes()), 0) QTest.mousePress(self.gframe.ui.treeProtocols.viewport(), Qt.LeftButton, pos=rect.center()) self.assertEqual(self.gframe.ui.treeProtocols.selectedIndexes()[0], index) mimedata = self.gframe.tree_model.mimeData( self.gframe.ui.treeProtocols.selectedIndexes()) self.gframe.table_model.dropMimeData( mimedata, 1, -1, -1, self.gframe.table_model.createIndex(0, 0)) self.assertEqual(self.gframe.table_model.row_count, 1) self.assertEqual(len(self.gframe.table_model.protocol.protocol_labels), 3) self.dialog = FuzzingDialogController( protocol=self.gframe.table_model.protocol, label_index=0, msg_index=0, proto_view=0, parent=self.gframe) self.dialog.finished.connect(self.gframe.refresh_label_list) self.dialog.finished.connect(self.gframe.refresh_table) self.dialog.finished.connect(self.gframe.set_fuzzing_ui_status) if self.SHOW: self.dialog.show()
def set_project_folder(self, path, ask_for_new_project=True, close_all=True): if self.project_file is not None or close_all: # Close existing project (if any) or existing files if requested self.main_controller.close_all_files() FileOperator.RECENT_PATH = path util.PROJECT_PATH = path self.project_path = path self.project_file = os.path.join(self.project_path, constants.PROJECT_FILE) collapse_project_tabs = False if not os.path.isfile(self.project_file): if ask_for_new_project: reply = QMessageBox.question( self.main_controller, "Project File", "Do you want to create a Project File for this folder?\n" "If you chose No, you can do it later via File->Convert Folder to Project.", QMessageBox.Yes | QMessageBox.No) if reply == QMessageBox.Yes: self.main_controller.show_project_settings() else: self.project_file = None if self.project_file is not None: root = ET.Element("UniversalRadioHackerProject") tree = ET.ElementTree(root) tree.write(self.project_file) self.modulation_was_edited = False else: tree = ET.parse(self.project_file) root = tree.getroot() collapse_project_tabs = bool( int(root.get("collapse_project_tabs", 0))) self.modulation_was_edited = bool( int(root.get("modulation_was_edited", 0))) cfc = self.main_controller.compare_frame_controller self.read_parameters(root) self.participants[:] = Participant.read_participants_from_xml_tag( xml_tag=root.find("protocol")) self.main_controller.add_files(self.read_opened_filenames()) self.read_compare_frame_groups(root) self.decodings = Encoding.read_decoders_from_xml_tag( root.find("protocol")) cfc.proto_analyzer.message_types[:] = self.read_message_types() cfc.message_type_table_model.update() cfc.proto_analyzer.from_xml_tag(root=root.find("protocol"), participants=self.participants, decodings=cfc.decodings) cfc.updateUI() try: for message_type in cfc.proto_analyzer.message_types: for lbl in filter(lambda x: not x.show, message_type): cfc.set_protocol_label_visibility(lbl) except Exception as e: logger.exception(e) self.modulators = self.read_modulators_from_project_file() self.main_controller.simulator_tab_controller.load_config_from_xml_tag( root.find("simulator_config")) if len(self.project_path) > 0 and self.project_file is None: self.main_controller.ui.actionConvert_Folder_to_Project.setEnabled( True) else: self.main_controller.ui.actionConvert_Folder_to_Project.setEnabled( False) self.main_controller.adjust_for_current_file(path) self.main_controller.filemodel.setRootPath(path) self.main_controller.ui.fileTree.setRootIndex( self.main_controller.file_proxy_model.mapFromSource( self.main_controller.filemodel.index(path))) self.main_controller.ui.fileTree.setToolTip(path) self.main_controller.ui.splitter.setSizes([1, 1]) if collapse_project_tabs: self.main_controller.collapse_project_tab_bar() else: self.main_controller.expand_project_tab_bar() self.main_controller.setWindowTitle("Universal Radio Hacker [" + path + "]") self.project_loaded_status_changed.emit(self.project_loaded) self.project_updated.emit()
def set_project_folder(self, path, ask_for_new_project=True, close_all=True): if self.project_file is not None or close_all: # Close existing project (if any) or existing files if requested self.main_controller.close_all_files() FileOperator.RECENT_PATH = path util.PROJECT_PATH = path self.project_path = path self.project_file = os.path.join(self.project_path, constants.PROJECT_FILE) collapse_project_tabs = False if not os.path.isfile(self.project_file): if ask_for_new_project: reply = QMessageBox.question(self.main_controller, "Project File", "Do you want to create a Project File for this folder?\n" "If you chose No, you can do it later via File->Convert Folder to Project.", QMessageBox.Yes | QMessageBox.No) if reply == QMessageBox.Yes: self.main_controller.show_project_settings() else: self.project_file = None if self.project_file is not None: root = ET.Element("UniversalRadioHackerProject") tree = ET.ElementTree(root) tree.write(self.project_file) self.modulation_was_edited = False else: tree = ET.parse(self.project_file) root = tree.getroot() collapse_project_tabs = bool(int(root.get("collapse_project_tabs", 0))) self.modulation_was_edited = bool(int(root.get("modulation_was_edited", 0))) cfc = self.main_controller.compare_frame_controller self.read_parameters(root) self.participants[:] = Participant.read_participants_from_xml_tag(xml_tag=root.find("protocol")) self.main_controller.add_files(self.read_opened_filenames()) self.read_compare_frame_groups(root) self.decodings = Encoding.read_decoders_from_xml_tag(root.find("protocol")) cfc.proto_analyzer.message_types[:] = self.read_message_types() cfc.message_type_table_model.update() cfc.proto_analyzer.from_xml_tag(root=root.find("protocol"), participants=self.participants, decodings=cfc.decodings) cfc.updateUI() try: for message_type in cfc.proto_analyzer.message_types: for lbl in filter(lambda x: not x.show, message_type): cfc.set_protocol_label_visibility(lbl) except Exception as e: logger.exception(e) self.modulators = self.read_modulators_from_project_file() self.main_controller.simulator_tab_controller.load_config_from_xml_tag(root.find("simulator_config")) if len(self.project_path) > 0 and self.project_file is None: self.main_controller.ui.actionConvert_Folder_to_Project.setEnabled(True) else: self.main_controller.ui.actionConvert_Folder_to_Project.setEnabled(False) self.main_controller.adjust_for_current_file(path) self.main_controller.filemodel.setRootPath(path) self.main_controller.ui.fileTree.setRootIndex( self.main_controller.file_proxy_model.mapFromSource(self.main_controller.filemodel.index(path))) self.main_controller.ui.fileTree.setToolTip(path) self.main_controller.ui.splitter.setSizes([1, 1]) if collapse_project_tabs: self.main_controller.collapse_project_tab_bar() else: self.main_controller.expand_project_tab_bar() self.main_controller.setWindowTitle("Universal Radio Hacker [" + path + "]") self.project_loaded_status_changed.emit(self.project_loaded) self.project_updated.emit()
def build_encoding_from_args(arguments: argparse.Namespace): if arguments.encoding is None: return None primitives = arguments.encoding.split(",") return Encoding(list(filter(None, map(str.strip, primitives))))
def test_cut_decoding(self): e = Encoding() received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("1010010101111111000") e.cutmode = 0 e.cutmark = [True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("00001010") e.cutmode = 1 e.cutmark = [True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("001010010101111111000") e.cutmode = 2 e.cutmark = 2 decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("000") e.cutmode = 3 e.cutmark = 2 decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("00001010010101111111000") e.cutmode = 0 e.cutmark = [True, False, True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result)
def test_cut_decoding(self): e = Encoding() received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("1010010101111111000") e.cutmode = 0 e.cutmark = [True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("00001010") e.cutmode = 1 e.cutmark = [True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("001010010101111111000") e.cutmode = 2 e.cutmark = 2 decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("000") e.cutmode = 3 e.cutmark = 2 decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit("00001010010101111111000") expected_result = e.str2bit("00001010010101111111000") e.cutmode = 0 e.cutmark = [True, False, True, False, True, False] decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result) received = e.str2bit( "11010101010101010101010101010101011101001110010101110100111001010000100011011111110000100001011100101010101111101111010000001110101111010000100000110100000010011011110101100100011110000100011011100010100111100000000000000000" ) expected_result = e.str2bit( "1010101010101010101010101010101011101001110010101110100111001010000100011011111110000100001011100101010101111101111010000001110101111010000100000110100000010011011110101100100011110000100011011100010100111100000000000000000" ) e.cutmode = 0 e.cutmark = e.str2bit("10101010101010101010101010101010") decoded, err, _ = e.code_cut(True, received) self.assertEqual(decoded, expected_result)