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

📄 mex_modem.c

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

 Description:		Mex function call for OFDM powerline modem 

 Copyright (C) 2000 - 2003 Texas Instruments Incorporated
 Texas Instruments Proprietary Information
 Use subject to terms and conditions of TI Software License Agreement

 Revision History:
========================================================================*/
#include "ofdm_modem.h"


//---- Input Arguments ---------
#define	CMD_STR			prhs[0]
#define	PARM1			prhs[1]
#define	PARM2			prhs[2]

//---- Output Arguments --------
#define	OUT1			plhs[0]
#define	OUT2			plhs[1]
#define	OUT3			plhs[2]


#define MAKE_FIELD(a) #a, a
#define MAKE_FUNC_PTR(a) #a, ((void *)a)

/*===============================================================
   local function prototypes
===============================================================*/
void		getUserDataFromMatlab(u16 *userData, const mxArray *matInArray);
void		copyWaveform2Matlab( const mxArray **matOutArray, i16 *pTxSignal);
i16			*getSignalFromMatlab(dCplxPtr dRecSignal, int startingSample);
double		copyReadData2Matlab(dCplxPtr dDataBuffer, u16 *userData, i16 parityGood );
//void 		parms2Matlab( const mxArray **matOutArray );
void 		parms2Matlab( mxArray **matOutArray );
u16 		readDataFramesFromMatlab( u16 *pUserData, dCplxPtr drec );

static void cleanup(void);


/*==============================================================
I/O function
	calling syntax:  
	[errorCount, userData] = ofdm_dataDet(recSignal, dataStart)
===============================================================*/
void mexFunction( int nlhs, mxArray *plhs[],
                  int nrhs, const mxArray *prhs[] )
{ 
	char		   	*CmdStr;
	char			prtStr[80];
	int			   	n;

	//---- transmit vars -----------------------
	i16			   	*pTxSignal;
	i16				winSignal[WINDOW_LEN];

	//---- agc vars -----------------------
	dCplxPtr		drec;
	dCplxPtr		drecAgc;
	double			*dBufferPos;
	i16				*recPtr;

	//---- receive vars -----------------------
	i16				errCount = 0;

	double			*errorCountPtr = NULL;
	dCplxPtr		dDataBuffer;
	
	//i16			*recSignal;			// use global version instead

	#if DEBUGIT > DEBUG_NONE
		diag.r = NULL;
		diag.i = NULL;
	#endif

	//---- get command string ----------------------------
	if( mxIsChar(CMD_STR) != 1 )
		mexErrMsgTxt("First argument must be a command string");

	n = 1 + ( mxGetM(CMD_STR)*mxGetN(CMD_STR) );		// Get input command string
	CmdStr = mxCalloc(n, sizeof(char));
	n = mxGetString(CMD_STR, CmdStr, n);
	if( n != 0 )
		mexErrMsgTxt("Error allocating command string."); 

	/*====================================================================
	Decode command and call associated functions
	Decode "XMIT"
	=====================================================================*/
 	if( strcmp(CmdStr, "xmit")==0 ) 
	{
	    //---- Check for proper number of arguments ---------------
		if( nlhs != 1 )
			mexErrMsgTxt("Unexpected number of output arguments."); 

		if( nrhs != 2 )
			mexErrMsgTxt("Syntax:  [pTxSignal] = mex_modem('xmit', userData)");

		getUserDataFromMatlab(txUserDataArray, PARM1);

		/*======================================================================
		generate transmit signal
		======================================================================*/
		pTxSignal = makePreamble(txSignalArray, winSignal);			// start at current ptr and build preamble
		pTxSignal = makeDataFrames( pTxSignal, winSignal, txUserDataArray);	// start a current ptr and build data frames

		/*======================================================================
		copy the waveform back to Matlab
		======================================================================*/
		copyWaveform2Matlab(&OUT1, txSignalArray);
	}
	
	/*====================================================================
	Decode "REC"
	=====================================================================*/
	else if( strcmp(CmdStr, "rec")==0 ) 
	{
	    //---- Check for proper number of arguments ---------------
		if( nrhs != 2 )
			mexErrMsgTxt("Wrong number of input arguments.\nSyntax:  [errorCount, userData, rxAgc] = mex_modem('rec', recSignal)");

	   	//---- input vars ---------------------------
		drec.i   = NULL;
		drec.r   = mxGetPr(PARM1);
		drec.len = mxGetM(PARM1)*mxGetN(PARM1);
		
	   	//---- Allocate output vars ---------------------------
		dDataBuffer.len = DATA_BUFFER_LEN*2;
		dDataBuffer.r = NULL;
		dDataBuffer.i = NULL;
		drecAgc.r = NULL;

		switch( nlhs )
		{
		case 3:
			OUT3 = mxCreateDoubleMatrix(mxGetM(PARM1), mxGetN(PARM1), mxREAL);
			drecAgc.r = mxGetPr(OUT3);
			drecAgc.i = NULL;
			drecAgc.len = drec.len;
		case 2:
			OUT2 = mxCreateDoubleMatrix(dDataBuffer.len, 1, mxREAL);
			dDataBuffer.r = mxGetPr(OUT2);
		case 1:
			OUT1 = mxCreateDoubleMatrix(1, 1, mxREAL);
			errorCountPtr = mxGetPr(OUT1);
			break;
		default:
			mexErrMsgTxt("Unexpected number of output arguments."); 
		}

		/*====================================================================
		do agc : get signal from Matlab, AGC, return AGC-ed signal if requested
				 detect packet and return pointer to signal
		=====================================================================*/
		recSignal = lookForPacket( drecAgc, drec );

		/*====================================================================
		do frame align & equalization
		=====================================================================*/
		recSignal = frameAlign(phaseEqArray, recSignal );

		if (frameAligned == 0 )
			postError("stopped");

		/*====================================================================
		read data and do detection
		=====================================================================*/
		errCount = readDataFrames(rxUserDataArray, recSignal, phaseEqArray );
	 
		//---- return the results to Matlab---------------------------------
		*errorCountPtr = copyReadData2Matlab(dDataBuffer, rxUserDataArray, errCount );
	}
	
	/*====================================================================
	Report modem parameters back to Matlab
	=====================================================================*/
	else if( strcmp(CmdStr, "parm")==0 ) 
	{
	    //---- Check for proper number of arguments ---------------
		if( nlhs != 1 )
			mexErrMsgTxt("Need variable assignment to accept structure of parameters.\nSyntax:  parmStruct = mex_modem('parm')");

		parms2Matlab(&OUT1);
	}

	/*====================================================================
	Decode "Align"
	=====================================================================*/
	else if( strcmp(CmdStr, "align")==0 )
	{
	    int			n;
		iCplx		*feqPtr;

		//---- Check for proper number of arguments ---------------
		if( nrhs != 3 )
			mexErrMsgTxt("Wrong number of input arguments.\nSyntax:  [freqEq] = mex_modem('align', recSignal, packetStart)");

	   	//---- input vars ---------------------------
		drec.i   = NULL;
		drec.r   = mxGetPr(PARM1);
		drec.len = mxGetM(PARM1)*mxGetN(PARM1);
		if( drec.len > RX_CIRC_BUFFER_LEN )
			mexErrMsgTxt("recSignal data passed is too big.");
		
		n = (int)(*mxGetPr(PARM2));				// recSignal starts at this offset
		recSignal = recSignalArray + n;	
		

	   	//---- Allocate output vars ---------------------------
		if( nlhs != 1)
			mexErrMsgTxt("Wrong number of output arguments");
		
		OUT1 = mxCreateDoubleMatrix(CARRIER_LEN, 1, mxCOMPLEX);
		drecAgc.r = mxGetPr(OUT1);
		drecAgc.i = mxGetPi(OUT1);
		drecAgc.len = CARRIER_LEN;

		//---- get receive data -------------------------
		recPtr = recSignalArray;
		for( n = 0; n < drec.len; n++ )
		{
			*recPtr = (i16)(*drec.r++);
			recPtr++;
		}

		// ---- do frame align & equalization ----------------------
		recSignal = frameAlign(phaseEqArray, recSignal );

		feqPtr = phaseEqArray;
		for( n = 0; n < CARRIER_LEN; n++ )
		{
			*drecAgc.r++ = feqPtr->re;
			*drecAgc.i++ = feqPtr->im;
			feqPtr++;
		}
	}	
	
	/*====================================================================
	Decode "SYMB"
	=====================================================================*/
	else if( strcmp(CmdStr, "symb")==0 )
	{
		u16			n;

	    //---- Check for proper number of arguments ---------------
		if( nrhs != 2 )
			mexErrMsgTxt("Wrong number of input arguments.\nSyntax:  [errorCount, <userData>, <freqEq>] = mex_modem('symb', symbolArray)");

	   	//---- Allocate output vars ---------------------------
		dDataBuffer.len = DATA_BUFFER_LEN*2;
		dDataBuffer.r = NULL;
		dDataBuffer.i = NULL;
		drecAgc.r = NULL;
		drecAgc.i = NULL;
		
		switch( nlhs )
		{
		case 3:
			OUT3 = mxCreateDoubleMatrix(CARRIER_LEN, 1, mxCOMPLEX);
			drecAgc.r = mxGetPr(OUT3);
			drecAgc.i = mxGetPi(OUT3);
			drecAgc.len = CARRIER_LEN;
		case 2:
			OUT2 = mxCreateDoubleMatrix(dDataBuffer.len, 1, mxREAL);
			dDataBuffer.r = mxGetPr(OUT2);
		case 1:
			OUT1 = mxCreateDoubleMatrix(1, 1, mxREAL);
			errorCountPtr = mxGetPr(OUT1);
			break;
		default:
			mexErrMsgTxt("Unexpected number of output arguments."); 
		}

		/*====================================================================
		get equalization data 
		=====================================================================*/
		drec.len = mxGetM(PARM1)*mxGetN(PARM1);
		drec.r   = mxGetPr(PARM1);
		drec.i   = NULL;
		
		if( drecAgc.r != NULL )
		{
			if( drec.len < (CARRIER_LEN*2*(DATA_FRAMES_PER_BLOCK*NUM_DATA_BLOCKS+1)) )
				mexErrMsgTxt("Trace buffer is to short to get freq Eq data!");

			drec.r += CARRIER_LEN*2*DATA_FRAMES_PER_BLOCK*NUM_DATA_BLOCKS;
			for( n = 0; n < CARRIER_LEN; n++ )
			{
				*drecAgc.r++ = *drec.r++;
				*drecAgc.i++ = *drec.r++;
			}
			drec.r   = mxGetPr(PARM1);
		}
	
		if( drec.len < (CARRIER_LEN*2*DATA_FRAMES_PER_BLOCK*NUM_DATA_BLOCKS) )
			mexErrMsgTxt("Trace buffer is to short get all symbols!");

		/*====================================================================
		read data and do detection
		=====================================================================*/
		errCount = readDataFramesFromMatlab(rxUserDataArray, drec );
	 
		//---- return the results to Matlab---------------------------------
		*errorCountPtr = copyReadData2Matlab(dDataBuffer, rxUserDataArray, errCount );
	}
	
	/*====================================================================
	Decode "SYMB"
	=====================================================================*/
	else if( strcmp(CmdStr, "symOld")==0 )
	{
		u16			n;

	    //---- Check for proper number of arguments ---------------
		if( nrhs != 2 )
			mexErrMsgTxt("Wrong number of input arguments.\nSyntax:  [errorCount, <userData>, <freqEq>] = mex_modem('symb', symbolArray)");

	   	//---- input vars ---------------------------
		drec.i   = NULL;
		drec.r   = mxGetPr(PARM1);
		drec.len = mxGetM(PARM1)*mxGetN(PARM1);
		
	   	//---- Allocate output vars ---------------------------
		dDataBuffer.len = DATA_BUFFER_LEN*2;
		dDataBuffer.r = NULL;
		dDataBuffer.i = NULL;
		drecAgc.r = NULL;
		drecAgc.i = NULL;
		
		switch( nlhs )
		{
		case 3:
			OUT3 = mxCreateDoubleMatrix(CARRIER_LEN, 1, mxCOMPLEX);
			drecAgc.r = mxGetPr(OUT3);
			drecAgc.i = mxGetPi(OUT3);
			drecAgc.len = CARRIER_LEN;
		case 2:
			OUT2 = mxCreateDoubleMatrix(dDataBuffer.len, 1, mxREAL);
			dDataBuffer.r = mxGetPr(OUT2);
		case 1:
			OUT1 = mxCreateDoubleMatrix(1, 1, mxREAL);
			errorCountPtr = mxGetPr(OUT1);
			break;
		default:
			mexErrMsgTxt("Unexpected number of output arguments."); 
		}

		/*====================================================================
		get equalization data 
		=====================================================================*/
		if( drecAgc.r != NULL )
		{
			for( n = 0; n < CARRIER_LEN; n++ )
			{
				*drecAgc.r++ = *drec.r++;
				*drecAgc.i++ = *drec.r++;
			}
		}
		else
		{

⌨️ 快捷键说明

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