"""
Скрипт, выводящий информацию о содержании Rich-сигнатуры PE-файла.

Пример использования:

    python get_rich_info.py d:/file.exe
"""

import sys
import hashlib
import pefile

__COMPID_DICT = {
    0: 'Unknown',
    1: 'Import0',
    2: 'Linker510',
    3: 'Cvtomf510',
    4: 'Linker600',
    5: 'Cvtomf600',
    6: 'Cvtres500',
    7: 'Utc11_Basic',
    8: 'Utc11_C',
    9: 'Utc12_Basic',
    10: 'Utc12_C',
    11: 'Utc12_CPP',
    12: 'AliasObj60',
    13: 'VisualBasic60',
    14: 'Masm613',
    15: 'Masm710',
    16: 'Linker511',
    17: 'Cvtomf511',
    18: 'Masm614',
    19: 'Linker512',
    20: 'Cvtomf512',
    21: 'Utc12_C_Std',
    22: 'Utc12_CPP_Std',
    23: 'Utc12_C_Book',
    24: 'Utc12_CPP_Book',
    25: 'Implib700',
    26: 'Cvtomf700',
    27: 'Utc13_Basic',
    28: 'Utc13_C',
    29: 'Utc13_CPP',
    30: 'Linker610',
    31: 'Cvtomf610',
    32: 'Linker601',
    33: 'Cvtomf601',
    34: 'Utc12_1_Basic',
    35: 'Utc12_1_C',
    36: 'Utc12_1_CPP',
    37: 'Linker620',
    38: 'Cvtomf620',
    39: 'AliasObj70',
    40: 'Linker621',
    41: 'Cvtomf621',
    42: 'Masm615',
    43: 'Utc13_LTCG_C',
    44: 'Utc13_LTCG_CPP',
    45: 'Masm620',
    46: 'ILAsm100',
    47: 'Utc12_2_Basic',
    48: 'Utc12_2_C',
    49: 'Utc12_2_CPP',
    50: 'Utc12_2_C_Std',
    51: 'Utc12_2_CPP_Std',
    52: 'Utc12_2_C_Book',
    53: 'Utc12_2_CPP_Book',
    54: 'Implib622',
    55: 'Cvtomf622',
    56: 'Cvtres501',
    57: 'Utc13_C_Std',
    58: 'Utc13_CPP_Std',
    59: 'Cvtpgd1300',
    60: 'Linker622',
    61: 'Linker700',
    62: 'Export622',
    63: 'Export700',
    64: 'Masm700',
    65: 'Utc13_POGO_I_C',
    66: 'Utc13_POGO_I_CPP',
    67: 'Utc13_POGO_O_C',
    68: 'Utc13_POGO_O_CPP',
    69: 'Cvtres700',
    70: 'Cvtres710p',
    71: 'Linker710p',
    72: 'Cvtomf710p',
    73: 'Export710p',
    74: 'Implib710p',
    75: 'Masm710p',
    76: 'Utc1310p_C',
    77: 'Utc1310p_CPP',
    78: 'Utc1310p_C_Std',
    79: 'Utc1310p_CPP_Std',
    80: 'Utc1310p_LTCG_C',
    81: 'Utc1310p_LTCG_CPP',
    82: 'Utc1310p_POGO_I_C',
    83: 'Utc1310p_POGO_I_CPP',
    84: 'Utc1310p_POGO_O_C',
    85: 'Utc1310p_POGO_O_CPP',
    86: 'Linker624',
    87: 'Cvtomf624',
    88: 'Export624',
    89: 'Implib624',
    90: 'Linker710',
    91: 'Cvtomf710',
    92: 'Export710',
    93: 'Implib710',
    94: 'Cvtres710',
    95: 'Utc1310_C',
    96: 'Utc1310_CPP',
    97: 'Utc1310_C_Std',
    98: 'Utc1310_CPP_Std',
    99: 'Utc1310_LTCG_C',
    100: 'Utc1310_LTCG_CPP',
    101: 'Utc1310_POGO_I_C',
    102: 'Utc1310_POGO_I_CPP',
    103: 'Utc1310_POGO_O_C',
    104: 'Utc1310_POGO_O_CPP',
    105: 'AliasObj710',
    106: 'AliasObj710p',
    107: 'Cvtpgd1310',
    108: 'Cvtpgd1310p',
    109: 'Utc1400_C',
    110: 'Utc1400_CPP',
    111: 'Utc1400_C_Std',
    112: 'Utc1400_CPP_Std',
    113: 'Utc1400_LTCG_C',
    114: 'Utc1400_LTCG_CPP',
    115: 'Utc1400_POGO_I_C',
    116: 'Utc1400_POGO_I_CPP',
    117: 'Utc1400_POGO_O_C',
    118: 'Utc1400_POGO_O_CPP',
    119: 'Cvtpgd1400',
    120: 'Linker800',
    121: 'Cvtomf800',
    122: 'Export800',
    123: 'Implib800',
    124: 'Cvtres800',
    125: 'Masm800',
    126: 'AliasObj800',
    127: 'PhoenixPrerelease',
    128: 'Utc1400_CVTCIL_C',
    129: 'Utc1400_CVTCIL_CPP',
    130: 'Utc1400_LTCG_MSIL',
    131: 'Utc1500_C',
    132: 'Utc1500_CPP',
    133: 'Utc1500_C_Std',
    134: 'Utc1500_CPP_Std',
    135: 'Utc1500_CVTCIL_C',
    136: 'Utc1500_CVTCIL_CPP',
    137: 'Utc1500_LTCG_C',
    138: 'Utc1500_LTCG_CPP',
    139: 'Utc1500_LTCG_MSIL',
    140: 'Utc1500_POGO_I_C',
    141: 'Utc1500_POGO_I_CPP',
    142: 'Utc1500_POGO_O_C',
    143: 'Utc1500_POGO_O_CPP',
    144: 'Cvtpgd1500',
    145: 'Linker900',
    146: 'Export900',
    147: 'Implib900',
    148: 'Cvtres900',
    149: 'Masm900',
    150: 'AliasObj900',
    151: 'Resource900',
    152: 'AliasObj1000',
    153: 'Cvtpgd1600',
    154: 'Cvtres1000',
    155: 'Export1000',
    156: 'Implib1000',
    157: 'Linker1000',
    158: 'Masm1000',
    159: 'Phx1600_C',
    160: 'Phx1600_CPP',
    161: 'Phx1600_CVTCIL_C',
    162: 'Phx1600_CVTCIL_CPP',
    163: 'Phx1600_LTCG_C',
    164: 'Phx1600_LTCG_CPP',
    165: 'Phx1600_LTCG_MSIL',
    166: 'Phx1600_POGO_I_C',
    167: 'Phx1600_POGO_I_CPP',
    168: 'Phx1600_POGO_O_C',
    169: 'Phx1600_POGO_O_CPP',
    170: 'Utc1600_C',
    171: 'Utc1600_CPP',
    172: 'Utc1600_CVTCIL_C',
    173: 'Utc1600_CVTCIL_CPP',
    174: 'Utc1600_LTCG_C ',
    175: 'Utc1600_LTCG_CPP',
    176: 'Utc1600_LTCG_MSIL',
    177: 'Utc1600_POGO_I_C',
    178: 'Utc1600_POGO_I_CPP',
    179: 'Utc1600_POGO_O_C',
    180: 'Utc1600_POGO_O_CPP',
    181: 'AliasObj1010',
    182: 'Cvtpgd1610',
    183: 'Cvtres1010',
    184: 'Export1010',
    185: 'Implib1010',
    186: 'Linker1010',
    187: 'Masm1010',
    188: 'Utc1610_C',
    189: 'Utc1610_CPP',
    190: 'Utc1610_CVTCIL_C',
    191: 'Utc1610_CVTCIL_CPP',
    192: 'Utc1610_LTCG_C ',
    193: 'Utc1610_LTCG_CPP',
    194: 'Utc1610_LTCG_MSIL',
    195: 'Utc1610_POGO_I_C',
    196: 'Utc1610_POGO_I_CPP',
    197: 'Utc1610_POGO_O_C',
    198: 'Utc1610_POGO_O_CPP',
    199: 'AliasObj1100',
    200: 'Cvtpgd1700',
    201: 'Cvtres1100',
    202: 'Export1100',
    203: 'Implib1100',
    204: 'Linker1100',
    205: 'Masm1100',
    206: 'Utc1700_C',
    207: 'Utc1700_CPP',
    208: 'Utc1700_CVTCIL_C',
    209: 'Utc1700_CVTCIL_CPP',
    210: 'Utc1700_LTCG_C ',
    211: 'Utc1700_LTCG_CPP',
    212: 'Utc1700_LTCG_MSIL',
    213: 'Utc1700_POGO_I_C',
    214: 'Utc1700_POGO_I_CPP',
    215: 'Utc1700_POGO_O_C',
    216: 'Utc1700_POGO_O_CPP',
    217: 'AliasObj1200',
    218: 'Cvtpgd1800',
    219: 'Cvtres1200',
    220: 'Export1200',
    221: 'Implib1200',
    222: 'Linker1200',
    223: 'Masm1200',
    224: 'Utc1800_C',
    225: 'Utc1800_CPP',
    226: 'Utc1800_CVTCIL_C',
    227: 'Utc1800_CVTCIL_CPP',
    228: 'Utc1800_LTCG_C ',
    229: 'Utc1800_LTCG_CPP',
    230: 'Utc1800_LTCG_MSIL',
    231: 'Utc1800_POGO_I_C',
    232: 'Utc1800_POGO_I_CPP',
    233: 'Utc1800_POGO_O_C',
    234: 'Utc1800_POGO_O_CPP',
    235: 'AliasObj1210',
    236: 'Cvtpgd1810',
    237: 'Cvtres1210',
    238: 'Export1210',
    239: 'Implib1210',
    240: 'Linker1210',
    241: 'Masm1210',
    242: 'Utc1810_C',
    243: 'Utc1810_CPP',
    244: 'Utc1810_CVTCIL_C',
    245: 'Utc1810_CVTCIL_CPP',
    246: 'Utc1810_LTCG_C ',
    247: 'Utc1810_LTCG_CPP',
    248: 'Utc1810_LTCG_MSIL',
    249: 'Utc1810_POGO_I_C',
    250: 'Utc1810_POGO_I_CPP',
    251: 'Utc1810_POGO_O_C',
    252: 'Utc1810_POGO_O_CPP',
    253: 'AliasObj1400',
    254: 'Cvtpgd1900',
    255: 'Cvtres1400',
    256: 'Export1400',
    257: 'Implib1400',
    258: 'Linker1400',
    259: 'Masm1400',
    260: 'Utc1900_C',
    261: 'Utc1900_CPP',
    262: 'Utc1900_CVTCIL_C',
    263: 'Utc1900_CVTCIL_CPP',
    264: 'Utc1900_LTCG_C ',
    265: 'Utc1900_LTCG_CPP',
    266: 'Utc1900_LTCG_MSIL',
    267: 'Utc1900_POGO_I_C',
    268: 'Utc1900_POGO_I_CPP',
    269: 'Utc1900_POGO_O_C',
    270: 'Utc1900_POGO_O_CPP',
}

try:
    file_path = sys.argv[1]
except IndexError:
    print('Не указан файл для поиска RICH сигнатуры.')
    sys.exit(0)
try:
    pe = pefile.PE(file_path)
except FileNotFoundError:
    print('Не удается найти указанный файл:', sys.argv[1])
    sys.exit(0)
except pefile.PEFormatError:
    print('Файл', sys.argv[1], 'не является PE файлом Windows.')
    sys.exit(0)
if pe.RICH_HEADER is not None:
    print('Rich key: ', pe.RICH_HEADER.key.hex())
    for i in range(0, len(getattr(pe.RICH_HEADER, 'values', [])), 2):
        comp_id = pe.RICH_HEADER.values[i]
        comp_cnt = pe.RICH_HEADER.values[i + 1]
        comp_name = __COMPID_DICT.get((comp_id & 0xffff0000) >> 16, '*Unknown*')
        comp_build = comp_id & 0xffff
        print(comp_name)
        print('\tbuild:', comp_build)
        print('\tcount:', comp_cnt)
    hasher = hashlib.new('md5')
    for i in range(0, len(getattr(pe.RICH_HEADER, 'values', []))):
        hasher.update(pe.RICH_HEADER.values[i].to_bytes(8, byteorder='little'))
    print('MD5 хеш от RICH сигнатуры:', hasher.hexdigest())
else:
    print('Файл', sys.argv[1], 'не содержит RICH сигнатуру.')
