/* Bit reverse yang diadopsi oleh fungsi interleave/deinterleave program WSPRD */
/* http://graphics.stanford.edu/~seander/bithacks.html#ReverseByteWith32Bits */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main()
{
  
  unsigned char tmp[162],sym[162],tsym[162];
  unsigned char p, i, j;
  
  /****************** Interleave **************************************/

  printf("\n\nData dummy:\n");
  for(i=0;i<162;i++){
    sym[i]=i;
    printf("[%d--> %d] ",i,sym[i]);
    if((i+1)%5==0)printf("\n");
  }
  
  p=0;
  i=0;
  while (p<162) {

    /*http://graphics.stanford.edu/~seander/bithacks.html#ReverseByteWith32Bits */
    j=((i * 0x80200802ULL) & 0x0884422110ULL) * 0x0101010101ULL >> 32;  /* bit reverse */
    //    	printf("%d %d %d", p,i,j);
    //    	getchar();
    if (j < 162 ) {
      tmp[j]=sym[p];    /* j dan p dibalik untuk interleave dan deinterleave */
      p=p+1;
    }
    i=i+1;
  }

  printf("\n\n");
  
  getchar();
  printf("Interleave:\n");
  for (i=0; i<162; i++) {
    sym[i]=tmp[i];
    tsym[i]=sym[i];
  }

  for (i=0; i<162; i++) {
    printf("[%d--> %d] ",i,sym[i]);
    if((i+1)%5==0)printf("\n");
  }

  /****************** Deinterleave **************************************/
  p=0;
  i=0;

  while (p<162) {
    /*http://graphics.stanford.edu/~seander/bithacks.html#ReverseByteWith32Bits */
    j=((i * 0x80200802ULL) & 0x0884422110ULL) * 0x0101010101ULL >> 32; /* bit reverse */
    if (j < 162 ) {
      tmp[p]=sym[j]; /* j dan p dibalik untuk interleave dan deinterleave */
      p=p+1;
    }
    i=i+1;
  }

  for (i=0; i<162; i++) {
    sym[i]=tmp[i];
  }
  printf("\n\n");

  getchar();
  printf("Deinterleave:\n");
  for (i=0; i<162; i++) {
    printf("[%d--> %d] ",tsym[i],sym[i]);
    if((i+1)%5==0)printf("\n");
  }

  printf("\n\n");
  
  return 0;
}
