61 lines
2.0 KiB
Python
61 lines
2.0 KiB
Python
"""Hash verify / sidecar tests for gost_util."""
|
|
from __future__ import annotations
|
|
|
|
import hashlib
|
|
import tempfile
|
|
import unittest
|
|
from pathlib import Path
|
|
|
|
from proxy_chain_manager import gost_util
|
|
|
|
|
|
class TestVerifyZipSha256(unittest.TestCase):
|
|
def test_matching_hash_passes(self) -> None:
|
|
data = b"hello world"
|
|
digest = hashlib.sha256(data).hexdigest()
|
|
gost_util._verify_zip_sha256(data, digest) # must not raise
|
|
|
|
def test_wrong_hash_raises(self) -> None:
|
|
data = b"hello world"
|
|
with self.assertRaises(RuntimeError) as ctx:
|
|
gost_util._verify_zip_sha256(data, "0" * 64)
|
|
self.assertIn("supply-chain", str(ctx.exception).lower())
|
|
|
|
def test_case_insensitive_match(self) -> None:
|
|
data = b"PROXYGOD"
|
|
digest = hashlib.sha256(data).hexdigest().upper()
|
|
gost_util._verify_zip_sha256(data, digest)
|
|
|
|
|
|
class TestExeHashSidecar(unittest.TestCase):
|
|
def test_sidecar_round_trip(self) -> None:
|
|
with tempfile.TemporaryDirectory() as tmp:
|
|
exe = Path(tmp) / "gost.exe"
|
|
exe.write_bytes(b"\x90" * 1024)
|
|
digest = gost_util._hash_file(exe)
|
|
gost_util._write_pinned_exe_hash(exe, digest)
|
|
self.assertEqual(gost_util._read_pinned_exe_hash(exe), digest)
|
|
|
|
def test_missing_sidecar_returns_none(self) -> None:
|
|
with tempfile.TemporaryDirectory() as tmp:
|
|
exe = Path(tmp) / "gost.exe"
|
|
exe.write_bytes(b"x")
|
|
self.assertIsNone(gost_util._read_pinned_exe_hash(exe))
|
|
|
|
def test_hash_file_matches_python_hashlib(self) -> None:
|
|
with tempfile.NamedTemporaryFile(delete=False) as f:
|
|
f.write(b"some payload bytes")
|
|
f.flush()
|
|
p = Path(f.name)
|
|
try:
|
|
self.assertEqual(
|
|
gost_util._hash_file(p),
|
|
hashlib.sha256(b"some payload bytes").hexdigest(),
|
|
)
|
|
finally:
|
|
p.unlink(missing_ok=True)
|
|
|
|
|
|
if __name__ == "__main__":
|
|
unittest.main()
|