📄 ext_transport232.c
字号:
default:
/* unknown telegram -> return with error */
mexPrintf("ExtSetTargetMsg: Unknown target response: %d\n", (uint8_T)ack_byte);
mexPrintf("ExtSetTargetMsg: userData->TelType: %d\n",(uint_T)userData->TelType);
#if DEBUG_MSG_LVL >= 1
{
char_T mb[28];
int16_T i;
if(ReadFile(userData->hCom, (LPSTR)&mb, 28, &nBytesGot, NULL)) {
mexPrintf("ExtSetTargetMsg: Subsequent bytes: ");
for(i=0; i< 28; i++)
mexPrintf("%d ", mb[i]);
mexPrintf("\n");
} else {
mexPrintf("ExtSetTargetMsg: Couldn't read any more bytes...\n");
}
}
#endif
return EXT_ERROR;
} /* switch (default) */
/* retrieve USR or DAT telegram, remaining telegram length in 'ack_byte' */
/* read 'ack_byte' more bytes from COM */
if(ReadFile(userData->hCom, (LPSTR)&(interceptDatBuf[TelLenInfoSize]), ack_byte, &nBytesGot, NULL)) {
if (nBytesGot != ack_byte) {
/* TIMEOUT occurred during reception of data */
mexPrintf ("ExtSetTargetMsg: timeout occurred during reception of intercepted user/data telegram (ReadFile)\n");
return EXT_ERROR;
}
else {
#if DEBUG_MSG_LVL >= 2
{
int_T i;
for(i=0; i<(int_T)(TelLenInfoSize+ack_byte); i++)
mexPrintf("ExtSetTargetMsg: incoming user/data telegram [%d/%d]) %d\n", i+1, (uint_T)interceptDatBuf[TelLenInfoSize-1], (uint_T)(interceptDatBuf[i]));
}
#endif
/* from here we exit the switch statement and loop back (while) */
}
}
else {
/* unspecified error during data reception */
mexPrintf ("ExtSetTargetMsg: unspecified error during reception of intercepted user/data telegram (ReadFile).\n");
return EXT_ERROR;
}
} /* switch */
#if DEBUG_MSG_LVL >= 3
mexPrintf("ExtSetTargetMsg: switch out\n");
#endif
}
} /* while(lookforACK) */
#if DEBUG_MSG_LVL >= 3
mexPrintf("ExtSetTargetMsg: OUT\n");
#endif
/* successfully received expecte acknowledgement -> return */
return EXT_NO_ERROR;
} /* acknowledgement section (end) */
}
else {
// Problem during data transmission (WriteFile)
mexPrintf ("ExtSetTargetMsg: Couldn't transmit all data values (WriteFile).\n");
{
DWORD err = GetLastError();
mexPrintf("Error code: %ld\n", err);
}
return EXT_ERROR;
}
}
else {
/* WriteFile() returned unsuccessfully */
mexPrintf("ExtSetTargetMsg: Unspecified error during data transmission (WriteFile).\n");
return EXT_ERROR;
}
} /* end ExtSetTargetMsg */
/* Function: ExtCloseConnection ================================================
* Abstract:
* Close the connection with the target.
*
* NOTES:
* o It is assumed that this function is always successful.
* o It is possible that user data will be NULL (due to a shutdown
* caused by an error early in the connect process).
*/
PUBLIC void ExtCloseConnection(ExternalSim *ES)
{
UserData *userData = (UserData *)esGetUserData(ES);
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtCloseConnection: IN\n");
#endif
if (userData == NULL) goto EXIT_POINT;
if (userData->hCom != INVALID_HANDLE_VALUE) {
// close serial interface 'hCom'
if(!CloseHandle(userData->hCom)) {
esSetError(ES, "Error when closing the serial interface.\n");
}
}
EXIT_POINT:
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtCloseConnection: OUT\n");
#endif
return; /* need something in the EXIT_POINT section */
} /* end ExtCloseConnection */
/* Function: ExtOpenConnection =================================================
* Abstract:
* Open the connection with the target.
*
* NOTES:
* o If an error is detected, set the error string via esSetError(ES)
* and return.
*
* o O.K. for this function to block (it is assumed that the connection
* procedure will complete "quickly")
*/
PUBLIC void ExtOpenConnection(ExternalSim *ES)
{
UserData *userData = (UserData *)esGetUserData(ES);
uint16_T port = userData->port;
uint32_T baudrate = userData->baudrate;
boolean_T verbosity = esGetVerbosity(ES);
HANDLE hCom;
static char COMxString[5]; // serial interface designator
char COMxStringParam[16];
DCB dcb;
COMMTIMEOUTS CommTimeouts;
char tmp[512]; // error messages
// default communication parameters (dummy)
#define DefaultComParam ":9600,n,8,1"
// default timeout value (ms) - send and receive
#define DefaultTimeout 1000
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtOpenConnection: IN\n");
#endif
// open serial interface 'COMxString'
sprintf(COMxString, "COM%1d", port);
hCom = CreateFile (COMxString, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
if (hCom == INVALID_HANDLE_VALUE)
{
sprintf(tmp, "Error while trying to open serial interface %s:\n", COMxString);
esSetError(ES, tmp);
goto EXIT_POINT;
}
// initialise 'DCB' structure
dcb.DCBlength = sizeof (DCB);
if (!GetCommState (hCom, &dcb))
{
esSetError(ES, "Error while trying to determine current state of the COM interface.\n");
goto EXIT_POINT;
}
sprintf (COMxStringParam, "%s%s", COMxString, DefaultComParam);
if (!BuildCommDCB (COMxStringParam, &dcb))
{
esSetError(ES, "Error while generating DCB data structure,\n");
goto EXIT_POINT;
}
// set transmission parameters
dcb.BaudRate = (unsigned long)baudrate; // transmission speed (bps)
dcb.fRtsControl = RTS_CONTROL_DISABLE; // RTS = 'low' (mis-used to generate a software 'reset'...
dcb.fOutX = FALSE; // disable XON/XOFF protocol
dcb.fInX = FALSE; // (both for TX and RX)
// initialise serial interface 'hCom'
if (!SetCommState (hCom, &dcb))
{
sprintf(tmp, "Error during initialisation of the serial interface %s:\n", COMxString);
esSetError(ES, tmp);
goto EXIT_POINT;
}
// reset 'hCom' and set length of input/output buffer to COMBUFSIZE (default: 2048) bytes (each)
if (!SetupComm (hCom, COMBUFSIZE, COMBUFSIZE))
{
sprintf(tmp, "Error during reset of the serial interface %s:\n", COMxString);
esSetError(ES, tmp);
goto EXIT_POINT;
}
if (verbosity) {
mexPrintf("serial port : %s\n", COMxString);
mexPrintf("baudrate : %ld\n", baudrate);
}
// initialise all timeouts (send/receive) as 'DefaultTimeout' (1000 ms)
CommTimeouts.ReadIntervalTimeout = DefaultTimeout;
CommTimeouts.ReadTotalTimeoutMultiplier = DefaultTimeout;
CommTimeouts.ReadTotalTimeoutConstant = DefaultTimeout;
CommTimeouts.WriteTotalTimeoutMultiplier = DefaultTimeout;
CommTimeouts.WriteTotalTimeoutConstant = DefaultTimeout;
SetCommTimeouts(hCom, &CommTimeouts);
// return HANDLE on serial interface through 'userData'
userData->hCom = hCom;
EXIT_POINT:
//Sleep(200);
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtOpenConnection: OUT\n");
#endif
return;
} /* end ExtOpenConnection */
/* Function: ExtUserDataCreate =================================================
* Abstract:
* Create the user data.
*/
PUBLIC UserData *ExtUserDataCreate()
{
UserData *ud = (UserData *)calloc(1, sizeof(UserData));
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtUserDataCreate called: IN\n");
#endif
if (ud != NULL) {
ud->hCom = INVALID_HANDLE_VALUE;
ud->TelType = 0;
ud->MsgTelIntercepted = FALSE;
ud->DataTelIntercepted = FALSE;
ud->UsrTelIntercepted = FALSE;
ud->ExtDisconnectConfirmed = FALSE;
ud->port = 0;
ud->baudrate = 0L;
}
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtUserDataCreate called: OUT\n");
#endif
return(ud);
} /* end ExtUserDataCreate */
/* Function: ExtUserDataDestroy ================================================
* Abstract:
* Destroy the user data.
*/
PUBLIC void ExtUserDataDestroy(UserData *userData)
{
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtUserDataDestroy called: IN\n");
#endif
if (userData != NULL) {
free(userData);
}
#if DEBUG_MSG_LVL >= 2
mexPrintf("ExtUserDataDestroy called: OUT\n");
#endif
} /* end ExtUserDataDestroy */
/* Function: ExtProcessArgs ====================================================
* Abstract:
* Process the arguments specified by the user in the 'Target Interface'
* panel of the 'External Mode Control' dialog. In the case of
* this serial communication example the args are:
* o port (1, 2, 3 or 4)
* o verbosity
* o baudrate (eg. 57600)
*
* Store values of settings into the userData.
*
* NOTES:
* o This function is only called as part of the connect procedure
* (EXT_CONNECT).
*
* o If an error is detected, set the error string via esSetError(ES)
* and return.
*/
PUBLIC void ExtProcessArgs(
ExternalSim *ES,
int nrhs,
const mxArray *prhs[])
{
UserData *userData = (UserData *)esGetUserData(ES);
/* ... Argument 1 - port */
if (nrhs >= 1 && !mxIsEmpty(prhs[0])) {
/* port name specified ('COMx')*/
uint16_T port;
const mxArray *mat = prhs[0];
int_T m = mxGetM(mat);
int_T n = mxGetN(mat);
const char msg[] =
"Port argument must be a real, scalar, integer value in the "
"range: [0-7].";
/* verify that we've got a real, scalar integer */
if (!mxIsNumeric(mat) || mxIsComplex(mat) || mxIsSparse(mat) ||
!mxIsDouble(mat) || (!(m ==1 && n ==1)) || !IS_INT(*mxGetPr(mat))) {
esSetError(ES, msg);
goto EXIT_POINT;
}
port = (uint16_T) *(mxGetPr(mat));
/* check port value */
if (port < 0 || port > 7) {
esSetError(ES, msg);
goto EXIT_POINT;
}
userData->port = port;
}
/* ... Argument 2 - verbosity */
if(nrhs >= 2) {
boolean_T verbosity;
const mxArray *mat = prhs[1];
int_T m = mxGetM(mat);
int_T n = mxGetN(mat);
const char msg[] =
"Verbosity argument must be a real, scalar, integer value in the "
"range: [0-1].";
/* verify that we've got a real, scalar integer */
if (!mxIsNumeric(mat) || mxIsComplex(mat) || mxIsSparse(mat) ||
!mxIsDouble(mat) || (!(m ==1 && n ==1)) || !IS_INT(*mxGetPr(mat))) {
esSetError(ES, msg);
goto EXIT_POINT;
}
verbosity = (boolean_T) *(mxGetPr(mat));
/* verify that it's 0 or 1 */
if ((verbosity != 0) && (verbosity != 1)) {
esSetError(ES, msg);
goto EXIT_POINT;
}
esSetVerbosity(ES, verbosity);
}
/* ... Argument 3 - baudrate value */
if (nrhs >= 3) {
uint32_T baudrate;
uint32_T b_div;
const mxArray *mat = prhs[2];
int_T m = mxGetM(mat);
int_T n = mxGetN(mat);
const char msg[] =
"Baud rate argument must be a real, scalar, integer value in the range: "
"[0-115200].";
/* verify that we've got a real, scalar integer */
if (!mxIsNumeric(mat) || mxIsComplex(mat) || mxIsSparse(mat) ||
!mxIsDouble(mat) || (!(m ==1 && n ==1)) || !IS_INT(*mxGetPr(mat))) {
esSetError(ES, msg);
goto EXIT_POINT;
}
baudrate = (uint32_T) *(mxGetPr(mat));
/* check baudrate value */
if (baudrate < 0 || baudrate > 115200) {
esSetError(ES, msg);
goto EXIT_POINT;
}
/* ensure that 'baudrate' is an admissible value */
b_div = (uint32_T)ceil(115200L/baudrate - 0.5);
if ((115200L/baudrate) != b_div)
{
baudrate = 115200L / b_div;
mexPrintf("Baudrate modified to %ld.\n", (long) baudrate);
}
userData->baudrate = baudrate;
} else {
/* use default */
userData->baudrate = 9600L;
}
EXIT_POINT:
return;
} /* end ExtProcessArgs */
/* [EOF] ext_transport.c */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -