PXI

cancel
Showing results for 
Search instead for 
Did you mean: 

Problem with NI-5672 stream generation!

I have written a c++ program that generate a GPS signal in the PC ram and then transfer it to NI-5672 signal generator, but there is a confusing situation! I have written two programs to debug the problem, one of them generate signal in ram and then save it in a file in HDD on my PC, second read the file from HDD and stream it to RFSG, in this situation everything works perfectly and GPS receiver can extract data from signal! But when I try to write data from PC ram to RFSG memory without saving to HDD, it seams that signal overwriting during generation and GPS receiver can't extract data from signal!

 

The Code I used for write signal to HDD :

FILE * stream = fopen(filePath, "wb");
NIComplexI16 * data_IQ = (NIComplexI16 *) malloc(1000000*sizeof(NIComplexI16));
// bool generateSignal(NIComplexI16 * data_IQ) => generates 1000000 I/Q samples of gps signal!
while(generateSignal(data_IQ))
{
	fwrite(data_IQ , sizeof(NIComplexI16), 1000000 , stream);
}
fclose(stream);

 The Code I used for read from HDD and generating signal:

// other configs trimed !
niRFSG_AllocateArbWaveform(session, "waveformName", 4 * 1000000);

FILE * stream = fopen(filePath, "rb");
NIComplexI16 * data_IQ = (NIComplexI16 *) malloc(1000000*sizeof(NIComplexI16));

// fill RFSG memory before starting signal generation :
int size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
if(status !=0 ) exit(1);

// Start signal generation :
status = niRFSG_Initiate(session);
if(status !=0 ) exit(1);
ViBoolean ended = false;
// Read signal from file and write to RFSG memory to generate:
while(size>0)
{
    size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
    status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
    if(status !=0 ) break;
	status = niRFSG_CheckGenerationStatus(session, &ended);
	if(ended) exit(1);
}
// signal generation ended!

 Above code works perfectly! but when I try to remove saving to HDD part, results are different!

 

The Code I used for generation signal on the fly and write to RFSG:

// other configs trimed !
niRFSG_AllocateArbWaveform(session, "waveformName", 4 * 1000000);

NIComplexI16 * data_IQ = (NIComplexI16 *) malloc(1000000*sizeof(NIComplexI16));

// fill RFSG memory before starting signal generation :
if(generateSignal(data_IQ)) status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
else exit(1);
if(generateSignal(data_IQ)) status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
else exit(1);
if(generateSignal(data_IQ)) status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
else exit(1);
if(generateSignal(data_IQ)) status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
else exit(1);
if(status !=0 ) exit(1);

// Start signal generation :
status = niRFSG_Initiate(session);
if(status !=0 ) exit(1);
ViBoolean ended = false;
// Read signal from file and write to RFSG memory to generate:
while(generateSignal(data_IQ))
{
    status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
    if(status !=0 ) break;
	status = niRFSG_CheckGenerationStatus(session, &ended);
	if(ended) exit(1);
}
// signal generation ended!

 

Please help me to figure out my problem!

 

I think that last code I wrote, overwrite signal before generation by RFSG!

 

0 Kudos
Message 1 of 10
(4,848 Views)

Hello HTALA,

 

There are two other ways I would troubleshoot this (assuming that RFSG configuration steps like center frequency, output power, IQ rate, are not provided in the code you posted).

  1. If you have a vector signal analyzer, compare the spectrum output of the program that streams from disk vs the program that generates on the fly.
  2. Do a benchmark test of how long it takes to generate the signal on the fly (without the use of RFSG) compared to how fast you can read out the file from the disk.

To do the benchmark test, I would use a for loop around the functions in question to run a specified number of times, and call GetTickCount() before and after the loop to get the difference in milliseconds. I suspect that reading from the disk is a much faster operation than the signal generation function. 

 

Here is a bit of psuedo-code, you will still need to open the file and create the stream, etc. Remember to choose enough iterations such that the time it takes the loop to complete is much greater than 50 ms.

#define iterations 10
int i;
int StartTime;
int DiskReadTime;
int OnTheFlyTime;



startTime = GetTickCount();
for (i = 0; i< iterations; i++)
{
	while(size>0)
	{
		size = fread(data_IQ, sizeof(NIComplexI16), 1000000, stream);
		//status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
		//if(status !=0 ) break;
		//status = niRFSG_CheckGenerationStatus(session, &ended);
		//if(ended) exit(1);
	}
}
DiskReadTime = GetTickCount() - startTime;



startTime = GetTickCount();
for (i = 0; i< iterations; i++)
{
	while(generateSignal(data_IQ))
	{
		//status = niRFSG_WriteArbWaveformComplexI16(session, "waveformName", 1000000, data_IQ);
		//if(status !=0 ) break;
		//status = niRFSG_CheckGenerationStatus(session, &ended);
		//if(ended) exit(1);
	}
}
OnTheFlyTime = GetTickCount() - startTime;

 

I have some additional questions as well:

  1. What is the IQ rate that you are using for generating this signal?
  2. Are you using an embedded controller or a remote controller? What model and brand?
  3. Are you getting any errors or is the GPS receiver just not working?
Anthony F.
Staff Software Engineer
National Instruments
0 Kudos
Message 2 of 10
(4,835 Views)

My IQ-Rate : 2,000,000

Using NI-5672 with external controller => A PC with following spec:

 

  CPU: Intel 980X => 6 cores, 12 threads, 3.4 GHz, 12MB cache

  RAM: 12GB ram

  Motherboard: Intel DX58SO2

 

  OS: Win 7 Ultimate x64

  PCIe-PXIe link: NI PXIe-8388

 

------------------------------------------

Benchmark of signal generation on the fly is only 6 secs for 60 secs of signal, it means => 1/10 of time!

Also, if signal generation rate in PC became slower from IQ rate, RFSG returns error and stops generation, so there is no problem with signal generation speed.

For example when I increase IQ-Rate to 40,000,000 (40 MS/s), signal generation stops after few milliseconds and RFSG returns "The data being written to the streaming waveform cannot keep up with the output. Decrease the sample rate or write data to the streaming waveform more frequently.";

------------------------------------------

 

I use a Garmin Quest GPS receiver for testing of my signal, by on the fly signal generation it can't extract signal data, but can figure out which satellites are visible, in this case it shows that signal corrupted or some of it overwritten.

 

0 Kudos
Message 3 of 10
(4,831 Views)

Hello Htata,

 

You are correct. I was trying to determine if there was an underflow happening, but it appears that you have already checked for that condition. 

 

Have you been able to check the output waveform when streaming from file or generating on the fly?  If you believe that you are overwriting memory on the device you can query the property NIRFSG_ATTR_STREAMING_SPACE_AVAILABLE_IN_WAVEFORM for the number of samples that are free on the arbitrary waveform generator and wait until enough samples become available before writing more data.

Anthony F.
Staff Software Engineer
National Instruments
0 Kudos
Message 4 of 10
(4,823 Views)

I already tried, after posting the problem to this board, I added this to my code, but there is no diffrence!

 

Is there any way to dump full data transfer to the signal generator !?

0 Kudos
Message 5 of 10
(4,821 Views)

Hello HTALA,

 

I am a little confused, have you looked at the spectrum output of the RFSG or have you added the property for the get available samples in memory to the program?

 

As far as dumping the full transfer log, you can use the NI I/O Trace program to capture all of the interaction with the device and your program.  It is located in the Start menu, All Programs, National Instruments

Anthony F.
Staff Software Engineer
National Instruments
0 Kudos
Message 6 of 10
(4,808 Views)

I have no vector signal analyzer, and I used NI IO Trace before, but IO trace can't dump data transferred to rfsg, it only show api calls and values of arguments of these calls, like address of memory data stored for transferring to RFSG.

 

Thanks for your responses. But it seams that there is a logical error in my code, and I'm really confused, because I use same code for generating signal! and transferring data to RFSG, in fact I use one program with a condition in writing signal part like below:

 

 

/// signal generation procedure trimmed !
//.....
//.....
while(running){
	if(useRFSG){
		ViInt64 spaceAvailableInStreamingWfm;
		status = niRFSG_GetAttributeViInt64(session, "", NIRFSG_ATTR_STREAMING_SPACE_AVAILABLE_IN_WAVEFORM, &spaceAvailableInStreamingWfm);
		if(status<0) return false;
		while(spaceAvailableInStreamingWfm<samples_count)
		{
			status = niRFSG_GetAttributeViInt64(session, "", NIRFSG_ATTR_STREAMING_SPACE_AVAILABLE_IN_WAVEFORM, &spaceAvailableInStreamingWfm);
			if(status<0) return false;
		}
		status = niRFSG_WriteArbWaveformComplexI16(session, waveformName, samples_count, SignalBuffer);
		if(status<0) return false;
		ViBoolean ended = false;
		status = niRFSG_CheckGenerationStatus(session, &ended);
		if(ended) return true; // ended!
	}else{
		fwrite(SignalBuffer , sizeof(NIComplexI16), samples_count , Data );
	}
}

 

I created a buffer of 100 milliseconds of signal to optimize signal transfer blocks, and fill this buffer and transfer it to RFSG, or write it in a File using fwrite(...).

So why "useRFSG" is "true" and my program generate signal on the fly, there is problem, but when I save signal to HDD and read saved signal and transfer it to RFSG with a second program I wrote with completely same strategy for transferring signal to RFSG, there is no problem!?

 

0 Kudos
Message 7 of 10
(4,806 Views)

Hello HTALA,

 

It looks like you are checking for errors but can you also check for warnings to see if status > 0 at any point in code?

 

Can you also post your C files so that I can troubleshoot your code as well? It is hard to hypothesize what might be wrong without seeing the full code.

Anthony F.
Staff Software Engineer
National Instruments
0 Kudos
Message 8 of 10
(4,797 Views)

I faced a problem that may cause this situation,

 

I set my IQ Rate to a value like 1500000.0000 (15e6) by code like below:

 

status = niRFSG_SetAttributeViReal64(session, "", NIRFSG_ATTR_IQ_RATE, iq_rate);
if(status!=0) return false;

 

But when re-read IQ-Rate with following code, it returns "1500000.00000014"  ?!!!

 

status = niRFSG_GetAttributeViReal64(session, "", NIRFSG_ATTR_IQ_RATE, &iq_rate);
if(status!=0) return false;
printf("%f",iq_rate);

 

0 Kudos
Message 9 of 10
(4,791 Views)

Can you ensure that you are really setting 15e6 and not 15e5? On the return value "1500000.00000014", it is actually closer to 15e5.

 

Did you check for warning in your code? Does the function work if you start from an example that was built for CVI?

Anthony F.
Staff Software Engineer
National Instruments
0 Kudos
Message 10 of 10
(4,779 Views)