Victor Morales Dionisio - 1 year ago 249

C Question

I've been looking for an answer for this but could not find it. I'm not trying to use ^ as a power operator.

Here's my problem.

I'm trying to reproduce an interleaver from a digital TV standard (physical layer protocol). It is a project for school.

Here's the code I have so far in C:

`#include <sys/io.h>`

#include <stdio.h>

#include <stdlib.h>

#include <errno.h>

#include <sys/types.h>

#include <sys/stat.h>

#include <fcntl.h>

#include <time.h>

#include <unistd.h>

#include <stdbool.h>

#include <string.h>

#include <complex.h>

#include <math.h>

int main()

{

int Mmax = 32768;

int Nr = log10(Mmax)/log10(2);

printf("Nr = %i \n",Nr);

int Lfm = 42;

int i,j,k,l;

// Create array R'i

unsigned char Rli[Mmax][Nr];

for (i = 0; i < Mmax; i++)

memset(Rli[i], 0, sizeof(unsigned char)*(Nr));

for (i = 0; i < Mmax; i++)

{

for(j = 1; j < Nr; j++)

{

if(i == 0 || i == 1)

{

Rli[i][j] = 0;

}

else if(i == 2)

{

Rli[i][j] = 0;

if(j == Nr - 2)

Rli[i][j] = 1;

}

else

{

Rli[i][j+1] = Rli[i-1][j];

}

}

if(i > 2)

{

Rli[i][1] = (((Rli[i-1][14] ^ Rli[i-1][13] ) ^ Rli[i-1][12] ) ^ Rli[i-1][2]);

}

Rli[i][0] = 0;

}

// wire permutation for array R'i - creates array Ri

unsigned char Ri[Mmax][Nr];

for (i = 0; i < Mmax; i++)

memset(Ri[i], 0, sizeof(unsigned char)*(Nr));

for (i = 0; i < Mmax; i++)

{

Ri[i][1] = Rli[i][8]; //Rli[i][7];

Ri[i][2] = Rli[i][9]; //Rli[i][8];

Ri[i][3] = Rli[i][14]; //Rli[i][13];

Ri[i][4] = Rli[i][4]; //Rli[i][3];

Ri[i][5] = Rli[i][6]; //Rli[i][5];

Ri[i][6] = Rli[i][13]; //Rli[i][12];

Ri[i][7] = Rli[i][3]; //Rli[i][2];

Ri[i][8] = Rli[i][2]; //Rli[i][1];

Ri[i][9] = Rli[i][12]; //Rli[i][11];

Ri[i][10] = Rli[i][5]; //Rli[i][4];

Ri[i][11] = Rli[i][10]; //Rli[i][9];

Ri[i][12] = Rli[i][11]; //Rli[i][10];

Ri[i][13] = Rli[i][1]; //Rli[i][0];

Ri[i][14] = Rli[i][7]; //Rli[i][6];

}

// Offset generator Gk

int Gmax = floor(Lfm/2);

unsigned char Gk[Gmax][Nr];

for (i = 0; i < Gmax; i++)

memset(Gk[i], 0, sizeof(unsigned char)*Nr-1);

for (k = 0; k < Gmax; k++)

{

for(j = 0; j < Nr; j++)

{

if(k == 0)

{

Gk[k][j] = 1;

}

else

{

Gk[k][j+1] = Gk[k-1][j];

}

}

if(k > 0)

{

Gk[k][0] = ( Gk[k-1][14] ^ Gk[k-1][13] );

}

}

// interleaving sequence

int Ndata = 26303; // numero de data

unsigned char Hl[Ndata];

double H1[Ndata], H2[Ndata];

memset(Hl, 0, sizeof(unsigned char)*Ndata);

memset(H1, 0, sizeof(double)*Ndata);

memset(H2, 0, sizeof(double)*Ndata);

int p,indice;

// loop from page 107 of the physical layer protocol.

for (i = 0; i < Lfm; i++)

{

for (k = 0; k < Mmax; k++)

{

p = 0;

for (j = 0; j < Nr; j++) // sum

{

if(j >= 0 && j <= Nr - 2)

H1[p] += Ri[k][j]*pow(2,j);

else if(j >= 0 && j <= Nr - 1)

{

indice = floor(i/2);

H2[p] += Gk[indice][j]*pow(2,j);

}

}

/*****/ Hl[p] = ((i % 2)*pow(2,Nr-1) + H1[p] ) ^ H2[p]; /*****/

if (Hl[p] < Ndata)

p += 1;

}

}

the line between the /*****/ in the end generates an error when I try to compile.

`freqint.c:146:43: error: invalid operands to binary ^ (have ‘double’ and ‘double’)`

Hl[p] = ((i % 2)*pow(2,Nr-1) + H1[p] ) ^ H2[p];

I want to do the XOR operation there, but I can't get it right.

I'm taking this from:

http://atsc.org/wp-content/uploads/2016/10/A322-2016-Physical-Layer-Protocol.pdf

the interleaving sequence is on the bottom of page 107

How do I write my code to avoid that error message and still do an XOR?

Recommended for you: Get network issues from **WhatsUp Gold**. **Not end users.**

Answer Source

As was stated in the comments, the `^`

operator can't be used on a `double`

, however you don't need to use `double`

.

You're using two functions which return a `double`

, namely `pow`

and `floor`

.

Each time you call `pow`

, you pass `2`

for the base. Raising 2 to a power can be done much more efficiently by left shifting the value `1`

by the exponent.

Similarly, each time you call `floor`

you're dividing an integer value by `2`

. Since integer division automatically drops the remainder of division (assuming you're working only with positive values), the call to `floor`

doesn't buy you anything.

So change all instances of `pow(2,x)`

to `(1 << x)`

, and change all instances of `floor(x/2)`

to `(x/2)`

. Then you can declare `H1`

and `H2`

as arrays of `unsigned int`

and you will be able to use the XOR operator `^`

.

Recommended from our users: **Dynamic Network Monitoring from WhatsUp Gold from IPSwitch**. ** Free Download**