
from __future__ import print_function

"""
RCSid:
	$Id: FakeHash.py,v 1.10 2023/04/25 16:54:17 sjg Exp $

	@(#) Copyright (c) 2012-2020 Simon J. Gerraty

	This file is provided in the hope that it will
	be of use.  There is absolutely NO WARRANTY.
	Permission to copy, redistribute or otherwise
	use this file is hereby granted provided that 
	the above copyright notice and this notice are
	left intact. 
      
	Please send copies of changes and bug-fixes to:
	sjg@crufty.net

"""

import struct

class FakeHash(object):
    """mimic a hash object, but simply use the hexdigest we are given"""

    # in case we are subsituting for a Crypto.Hash...
    #: This value uniquely identifies the SHA-1 algorithm.
    oid = '\x06\x05\x2b\x0e\x03\x02\x1a'

    block_size = 64

    def __init__(self, data=None, digest_size=0):
        self.digest_size = digest_size
        self.data = None
        self.hexdata = None
        if data:
            self.set_state(data)

    def set_state(self, hexdata):
        """[re]set the internal state"""
        self.hexdata = hexdata.strip()
        n = len(self.hexdata)
        if self.digest_size > 0:
            if n != 2 * self.digest_size:
                raise ValueError('expect {0} bytes hexdigest as input'.format(2*self.digest_size))
        elif n % 2 or n < 32 or n > 128:
            raise ValueError('{0} bytes input, is invalid'.format(n))
        else:
            self.digest_size = n >> 1
        d = []
        i = 0
        while i < n:
            d.append(int(self.hexdata[i:i+2], base=16))
            i += 2
        self.data = struct.pack(self.digest_size*'B', *d)

    def digest(self):
        return self.data

    def hexdigest(self):
        return self.hexdata


def new(data=None):
    return FakeHash(data)


if __name__ == '__main__':
    import sys
    import struct
    
    h = FakeHash(sys.argv[1])

    d = struct.unpack(h.digest_size*'B', h.digest())
    for x in d:
        print('{0:#x} '.format(x), end=' ')
    print()
    print(h.hexdigest())
    
