Merge branch 'main' into hw-slot-info

This commit is contained in:
Philippe Teuwen
2023-08-20 00:11:42 +02:00
committed by GitHub
7 changed files with 169 additions and 61 deletions
+6 -1
View File
@@ -116,6 +116,7 @@ class ChameleonCLI:
'settings': new_uint(chameleon_cli_unit.HFMFSettings, "Settings of Mifare Classic emulator"),
'sim': new_uint(chameleon_cli_unit.HFMFSim, "Simulate a Mifare Classic card"),
'eload': new_uint(chameleon_cli_unit.HFMFELoad, "Load data to emulator memory"),
'eread': new_uint(chameleon_cli_unit.HFMFERead, "Read data from emulator memory"),
'help': "Mifare Classic mini/1/2/4, attack/read/write"
},
'help': "high frequency tag/reader",
@@ -124,7 +125,11 @@ class ChameleonCLI:
'em': {
'read': new_uint(chameleon_cli_unit.LFEMRead, "Scan em410x tag and print id"),
'write': new_uint(chameleon_cli_unit.LFEMWriteT55xx, "Write em410x id to t55xx"),
'sim': new_uint(chameleon_cli_unit.LFEMSim, "Simulation a em410x id card"),
'sim': {
'set': new_uint(chameleon_cli_unit.LFEMSimSet, "Set simulated em410x card id"),
'get': new_uint(chameleon_cli_unit.LFEMSimGet, "Get simulated em410x card id"),
'help': "Manage EM410x emulation data for selected slot"
},
'help': "EM410x read/write/emulator",
},
'help': "low frequency tag/reader",
+64 -3
View File
@@ -1,3 +1,4 @@
import binascii
import os
import re
import subprocess
@@ -681,6 +682,55 @@ class HFMFELoad(DeviceRequiredUnit):
block += 1
print("\n - Load success")
class HFMFERead(DeviceRequiredUnit):
def args_parser(self) -> ArgumentParserNoExit or None:
parser = ArgumentParserNoExit()
parser.add_argument('-f', '--file', type=str, required=True, help="file path")
parser.add_argument('-t', '--type', type=str, required=False, help="content type", choices=['bin', 'hex'])
return parser
def on_exec(self, args: argparse.Namespace):
file = args.file
if args.type is None:
if file.endswith('.bin'):
content_type = 'bin'
elif file.endswith('.eml'):
content_type = 'hex'
else:
raise Exception("Unknown file format, Specify content type with -t option")
else:
content_type = args.type
selected_slot = self.cmd_positive.get_active_slot().data[0]
slot_info = self.cmd_positive.get_slot_info().data
tag_type = chameleon_cmd.TagSpecificType(slot_info[selected_slot * 2])
if tag_type == chameleon_cmd.TagSpecificType.TAG_TYPE_MIFARE_Mini:
block_count = 20
elif tag_type == chameleon_cmd.TagSpecificType.TAG_TYPE_MIFARE_1024:
block_count = 64
elif tag_type == chameleon_cmd.TagSpecificType.TAG_TYPE_MIFARE_2048:
block_count = 128
elif tag_type == chameleon_cmd.TagSpecificType.TAG_TYPE_MIFARE_4096:
block_count = 256
else:
raise Exception("Card in current slot is not Mifare Classic/Plus in SL1 mode")
with open(file, 'wb') as fd:
block = 0
while block < block_count:
response = self.cmd_positive.get_mf1_block_data(block, 1)
print('.', end='')
block += 1
if content_type == 'hex':
hex_char_repr = binascii.hexlify(response.data)
fd.write(hex_char_repr)
fd.write(bytes([0x0a]))
else:
fd.write(response.data)
print("\n - Read success")
class HFMFSettings(DeviceRequiredUnit):
def args_parser(self) -> ArgumentParserNoExit or None:
@@ -965,18 +1015,29 @@ class HWSlotEnableSet(SlotIndexRequireUint):
print(f' - Set slot {slot_num} {"enable" if enable else "disable"} success.')
class LFEMSim(LFEMCardRequiredUint):
class LFEMSimSet(LFEMCardRequiredUint):
def args_parser(self) -> ArgumentParserNoExit or None:
parser = ArgumentParserNoExit()
return self.add_card_arg(parser)
# lf em sim --id 4545454545
# lf em sim set --id 4545454545
def on_exec(self, args: argparse.Namespace):
id_hex = args.id
id_bytes = bytearray.fromhex(id_hex)
self.cmd_positive.set_em140x_sim_id(id_bytes)
self.cmd_positive.set_em410x_sim_id(id_bytes)
print(f' - Set em410x tag id success.')
class LFEMSimGet(DeviceRequiredUnit):
def args_parser(self) -> ArgumentParserNoExit or None:
return None
# lf em sim get
def on_exec(self, args: argparse.Namespace):
response = self.cmd_positive.get_em410x_sim_id()
print(f' - Get em410x tag id success.')
print(f'ID: {response.data.hex()}')
class HWSlotNickSet(SlotIndexRequireUint, SenseTypeRequireUint):
def args_parser(self) -> ArgumentParserNoExit or None:
+26 -8
View File
@@ -1,4 +1,5 @@
import enum
import struct
import chameleon_com
import chameleon_status
@@ -48,9 +49,15 @@ DATA_CMD_MF1_WRITE_ONE_BLOCK = 2009
DATA_CMD_SCAN_EM410X_TAG = 3000
DATA_CMD_WRITE_EM410X_TO_T5577 = 3001
DATA_CMD_LOAD_MF1_BLOCK_DATA = 4000
DATA_CMD_LOAD_MF1_EMU_BLOCK_DATA = 4000
DATA_CMD_SET_MF1_ANTI_COLLISION_RES = 4001
DATA_CMD_SET_MF1_DETECTION_ENABLE = 4004
DATA_CMD_GET_MF1_DETECTION_COUNT = 4005
DATA_CMD_GET_MF1_DETECTION_RESULT = 4006
DATA_CMD_READ_MF1_EMU_BLOCK_DATA = 4008
DATA_CMD_GET_MF1_EMULATOR_CONFIG = 4009
DATA_CMD_GET_MF1_GEN1A_MODE = 4010
DATA_CMD_SET_MF1_GEN1A_MODE = 4011
@@ -62,9 +69,7 @@ DATA_CMD_GET_MF1_WRITE_MODE = 4016
DATA_CMD_SET_MF1_WRITE_MODE = 4017
DATA_CMD_SET_EM410X_EMU_ID = 5000
DATA_CMD_SET_MF1_DETECTION_ENABLE = 5003
DATA_CMD_GET_MF1_DETECTION_COUNT = 5004
DATA_CMD_GET_MF1_DETECTION_RESULT = 5005
DATA_CMD_GET_EM410X_EMU_ID = 5001
@enum.unique
@@ -439,7 +444,7 @@ class BaseChameleonCMD:
data.append(0x01 if enable else 0x00)
return self.device.send_cmd_sync(DATA_CMD_SET_SLOT_ENABLE, 0X00, data)
def set_em140x_sim_id(self, id_bytes: bytearray):
def set_em410x_sim_id(self, id_bytes: bytearray):
"""
设置EM410x模拟的卡号
:param id_bytes: 卡号的字节
@@ -448,6 +453,12 @@ class BaseChameleonCMD:
if len(id_bytes) != 5:
raise ValueError("The id bytes length must equal 5")
return self.device.send_cmd_sync(DATA_CMD_SET_EM410X_EMU_ID, 0x00, id_bytes)
def get_em410x_sim_id(self):
"""
Get the simulated EM410x card id
"""
return self.device.send_cmd_sync(DATA_CMD_GET_EM410X_EMU_ID, 0x00)
def set_mf1_detection_enable(self, enable: bool):
"""
@@ -486,7 +497,14 @@ class BaseChameleonCMD:
data = bytearray()
data.append(block_start & 0xFF)
data.extend(block_data)
return self.device.send_cmd_sync(DATA_CMD_LOAD_MF1_BLOCK_DATA, 0x00, data)
return self.device.send_cmd_sync(DATA_CMD_LOAD_MF1_EMU_BLOCK_DATA, 0x00, data)
def get_mf1_block_data(self, block_start: int, block_count: int):
"""
Gets data for selected block range
"""
data = struct.pack('<BH', block_start, block_count)
return self.device.send_cmd_sync(DATA_CMD_READ_MF1_EMU_BLOCK_DATA, 0x00, data)
def set_mf1_anti_collision_res(self, sak: bytearray, atqa: bytearray, uid: bytearray):
"""
@@ -710,8 +728,8 @@ class PositiveChameleonCMD(BaseChameleonCMD):
self.check_status(ret.status, chameleon_status.Device.STATUS_DEVICE_SUCCESS)
return ret
def set_em140x_sim_id(self, id_bytes: bytearray):
ret = super(PositiveChameleonCMD, self).set_em140x_sim_id(id_bytes)
def set_em410x_sim_id(self, id_bytes: bytearray):
ret = super(PositiveChameleonCMD, self).set_em410x_sim_id(id_bytes)
self.check_status(ret.status, chameleon_status.Device.STATUS_DEVICE_SUCCESS)
return ret