⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mex_modem.c

📁 DSP 5409 plc应用程序,调试通过,是用在电力线通讯上的演示程序.
💻 C
📖 第 1 页 / 共 2 页
字号:
			drec.r += CARRIER_LEN*2;
		}

		drec.r +=2;		// increment past uTraceAGCFound and uTraceIndex 

		/*====================================================================
		read data and do detection
		=====================================================================*/
		errCount = readDataFramesFromMatlab(rxUserDataArray, drec );
	 
		//---- return the results to Matlab---------------------------------
		*errorCountPtr = copyReadData2Matlab(dDataBuffer, rxUserDataArray, errCount );
	}
	
	/*====================================================================
	Unrecognized decode 
	=====================================================================*/
	else
	{
		strcpy( prtStr, "Unrecognized command string.  Valid syntax:\n" );
		strcat( prtStr, "		[txSignal]						   = mex_modem('xmit', userData)\n" );
		strcat( prtStr, "		[errorCount, <userData>]		   = mex_modem('rec', recSignal, PreambleStart)" ); 
		strcat( prtStr, "		[errorCount, <userData>, <freqEq>] = mex_modem('symb', symbolArray)" );
		strcat( prtStr, "		[freqEq]						   = mex_modem('align', recSignal, packetStart)" );
		mexErrMsgTxt(prtStr);
	}

}



/*====================================================================
functions
=====================================================================*/


/*====================================================================
	Allocate byte buffer and fill with float data from Matlab
=====================================================================*/
void getUserDataFromMatlab(u16 *userData, const mxArray *matInArray)
{
	char			prtStr[80];
	i16				n;					// loop counter
	i16				wordCount = 0;
	u16				hiByte = 0;
	dCplxPtr		dUserData;

	//---- Get user data as bytes ---------------------------
	dUserData.i   = NULL;
	dUserData.r   = mxGetPr(matInArray);
	dUserData.len = mxGetM(matInArray)*mxGetN(matInArray);
	if( dUserData.len > NUM_USER_BYTES )
	{
		sprintf(prtStr, "Packet set up for %d bytes max, you passed %d bytes.", 
			NUM_USER_BYTES, dUserData.len ); 
		mexErrMsgTxt(prtStr); 
	}
	
	//---- put 2 "bytes" from Matlab in each word of the userData buffer -------
	for(n = 0;  n < dUserData.len; n++ )
	{
		hiByte = (hiByte + 1) & 0x01;	
		if( hiByte == 1 )
		{
			*userData = ((u16)(*dUserData.r++)) << BYTE_LEN;
		}
		else
		{
			*userData++ += (u16)(*dUserData.r++);
			wordCount++;
		}
	}

	if( hiByte == 1 )	// finish out last data word if necessary
	{
		userData++;
		wordCount++;
	}

	for( ; wordCount < DATA_BUFFER_LEN; wordCount++ )	// make the rest of buffer zeros
		*userData++ = 0;

}

	
/*====================================================================
  Copy the integer transmit waveform into the double Matlab array.
  The Matlab array is intialized to all zeros, so to add a zero pad
  to the front of the Matlab array, add an offset to the Matlab array 
  pointer.
=====================================================================*/
void copyWaveform2Matlab( const mxArray **matOutArray, i16 *pTxSignal)
{
	int				n;
	int				txSignalLen;
	dCplxPtr		dTxSignal;		// pointer to user data in Matlab array
	
	txSignalLen = NUM_PRE_FRAMES * FFT_LEN
				+ (int)SYNC_FIELD_LEN
				+ NUM_DATA_BLOCKS * DATA_FRAMES_PER_BLOCK * (CYCLIC_PREFIX_LEN + FFT_LEN);
	dTxSignal.len = WAVE_ZERO_PAD_FRONT + txSignalLen + WAVE_ZERO_PAD_BACK;

	*matOutArray = mxCreateDoubleMatrix(dTxSignal.len, 1, mxREAL);

	dTxSignal.r = mxGetPr(*matOutArray) + WAVE_ZERO_PAD_FRONT;	// offset pointer to make zero pad

	for( n = 0; n < txSignalLen;  n++ )		// do the copy
		*dTxSignal.r++ = (double)(*pTxSignal++);

	#if DEBUGIT == DEBUG_PUT_MAT
	{	i16		*ptr = pTxSignal;
		diagArray = mxCreateDoubleMatrix(dTxSignal.len, 1, mxREAL);
		mxSetName(diagArray, "ofdm_diag");
		diag.r = mxGetPr(diagArray);
		for( n = 0 ; n < TX_BUFFER_LEN ; n++ )
			*diag.r++ = (double)(*ptr++);
		mexPutArray(diagArray, "caller");
	}
	#endif

}


/*====================================================================
	Get and integer copy of the received signal from Matlab
	
=====================================================================*/
i16 *getSignalFromMatlab(dCplxPtr dRecSignal, int startingSample)
{
	i16				n;
	i16				*recSignal;
	
	//---- copy it -----------------------------------------
	recSignal = recSignalArray;
	for( n = 0;  n < dRecSignal.len;  n++ )
	{
		*recSignal++ = (i16)(*dRecSignal.r++);
		if( n >= RX_CIRC_BUFFER_LEN )
			mexErrMsgTxt("Overran circular buffer.");
	}
	return recSignalArray + startingSample -1;	// the -1 is a Matlab thing!
}


/*====================================================================
	if asked for, copy the received data into a double Matlab array 
	and return parityGood, else assume that the data was all zeros,
	count the non-zero bits and return the number of non-zero bits as
	the error count.
=====================================================================*/
double copyReadData2Matlab(dCplxPtr dDataBuffer, u16 *userData, i16 parityGood )
{
	i16				n;

	if( dDataBuffer.r != NULL )
	{
		for( n = 0; n < DATA_BUFFER_LEN;  n++ )
		{	
			//*dDataBuffer.r++ = (double)(*userData++);
			*dDataBuffer.r++ = (double)(*userData >> BYTE_LEN);
			*dDataBuffer.r++ = (double)(0x00FF & *userData++);
		}
		return parityGood;			
	}
	else
	{
		return countErrors(userData);
	}
}


/*====================================================================
	Send data to the matlab workspace

=====================================================================*/
void	diagData( void *array, u16 len, char *matName, diagType flag)
{
	mxArray		*diagArray;
	dCplxPtr	diag;

	u16			n;
	u16			*unum;
	i16			*inum;
	iCplx		*jnum;

	switch( flag )
	{
	case diagU16:
		diagArray = mxCreateDoubleMatrix(len, 1, mxREAL);
		diag.r = mxGetPr(diagArray);
		unum = (u16 *)array;
		for( n = 0 ; n < len; n++ )
		{
			*diag.r++ = (double)(*unum++);
		}
		break;
	case diagI16:
		diagArray = mxCreateDoubleMatrix(len, 1, mxREAL);
		diag.r = mxGetPr(diagArray);
		inum = (i16 *)array;
		for( n = 0 ; n < len; n++ )
		{
			*diag.r++ = (double)(*inum++);
		}
		break;
	case diagICPLX:
		diagArray = mxCreateDoubleMatrix(len, 1, mxCOMPLEX);
		diag.r = mxGetPr(diagArray);
		diag.i = mxGetPi(diagArray);
		jnum = (iCplx *)array;
		for( n = 0 ; n < len; n++ )
		{
			*diag.r++ = (double)(jnum->re);
			*diag.i++ = (double)(jnum->im);
			jnum++;
		}
		break;
	default:
		postError("Unrecognized diag type.");
	}

	mxSetName(diagArray, matName);
	mexPutArray(diagArray, "caller");

}


//====================================================================
//	return to Matlab some important constant parameters
//  11/17/03  Hagen		added more constants to returned parms
//=====================================================================
//void parms2Matlab( const mxArray **matOutArray )
void parms2Matlab( mxArray **matOutArray )
{
	i16			n;
	mxArray 	*fieldValue;
	//i16			fieldNamesLen;
	i16			numFields = 0;

	char		**fieldNames;

	struct		parmDataSt
	{
		char		*name;
		double		value;
	};
	struct parmDataSt	parmData[]  =  
		{	MAKE_FIELD( FFT_LEN               ),
  			MAKE_FIELD( CYCLIC_PREFIX_LEN     ),
  			MAKE_FIELD( WINDOW_LEN            ),
  			MAKE_FIELD( SYNC_FIELD_LEN        ),
  			MAKE_FIELD( NUM_PRE_FRAMES        ),
  			MAKE_FIELD( NUM_USER_BYTES        ),
  			MAKE_FIELD( CARRIER_LOW           ),
  			MAKE_FIELD( CARRIER_HIGH          ),
  			MAKE_FIELD( CARRIER_LEN           ),
  			MAKE_FIELD( NUM_DATA_BLOCKS       ),
  			MAKE_FIELD( NUM_SYMBOLS           ),
  			MAKE_FIELD( DATA_FRAMES_PER_BLOCK ),
  			MAKE_FIELD( SYMBOL_OFFSET         ),
  			MAKE_FIELD( DATA_BUFFER_LEN       ),
  			MAKE_FIELD( TX_BUFFER_LEN         ),
  			MAKE_FIELD( RX_CIRC_BUFFER_LEN    ),
  			MAKE_FIELD( VITERBI_ENCODE_SHIFT  ),			 
  			MAKE_FIELD( VITERBI_DISTANCE_SHIFT),			 
  			MAKE_FIELD( PRE_IFFT_SCALE        ),			 
  			MAKE_FIELD( DATA_IFFT_SCALE       ),			 
  			MAKE_FIELD( IMP_IFFT_SCALE        ),			 
  			MAKE_FIELD( DDPHASE_MSHIFT        ),			 
  			MAKE_FIELD( DDPHASE_HI_LIM        ),			 
  			MAKE_FIELD( DDPHASE_LO_LIM        ),			 
  			MAKE_FIELD( PWR_SCALE_SHIFT       ),			 
  			MAKE_FIELD( CARRIER_SCALE         ),			 
  			MAKE_FIELD( PWR_SHIFT             ),			 
  			MAKE_FIELD( FEQ_SHIFT             ),
  			MAKE_FIELD( DEBUGIT               ),			 
			"parmEnd",			0
		};
  			
	while( strcmp( parmData[numFields].name, "parmEnd" ) != 0 )
		numFields++;

	fieldNames	   = malloc( numFields*sizeof(char*) );
	for( n = 0; n < numFields; n++ )
		fieldNames[n] = parmData[n].name;

	*matOutArray = mxCreateStructMatrix(1, 1, numFields, fieldNames);

	for( n = 0; n < numFields; n++ )
	{
		fieldValue = mxCreateDoubleMatrix(1,1,mxREAL);
		*mxGetPr(fieldValue) = parmData[n].value;
		mxSetFieldByNumber( *matOutArray, 0, n, fieldValue );
	}
	return;
}

/*
#if 0	
//====================================================================
//	function pointer dereference
//
//=====================================================================
void displayFunctionAddr( void )
{
	static int CallCount = 0;
	struct 
	{
		char *name;
		void *func;
	}  funcs[] =	
		{		
		    MAKE_FUNC_PTR(mexFunction),
		    MAKE_FUNC_PTR(lookForPacket),
//SNR_CALC  MAKE_FUNC_PTR(getPowerFromFFT),
		    MAKE_FUNC_PTR(frameAlign),
		    MAKE_FUNC_PTR(readDataFrames),
		    MAKE_FUNC_PTR(decodeData),
		    MAKE_FUNC_PTR(aveFFT),
		    MAKE_FUNC_PTR(AlignPhaseCompare),
		    MAKE_FUNC_PTR(getFrameStartFromImpulse),
		    MAKE_FUNC_PTR(getFreqEq),
		    MAKE_FUNC_PTR(dataFFT),
		    MAKE_FUNC_PTR(dataPhaseCompare),
		    MAKE_FUNC_PTR(deinterleaveSymbols),
		  //MAKE_FUNC_PTR(deinterleave),
		    MAKE_FUNC_PTR(viterbiDecodeSoft),
		    MAKE_FUNC_PTR(viterbiDecodeHard),
		    MAKE_FUNC_PTR(compareParityCheckBytes),
		    MAKE_FUNC_PTR(countErrors),
		    MAKE_FUNC_PTR(fillCarriers),
		    MAKE_FUNC_PTR(mexfft),
		    MAKE_FUNC_PTR(mexrfft),
		    MAKE_FUNC_PTR(circFFT),
		    MAKE_FUNC_PTR(circFFTshort),
		    MAKE_FUNC_PTR(backFFT),
		    MAKE_FUNC_PTR(diagData),
		    MAKE_FUNC_PTR(getUserDataFromMatlab),
		    MAKE_FUNC_PTR(copyWaveform2Matlab),
		    MAKE_FUNC_PTR(getSignalFromMatlab),
		    MAKE_FUNC_PTR(copyReadData2Matlab),
		    MAKE_FUNC_PTR(parms2Matlab),
		    "End of funcs", 0
		};

	for(n = 0; strcmp((funcs + n)->name,"End of funcs") != 0; n++)
		mexPrintf("%-30s = %p\n", (funcs + n)->name, (funcs + n)->func);

	mexPrintf("Call Count = %10d\n", ++CallCount);
	//if(CallCount >= 33)
	//	CallCount += 7;

	mexPrintf("rx buffer   %p\n", recSignalArray );
	//mexPrintf("dma offset  %p =  %d\n", &rxDMAoffset, rxDMAoffset );
	mexPrintf("rx pointer  %p =  %d\n", recSignal, (i16)(recSignal-recSignalArray) );

	return;
}
#endif
*/

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -