/* Layland-Lushbaugh code
 * Nonsystematic, non-quick look-in, dmin=?, dfree=?
 */
#define	POLY1	0xf2d05351
#define	POLY2	0xe4613c47


/* Convolutional encoder macro. Takes the encoder state, generates
 * a rate 1/2 symbol pair and stores it in 'sym'. The symbol generated from
 * POLY1 goes into the 2-bit of sym, and the symbol generated from POLY2
 * goes into the 1-bit.
 */
/*
#define	ENCODE(sym,encstate){\
	unsigned long _tmp;\
\
	_tmp = (encstate) & POLY1;\
	_tmp ^= _tmp >> 16;\
	(sym) = Partab[(_tmp ^ (_tmp >> 8)) & 0xff] << 1;\
	_tmp = (encstate) & POLY2;\
	_tmp ^= _tmp >> 16;\
	(sym) |= Partab[(_tmp ^ (_tmp >> 8)) & 0xff];\
}
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include "fano.h"
#include "tab.c"


int main(){
  unsigned long encstate, tmp, dectmpall;
  int sym;
  char bit[2];
  char hexdec[100];
  char poly1[100];
  char poly2[100];
  char binpoly1[100];
  binpoly1[0]='\0';
  char binpoly2[100];
  binpoly2[0]='\0';;
  char bininput[100];
  bininput[0]='\0';
  char hextmp1[100];
  char bintmp1[100];
  bintmp1[0]='\0';
  char hextmp2[100];
  char bintmp2[100];
  bintmp2[0]='\0';
  char hextmpg8[100];
  char bintmpg8[100];
  bintmpg8[0]='\0';
  char hextmpexor[100];
  char bintmpexor[100];
  bintmpexor[0]='\0';
  char hextmpall[100];
  char bintmpall[100];
  bintmpall[0]='\0';
  char hextmpg16[100];
  char bintmpg16[100];
  bintmpg16[0]='\0';
  char hextmpff[100];
  char bintmpff[100];
  bintmpff[0]='\0';
  char hexsym1[100];
  char binsym1[100];
  binsym1[0]='\0';
  char symdec[10];
  char symbin[10];
  symbin[0]='\0';
  char satu[2]="1";

	//	bininput[0]='\0';
	//	symdec[0]='\0';
	//	symbin[0]='\0';
	void HexToBin();
	void DecToBin();

	encstate=0xf2d05351;
	//	encstate=0x00000000;
	sprintf(poly1,"%0x",POLY1);
	sprintf(poly2,"%0x",POLY2);
	HexToBin(poly1,binpoly1);
	HexToBin(poly2,binpoly2);

	printf("\n\n");
	//	printf("encstate hexadesimal = %0lx\n",encstate);
	//	printf("encstate desimal = %lu\n",encstate);
	//	printf("encstate binary = %s\n",bin);
	//	printf("\n\n");


	unsigned long isim;
	//	for(isim=0;isim<1000;isim+=4){
	for(isim=0;isim<1000;isim++){

	  /*------ atas  ---*/
	  printf("POLY1=                      %s\n",binpoly1);
	  sprintf(hexdec,"%0lx",encstate);
	  bininput[0]='\0';
	  HexToBin(hexdec,bininput);
	  printf("encstate=                   %s\n",bininput);
	  tmp = (encstate) & POLY1;
	  sprintf(hextmp1,"%0lx",tmp);
	  bintmp1[0]='\0';
	  HexToBin(hextmp1,bintmp1);
	  printf("tmp = ((encstate) & POLY1)= %s\n",bintmp1);
	  /*--------------------*/
	  int panjang,ii,numof1=0,kode;
	  panjang=strlen(bintmp1);
	  printf("panjang bit= %d\n",panjang);
	  for(ii=0;ii<panjang;ii++){
	    bit[0]=bintmp1[ii];
	    bit[1]='\0';
	    if(strcmp(bit,satu)==0)numof1++;
	  }
	  if(numof1 % 2 == 0)kode=0;
	  else kode=1;
	  printf("Jumlah digit \"1\"= %d; Kode= %d\n",numof1,kode);
	  /*--------------------*/
	  sprintf(hextmpg16,"%0lx",tmp >> 16);
	  bintmpg16[0]='\0';
	  HexToBin(hextmpg16,bintmpg16);
	  printf("(tmp >> 16)=                                %s\n",bintmpg16);
	  tmp ^= (tmp >> 16);   /*C ^= 2 is same as C = C ^ 2 */
	  sprintf(hextmp2,"%0lx",tmp);
	  bintmp2[0]='\0';
	  HexToBin(hextmp2,bintmp2);
	  printf("(tmp ^= (tmp >> 16))=       %s\n",bintmp2);
	  (sym) = Partab[(tmp ^ (tmp >> 8)) & 0xff] << 1;
	  sprintf(hextmpg8,"%0lx",tmp>>8);
	  bintmpg8[0]='\0';
	  HexToBin(hextmpg8,bintmpg8);
	  printf("(tmp >> 8)=                         %s\n",bintmpg8);
	  sprintf(hextmpexor,"%0lx",tmp ^ tmp>>8);
	  bintmpexor[0]='\0';
	  HexToBin(hextmpexor,bintmpexor);
	  printf("(tmp ^ (tmp >> 8))=         %s\n",bintmpexor);
	  sprintf(hextmpff,"ff");
	  bintmpff[0]='\0';
	  HexToBin(hextmpff,bintmpff);
	  printf("(0xff)=                                             %s\n",bintmpff);
	  sprintf(hextmpall,"%0lx",(tmp ^ tmp>>8) & 0xff);
	  bintmpall[0]='\0';
	  HexToBin(hextmpall,bintmpall);
	  printf("((tmp ^ tmp>>8) & 0xff)=                            %s = ",bintmpall);
	  dectmpall= (tmp ^ tmp>>8) & 0xff;
	  printf("%lu\n", dectmpall);
	  printf("(Partab[%lu])= %d\n",dectmpall, Partab[dectmpall]);
          printf("(Partab[%lu]) << 1 = %d\n",dectmpall,Partab[dectmpall] << 1);
	  
	  sprintf(hexsym1,"%0x",sym);
	  binsym1[0]='\0';
	  HexToBin(hexsym1,binsym1);
	  printf("sym= %s (dalam bilangan biner)\n",binsym1);
	  printf("\n\n");

	  /*------ bawah  ---*/
	  printf("POLY2=                      %s\n",binpoly2);
	  sprintf(hexdec,"%0lx",encstate);
	  bininput[0]='\0';
	  HexToBin(hexdec,bininput);
	  printf("encstate=                   %s\n",bininput);
	  tmp = (encstate) & POLY2;
	  sprintf(hextmp1,"%0lx",tmp);
	  bintmp1[0]='\0';
	  HexToBin(hextmp1,bintmp1);
	  printf("tmp = ((encstate) & POLY2)= %s\n",bintmp1);

	  /*--------------------*/
	  numof1=0;
	  panjang=strlen(bintmp1);
	  printf("panjang bit= %d\n",panjang);
	  for(ii=0;ii<panjang;ii++){
	    bit[0]=bintmp1[ii];
	    bit[1]='\0';
	    if(strcmp(bit,satu)==0)numof1++;
	  }
	  if(numof1 % 2 == 0)kode=0;
	  else kode=1;
	  printf("Jumlah digit \"1\"= %d; Kode= %d\n",numof1,kode);
	  /*--------------------*/

	  sprintf(hextmpg16,"%0lx",tmp >> 16);
	  bintmpg16[0]='\0';
	  HexToBin(hextmpg16,bintmpg16);
	  printf("(tmp >> 16)=                                %s\n",bintmpg16);
	  tmp ^= (tmp >> 16);   /*C ^= 2 is same as C = C ^ 2 */
	  sprintf(hextmp2,"%0lx",tmp);
	  bintmp2[0]='\0';
	  HexToBin(hextmp2,bintmp2);
	  printf("(tmp ^= (tmp >> 16))=       %s\n",bintmp2);
	  (sym) |= Partab[(tmp ^ (tmp >> 8)) & 0xff] ;
	  sprintf(hextmpg8,"%0lx",tmp>>8);
	  bintmpg8[0]='\0';
	  HexToBin(hextmpg8,bintmpg8);
	  printf("(tmp >> 8)=                         %s\n",bintmpg8);
	  sprintf(hextmpexor,"%0lx",tmp ^ tmp>>8);
	  bintmpexor[0]='\0';
	  HexToBin(hextmpexor,bintmpexor);
	  printf("(tmp ^ (tmp >> 8))=         %s\n",bintmpexor);
	  sprintf(hextmpff,"ff");
	  bintmpff[0]='\0';
	  HexToBin(hextmpff,bintmpff);
	  printf("(0xff)=                                             %s\n",bintmpff);
	  sprintf(hextmpall,"%0lx",(tmp ^ tmp>>8) & 0xff);
	  bintmpall[0]='\0';
	  HexToBin(hextmpall,bintmpall);
	  printf("((tmp ^ tmp>>8) & 0xff)=                            %s = ",bintmpall);
	  dectmpall= (tmp ^ tmp>>8) & 0xff;
	  printf("%lu\n", dectmpall);
	  printf("(Partab[%lu])= %d\n",dectmpall, Partab[dectmpall]);
          printf("(Partab[%lu])  = %d\n",dectmpall,Partab[dectmpall] );
	  
	  sprintf(hexsym1,"%0x",sym);
	  binsym1[0]='\0';
	  HexToBin(hexsym1,binsym1);
	  printf("sym= %s (dalam bilangan biner)\n",binsym1);
	  printf("\n");

	  printf("channel code= %d --> ",sym);
	  sprintf(symdec,"%d",sym);
	  DecToBin(symdec,symbin);
	  printf("%s\n",symbin);
	  //	  encstate +=isim;
	  encstate ++;

	  getchar();
	}
}
// function to convert Hexadecimal to Binary Number
void HexToBin(char* hexdec, char* bin)
{

  long int i = 0;

  while (hexdec[i]) {

    switch (hexdec[i]) {
    case '0':
      strcat(bin,"0000");
      break;
    case '1':
      strcat(bin,"0001");
      break;
    case '2':
      strcat(bin,"0010");
      break;
    case '3':
      strcat(bin,"0011");
      break;
    case '4':
      strcat(bin,"0100");
      break;
    case '5':
      strcat(bin,"0101");
      break;
    case '6':
      strcat(bin,"0110");
      break;
    case '7':
      strcat(bin,"0111");
      break;
    case '8':
      strcat(bin,"1000");
      break;
    case '9':
      strcat(bin,"1001");
      break;
    case 'A':
    case 'a':
      strcat(bin,"1010");
      break;
    case 'B':
    case 'b':
      strcat(bin,"1011");
      break;
    case 'C':
    case 'c':
      strcat(bin,"1100");
      break;
    case 'D':
    case 'd':
      strcat(bin,"1101");
      break;
    case 'E':
    case 'e':
      strcat(bin,"1110");
      break;
    case 'F':
    case 'f':
      strcat(bin,"1111");
      break;
    default:
      printf("\nInvalid hexadecimal digit %c",
	     hexdec[i]);
    }
    i++;
  }
}
void DecToBin(char* symdec, char* symbin)
{

  long int i = 0;

  while (symdec[i]) {

    switch (symdec[i]) {
    case '0':
      strcpy(symbin,"00");
      break;
    case '1':
      strcpy(symbin,"01");
      break;
    case '2':
      strcpy(symbin,"10");
      break;
    case '3':
      strcpy(symbin,"11");
      break;
    }
    i++;
  }
}

/*
void HexToBin(char* hexdec, char* bin)
{

  long int i = 0;

  while (hexdec[i]) {

    switch (hexdec[i]) {
    case '0':
      printf("0000");
      break;
    case '1':
      printf("0001");
      break;
    case '2':
      printf("0010");
      break;
    case '3':
      printf("0011");
      break;
    case '4':
      printf("0100");
      break;
    case '5':
      printf("0101");
      break;
    case '6':
      printf("0110");
      break;
    case '7':
      printf("0111");
      break;
    case '8':
      printf("1000");
      break;
    case '9':
      printf("1001");
      break;
    case 'A':
    case 'a':
      printf("1010");
      break;
    case 'B':
    case 'b':
      printf("1011");
      break;
    case 'C':
    case 'c':
      printf("1100");
      break;
    case 'D':
    case 'd':
      printf("1101");
      break;
    case 'E':
    case 'e':
      printf("1110");
      break;
    case 'F':
    case 'f':
      printf("1111");
      break;
    default:
      printf("\nInvalid hexadecimal digit %c",
	     hexdec[i]);
    }
    i++;
  }
}
*/
