📄 x25lib.c
字号:
#include "..\sys\Include.h"
unsigned char * sSendBuff[MAX_BSC_CONNECT];
//unsigned char * sRecvBuff[MAX_BSC_CONNECT];
//unsigned char * sRecvBuffUplink[MAX_BSC_CONNECT];
// 初试化x.25的环境, 如果初试失败可以根据其失败的代码取其原因
int Init25(void)
{
int i;
int Cid;
struct x25stat buffer;
if(x25init(0,0) < 0)
{
return FAILURE ;
}
/* 预先申请好收发空间 */
for (i=0;i<MAX_BSC_CONNECT;i++)
{
if ( (sSendBuff[i]=x25alloc(X25_MAXDATALEN)) == NULL )
return FAILURE;
// if ( (sRecvBuff[i]=x25alloc(X25_MAXDATALEN)) == NULL )
// return FAILURE;
/// if ( (sRecvBuffUplink[i]=x25alloc(X25_MAXDATALEN_UPLINK)) == NULL )
// return FAILURE;
}
f_port_lsn=fopen("Port_lsn.dat","r+bc");
if (f_port_lsn==NULL)
{
f_port_lsn=fopen("Port_lsn.dat","w+bc");
}
else
{
/* 读文件释放虚链路 */
fread(&BscX25_Port_Lsn[0],sizeof(X25_PORT_LSN_t),MAX_BSC_CONNECT ,f_port_lsn);
for(i=0;i<MAX_BSC_CONNECT;i++)
{
BscX25_Port_Lsn[i].BscAddr[BSC_ADDR_LEN]=0;
if (BscX25_Port_Lsn[i].DownlinkFlag==1)
{
if ( x25mkconn( &Cid, BscX25_Port_Lsn[i].DownlinkPort, BscX25_Port_Lsn[i].DownlinkLsn, X25WAIT) >= 0)
{
if (x25status(Cid, &buffer, NULL)==0)
{
/* 如果连接 */
if(buffer.xs_status<=XS_SESSION )
{
HangupConnect( Cid,NULL,NULL,NULL,0);
}
}
// HangupConnect( Cid,BscX25_Port_Lsn[i].BscAddr , g_X25LocalAddr ,NULL,0);
}
}
if (BscX25_Port_Lsn[i].UplinkFlag==1)
{
if ( x25mkconn( &Cid, BscX25_Port_Lsn[i].UplinkPort, BscX25_Port_Lsn[i].UplinkLsn, X25WAIT) == 0)
{
if (x25status(Cid, &buffer, NULL)==0)
{
/* 如果连接 */
if(buffer.xs_status<=XS_SESSION )
{
HangupConnect( Cid,NULL , NULL ,NULL,0);
}
}
}
}
}
/* 全置0 */
Del_Port_lsn(0,2);
}
return SUCCESS;
}
//退出x.25 的环境 系统退出时最好调用此函数
int Exit25(void)
{
if(x25exit() < 0)
{
return FAILURE;
}
return SUCCESS;
}
/* 连接远端的DTE */
int CallToRemote(char *sRemoteAddr , char *sLocalAddr , int nPort , char *sUserInfo , int nUserInfoLen , int nMode)
{
struct x25data rUserData;
struct x25data rFacility;
OSINT nCid;
OSINT nInfo = 0;
unsigned char Compressremote[7];
struct x25doneinfo done_info;
int error;
memset(Compressremote,0,7);
rFacility.xd_len = 28;
rFacility.xd_data[0]=0;
rFacility.xd_data[1]=0x0f;
rFacility.xd_data[2]=0xcb;
rFacility.xd_data[3]=0x0a;
rFacility.xd_data[4]=0x12;
rFacility.xd_data[5]=0x37;
// rFacility.xd_data[6]=0x00;
// rFacility.xd_data[7]=0;
// rFacility.xd_data[8]=0;
// rFacility.xd_data[9]=0;
// rFacility.xd_data[10]=0;
// rFacility.xd_data[11]=0x01;
// rFacility.xd_data[12]=0x23;
rFacility.xd_data[13]=0;
rFacility.xd_data[14]=0xc9;
rFacility.xd_data[15]=0x0a;
rFacility.xd_data[16]=0x12;
rFacility.xd_data[17]=0x37;
// rFacility.xd_data[18]=0;
// rFacility.xd_data[19]=0;
// rFacility.xd_data[20]=0;
// rFacility.xd_data[21]=0;
// rFacility.xd_data[22]=0;
// rFacility.xd_data[23]=0x04;
// rFacility.xd_data[24]=0x56;
rFacility.xd_data[25]=0;
rFacility.xd_data[26]=0x0b;
rFacility.xd_data[27]=0;
/* 本地地址 */
AddrStringTo7Compress(sLocalAddr,Compressremote);
memcpy(&rFacility.xd_data[6],Compressremote,7);
/* 远端地址 */
AddrStringTo7Compress(sRemoteAddr,Compressremote);
memcpy(&rFacility.xd_data[18],Compressremote,7);
rUserData.xd_len = 0;
/* 初试化用户数据 请不要超过128 byte */
if( (rUserData.xd_len=nUserInfoLen) > 0 )
{
memcpy(rUserData.xd_data , sUserInfo , nUserInfoLen );
}
/* 按非等待方式连接对方 */
if ( x25xcall(&nCid, X25NOWAIT, nPort, nInfo, &rFacility, &rUserData, sRemoteAddr, sLocalAddr, X25NULLFN)< 0) {
printf("\n ErrorNo = %d\n" , x25error() );
return FAILURE ;
}
if (x25done(nCid, CALLTOREMOTE_TIME_LEN, &done_info) < 0 )
{
error = x25error();
/* the request hasn't completed,cancel request */
if (error == ENETPEND)
{
//Submit the cancel. X25cancel is always submitted in wait mode.
if (x25cancel(nCid, NULL)< 0 )
{
//x25cancel() failed
error = x25error();
if (error != ENETICMD)
{
/*
Do error handling
*/
}
}
else
{
/* X25cancel */
x25done(nCid, XD_TONOW, &done_info);
}
}
return FAILURE ;
}
if ( done_info.xi_retcode==0 )
{
/* 连接成功 */
return nCid;
}
else
{
return FAILURE;
}
}
/*
//listen 和 accept 同时完成
int ListenFromRetmote(int nPort , char *sRemoteAddr , char *sLocalAddr , char *sUserData , int *nUserDataLen)
{
OSINT nCid;
OSINT nInfo = 0;
struct x25data rFacility;
struct x25data rUserData;
rFacility.xd_len = 0;
rUserData.xd_len = 0;
if(x25xlisten (&nCid, X25WAIT, nPort, nInfo, &rFacility, &rUserData, sRemoteAddr, sLocalAddr, X25NULLFN)< 0)
{
printf("\n error = %d\n" , x25error() );
return FAILURE;
}
*nUserDataLen = rUserData.xd_len ;
memcpy(sUserData , rUserData.xd_data , *nUserDataLen );
return nCid ; // 返回连接句柄
}
*/
/* listen 和 accept 分开完成
*/
//int ListenFromRetmote(int nPort , char *sRemoteAddr , char *sLocalAddr , char *sUserData, int *nUserDataLen, int Tid)
void X25UplinkListen(int *Tid)
{
OSINT nCid;
OSINT nInfo = XI_QBIT;
struct x25data rFacility;
struct x25data rUserData;
unsigned char unpackbuf[100];
unsigned char Senddata[100];
unsigned char FailureReason[3];
int len;
unsigned char Compressremote[7];
int OperatorCheck;
int nTid;
/* accept */
struct x25data facility;
struct x25data udata;
OSINT info ;
int error ;
/* Bind */
VBIND_t m_bind;
/* X25卡的端口号和逻辑会话号 */
unsigned OSINT port; /* EiconCard port number */
unsigned OSINT lsn; /* logical session number */
struct x25doneinfo done_info; /* Completed request information */
char RemoteBscAddress[BSC_ADDR_LEN+2048];
char LocalCBCAddress[BSC_ADDR_LEN+2048];
/* 告警描述字串 */
unsigned char cWarningDescription[WARNING_DESC_LEN];
nTid=*Tid;
/* incorrect-ID-or-password */
FailureReason[0]=2;
FailureReason[1]=1;
FailureReason[2]=3;
for(;;)
{
if (s_BSCCellInfo[nTid].bFlag==0)
{
/* 上行监听线程退出 */
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
// ExitThread(1);
}
/* 连接关闭,退出线程 */
if(s_BscConnectInfo[nTid].ConnectOpen==OFF)
{
// //在接收线程释放
// if(s_BscConnectInfo[nTid].UplinkStatus==BSC_STEADY)
// {
// Del_Port_lsn(nTid,1);
/* 释放链路 */
// HangupConnectNOWAIT(s_BscConnectInfo[nTid].X25UpLinkHandle,NULL, NULL ,NULL,0);
// s_BscConnectInfo[nTid].UplinkStatus=BSC_DISCONNECT;
// }
/* 上行监听线程退出 */
while(s_BscConnectInfo[nTid].UplinkStatus==BSC_STEADY)
{
Sleep(1000);
}
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
#ifdef DEBUG_PRINT
printf("x25Uplink listen thread exit,BscId=%d\n",*(unsigned short *)&s_BscConnectInfo[nTid].BscIdentifier[0]);
#endif
ExitThread(1);
}
memset(unpackbuf,0,100);
memset(Senddata,0,100);
memset(&m_bind,0,sizeof(VBIND_t));
/*
Senddata[0] = 48;
Senddata[1] = 13;
Senddata[2] = 160;
Senddata[3] = 11;
Senddata[4] = 128;
Senddata[5] = 4;
Senddata[6] = 101;
Senddata[7] = 99;
Senddata[8] = 115;
Senddata[9] = 99;
Senddata[10] = 130;
Senddata[11] = 3;
Senddata[12] = 49;
Senddata[13] = 50;
Senddata[14] = 51;
*/
rFacility.xd_len=0;
rUserData.xd_len = 0;
/* 给远端BSC地址赋值 */
memset(RemoteBscAddress,0,BSC_ADDR_LEN+1);
memcpy(RemoteBscAddress,s_BscConnectInfo[nTid].BscAddr,BSC_ADDR_LEN);
/* 给CBC地址赋值 */
memset(LocalCBCAddress,0,BSC_ADDR_LEN+1);
memcpy(LocalCBCAddress,g_X25LocalAddr,BSC_ADDR_LEN);
if(s_BscConnectInfo[nTid].UplinkStatus==BSC_DISCONNECT)
{
if(x25xlisten (&nCid, X25NOWAIT, PORT, nInfo, &rFacility, &rUserData, RemoteBscAddress, LocalCBCAddress, X25NULLFN)< 0)
{
printf("\n error = %d\n" , x25error() );
// ExitThread(1);
}
while ( x25done(nCid, 3 , &done_info) < 0 )
{
if (s_BSCCellInfo[nTid].bFlag==0)
{
/* 上行监听线程退出 */
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
// ExitThread(1);
}
/* 连接关闭,退出线程 */
if(s_BscConnectInfo[nTid].ConnectOpen==OFF)
{
if(s_BscConnectInfo[nTid].UplinkStatus==BSC_STEADY)
{
Del_Port_lsn(nTid,1);
/* 释放链路 */
HangupConnectNOWAIT(s_BscConnectInfo[nTid].X25UpLinkHandle,NULL, NULL ,NULL,0);
// HangupConnectNOWAIT(s_BscConnectInfo[nTid].X25UpLinkHandle,&s_BscConnectInfo[nTid].BscAddr[0], g_X25LocalAddr ,NULL,0);
s_BscConnectInfo[nTid].UplinkStatus=BSC_DISCONNECT;
}
/* 上行监听线程退出 */
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
/* 安全退出 */
error = x25error();
/* the request hasn't completed,cancel request */
if (error == ENETPEND)
{
//Submit the cancel. X25cancel is always submitted in wait mode.
if (x25cancel(nCid, NULL)< 0 )
{
//x25cancel() failed
error = x25error();
if (error != ENETICMD)
{
/*
Do error handling
*/
}
}
else
{
/* X25cancel */
x25done(nCid, XD_TONOW, &done_info);
}
}
#ifdef DEBUG_PRINT
printf("x25Uplink listen thread exit,BscId=%d\n",*(unsigned short *)&s_BscConnectInfo[nTid].BscIdentifier[0]);
#endif
ExitThread(1);
}
/*
X25done() failed. If the error is ENETPEND, then the request hasn't completed - keep
polling. Otherwise, we have a less recoverable error - exit.
*/
error = x25error();
if (error != ENETPEND)
{
//break;
/*
Do error handling
*/
}
}
switch (done_info.xi_retcode)
{
case 0:
{
/*
Request completed successfully!
The connection is not yet established. Remote, local, facility, and udata will
be updated.
Depending on those values the application will accept or reject the call by
doing x25xhangup or x25accept. For example, the udata may contain a password
for validation.
*/
/*
Accepting the call.
submit x25accept().
*/
// rFacility.xd_len=done_info.xi_len;
// memcpy(rFacility.xd_data,done_info.xi_buf,rFacility.xd_len);
}
break;
case ENETCMDCANC:
/*
No connection established.
The listen was cancel by the user application.
The user application issue a x25cancel.
See x25cancel() example to see how to cancel a pending request (listen)
*/
// x25cancel(nCid, NULL);
goto stop;
break;
default:
/*
No connection established.
Handle remaining return codes.
See list of return codes.
*/
// x25cancel(nCid, NULL);
goto stop;
break;
}
/* ----------------------------------- */
/* Accept facility */
// facility.xd_len = rFacility.xd_len ;
// memcpy(facility.xd_data,rFacility.xd_data,facility.xd_len);
/* Accept */
info=0;
facility.xd_len = 0x10;
facility.xd_data[0]=0x00;
facility.xd_data[1]=0x0f;
facility.xd_data[2]=0xc9;
facility.xd_data[3]=0x0a;
facility.xd_data[4]=0x12;
facility.xd_data[5]=0x37;
facility.xd_data[6]=0x00;
facility.xd_data[7]=0x00;
facility.xd_data[8]=0x00;
facility.xd_data[9]=0x00;
facility.xd_data[10]=0x00;
facility.xd_data[11]=0x04;
facility.xd_data[12]=0x56;
facility.xd_data[13]=0x00;
facility.xd_data[14]=0x0b;
facility.xd_data[15]=0x00;
AddrStringTo7Compress(s_BscConnectInfo[nTid].BscAddr,Compressremote);
memcpy(&facility.xd_data[6],Compressremote,7);
udata.xd_len=0;
/* 返回确认 */
if ( x25accept(&nCid,info,&facility,&udata,s_BscConnectInfo[nTid].BscAddr,g_X25LocalAddr,X25NULLFN) < 0 )
{
/*
Cannot submit the x25accept. Call x25error to get the error message.
*/
printf("\n error = %d\n" , x25error() );
// ExitThread(1);
/*
Do error handling;
*/
}
while ( x25done(nCid, 3, &done_info) < 0 )
{
if (s_BSCCellInfo[nTid].bFlag==0)
{
/* 上行监听线程退出 */
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
}
/* 连接关闭,退出线程 */
if(s_BscConnectInfo[nTid].ConnectOpen==OFF)
{
/* 安全退出 */
error = x25error();
/* the request hasn't completed,cancel request */
if (error == ENETPEND)
{
//Submit the cancel. X25cancel is always submitted in wait mode.
if (x25cancel(nCid, NULL)< 0 )
{
//x25cancel() failed
error = x25error();
if (error != ENETICMD)
{
/*
Do error handling
*/
}
}
else
{
/* X25cancel */
x25done(nCid, XD_TONOW, &done_info);
}
}
/* 释放链路 */
HangupConnectNOWAIT(nCid,NULL, NULL ,NULL,0);
s_BscConnectInfo[nTid].UplinkStatus=BSC_DISCONNECT;
/* 上行监听线程退出 */
s_BscConnectInfo[nTid].UplinkThreadOpen=OFF;
#ifdef DEBUG_PRINT
printf("x25Uplink listen thread exit,BscId=%d\n",*(unsigned short *)&s_BscConnectInfo[nTid].BscIdentifier[0]);
#endif
ExitThread(1);
}
/*
X25done() failed. If the error is ENETPEND, then
the request hasn't completed - keep polling.
Otherwise, we have a less recoverable error - exit.
*/
error = x25error();
if (error != ENETPEND)
{
/*
Do error handling, and typically x25exit() and exit();
*/
}
}
switch (done_info.xi_retcode)
{
case 0:
/*
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -