Files
WindowsXPKg/extras/pidgenx.ipynb
T
TheTank20andWitherOrNot f7427792e3 Add Wither's gists as references (#137)
* Add Wither's gists as references

* remove broken ones

---------

Co-authored-by: WitherOrNot <damemem@gmail.com>
2025-07-09 20:12:49 -05:00

12 KiB

The math in this notebook is described in this patent. Be warned, the math is very complicated.

In [ ]:
# Windows 7 Retail/GVLK, public key ID 170

pubkey_data = {
    "field": {
        "modulus": 886368969471450739924935101400677,
        "ec_base_order": 886368969471450710152985728350703,
        "k3_minpoly": [
            4,
            1,
            0,
            1
        ],
        "k6_minpoly": [
            2,
            0,
            1
        ]
    },
    "h1_bases": [
        1,
        3,
        8,
        15,
        15,
        15,
        31,
        3,
        3,
        3,
        3,
        3,
        7,
        63
    ],
    "curve": {
        "a": 26392827536965106777121445123290,
        "b": 372325368096095544195525883520589
    },
    "points": [
        {
            "x": [
                365236101742748463929673543888206,
                858097895593939865996182272259769,
                148438159087534462792506738986740
            ],
            "y": [
                776418047571862972603801173382237,
                873677028107508092012208744232957,
                622138327043805563266794621920098
            ]
        },
        {
            "x": [
                940136574680879136511599445781,
                566978253317108608042529258054523,
                176284220413545220121710961573292
            ],
            "y": [
                828856809691743749590800150937649,
                225146018128364550960496522448712,
                348601659612301002638949468744847
            ]
        },
        {
            "x": [
                733747358623171948496764545320051,
                728506535527490173098593825125337,
                82462451162574422717677160727098
            ],
            "y": [
                416331132638004657079841565104549,
                366794872410090667339979925100938,
                154519017608105570119249112044121
            ]
        },
        {
            "x": [
                849718119860311390685018324089317,
                69736499980142833460080381132368,
                72139323263966224829624934948858
            ],
            "y": [
                122550620604034160835298121626961,
                232865179257577260620478614346661,
                96495922331236902442197840422963
            ]
        },
        {
            "x": [
                737949449696062407373114808812927,
                526576673882551145431025311648593,
                577710732700754839750249914833193
            ],
            "y": [
                245977198113437420529250724111432,
                316396368275232555978824338443046,
                755792900000892204654488821885538
            ]
        },
        {
            "x": [
                712586405875738967442641545880322,
                615445286425878710157557053762371,
                734183236086095230968388017605820
            ],
            "y": [
                851284376759840359812981263306021,
                769237654873203944088649987250083,
                359324880331507581802773028306633
            ]
        },
        {
            "x": [
                579665839598807564349118802507078,
                793103874095793223248478622956780,
                502860226530799804560661048077280
            ],
            "y": [
                526775274489316486107329470634542,
                828721161962151275145535457964404,
                204415317809040518371881977645416
            ]
        },
        {
            "x": [
                804790447447351785544412956578788,
                119046642031064430140912082580578,
                475159529884254928674792290619954
            ],
            "y": [
                458245266057063984580129835988070,
                338411981227059768831710308435687,
                577923375329917551735757167190702
            ]
        },
        {
            "x": [
                448295070796654878810211055051604,
                482910785083759911781193909334072,
                795628820954832750108065551162801
            ],
            "y": [
                417757375223493128894380427308216,
                755520039102173573177271365439537,
                863842006193777913816171128026446
            ]
        },
        {
            "x": [
                663389221842281261857262032548436,
                846447543951704162020988219326272,
                686142287698732386980948449542167
            ],
            "y": [
                769015970121598916167134609518482,
                738460771147019950148429256265493,
                613009789239563486872501072748270
            ]
        },
        {
            "x": [
                23530113060362511985797534739195,
                718131004725002854064127778364823,
                140870968646848990835780066321375
            ],
            "y": [
                641031697928634900295866764583620,
                295544383156746469642549388283327,
                133766761871461067699690599056442
            ]
        },
        {
            "x": [
                7518354584460889742005963384331,
                340825540582760123772991939806390,
                525549834323799848592419044187971
            ],
            "y": [
                585295007893871934790357000030208,
                117490751031779271453224407217079,
                838852298106199238437827740364400
            ]
        },
        {
            "x": [
                806036388470182281562651653929939,
                266085928879449679004785507000719,
                201474020142460453395308745398496
            ],
            "y": [
                573468377549807523205344415925956,
                667459718759242575444856430313959,
                226975716159080217447594275999935
            ]
        },
        {
            "x": [
                794167987155642331621801361756614,
                809201520617560616339201020039820,
                198696155869194654384403079624544
            ],
            "y": [
                725959545288387914551997303844726,
                49262476800238214847233993847181,
                537326577113493149345527624223733
            ]
        }
    ],
    "pairing_val": [
        [
            242940802691096077821709859741616,
            178851543248946074944443141484182,
            802059826004050667481466713086225
        ],
        [
            701042518368651902930590425782509,
            265571225406900742458432149860962,
            699432283102586243018242179516873
        ]
    ]
}
In [ ]:
p = pubkey_data["field"]["modulus"]
a = pubkey_data["curve"]["a"]
b = pubkey_data["curve"]["b"]
order = pubkey_data["field"]["ec_base_order"]
h1_bases = list(map(lambda x: x+1, pubkey_data["h1_bases"]))
KCHARS = "BCDFGHJKMPQRTVWXY2346789"

def decode_pkey(k):
    k = k.replace("-", "")
    out = 0
    
    for c in k:
        out *= 24
        out += KCHARS.index(c)
    
    return out

K = GF(p)
Kx.<x> = K[]
K3.<u> = K.extension(Kx(pubkey_data["field"]["k3_minpoly"]))
K3y.<y> = K3[]
K6.<t> = K3.extension(K3y(pubkey_data["field"]["k6_minpoly"]))

E = EllipticCurve(K, [a, b])
E6 = EllipticCurve(K6, [a, b])

Qi = [E6(K3(point["x"]) * t^-2, K3(point["y"]) * t^-3) for point in pubkey_data["points"]]

# pairing_val = e_m(P, S)
pairing_val = K6([K3(pubkey_data["pairing_val"][0]), K3(pubkey_data["pairing_val"][1])])

assert is_prime(p)
assert len(h1_bases) == len(Qi)
assert h1_bases[0] == 2
assert pairing_val^order == 1
In [ ]:
pkey_chars = "33PXH-7Y6KF-2VJC9-XBBR8-HVTHH"

# pkey = HASH(M)
# HASH is a currently unknown hash function
pkey = decode_pkey(pkey_chars)

# h1_coeffs = H1(M)
# During validation, coeffs must be found by a search that i havent implemented
# h1_coeffs = [1, 0, 7, 1, 4, 15, 9, 1, 1, 0, 2, 1, 0, 19]

# 10 bits unknown, 30 bits product ID, 1 bit unknown (upgrade?)
key_data = (342 << 31 | 918500000 << 1 | 0)
h1_coeffs = [1]

for i in range(len(h1_bases) - 1):
    h1_coeffs.append(key_data % h1_bases[i + 1])
    key_data //= h1_bases[i + 1]

print(h1_coeffs)

# H2(M) = E.lift_x(HASH(M) % p)
T = E6(E.lift_x(pkey % p))
Q = sum(map(lambda x: x[0] * x[1], zip(h1_coeffs, Qi))) 

test_pairing = T.tate_pairing(Q, order, 6, q=p)

print(test_pairing == pairing_val or test_pairing == 1/pairing_val)

key_data = 0

for i in range(len(h1_bases) - 1, 0, -1):
    key_data *= h1_bases[i]
    key_data += h1_coeffs[i]
    print(h1_bases[i], h1_coeffs[i], key_data)

pid = (key_data & ((1 << 31) - 1)) >> 1