
#include <stdio.h>
#include <stdint.h>

// ireducib. polynom m(x) = x^8 + x^4 + x^3 + x + 1
// t.j. koef. m_8 = m_4 = m_3 = m_1 = m_0 = 1
// a koef. m_7 = m_6 = m_5 = m_2 = 0
// binarna reprezentacia je 0b100011011
// hexadecimalne 0x11b

#define POLYNOM_MX 0x11b

// scitanie polynomov v poli GF(2^8)
// je to vlastne bitovy XOR
uint8_t gf_add( uint8_t a, uint8_t b )
{
	return (a ^ b);
}

// nasobenie polynomu polynomom "x"
// modulo ireducibilny polynom m(x)
uint8_t gf_mulx( uint8_t a )
{
	// ak je stupen polynomu 6 a menej
	if ( (a & 0x80) == 0 )
		return (a << 1);
	// ak je stupen 7, musim pripocitat m(x)
	else 
		return (a << 1) ^ POLYNOM_MX;
}

// nasobenie polynomov a(x) a b(x)
uint8_t gf_mul( uint8_t a, uint8_t b )
{
	int i, result = 0;
	for ( i = 0; i < 8; i++ )
	{
		if ( (b & 0x01) != 0 ) 
			result = gf_add( result, a );
		a = gf_mulx( a );
		b = (b >> 1);
	}
	return result;
}

int main( int argc, char argv[] )
{
	uint8_t a = 0xaa;

	int i;
	uint8_t b = 0x01;
	for ( i = 0; i < 256; i++ )
	{
		if ( gf_mul(a, b) == 0x01 )
		{
			printf( "Inverzny prvok k 0x%02x je 0x%02x\n", a, b );
		}

		b++;
	}

	return 0;
}

