?? smsc_sema.c
字號:
/* ==================================================================== * The Kannel Software License, Version 1.0 * * Copyright (c) 2001-2005 Kannel Group * Copyright (c) 1998-2001 WapIT Ltd. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, * if any, must include the following acknowledgment: * "This product includes software developed by the * Kannel Group (http://www.kannel.org/)." * Alternately, this acknowledgment may appear in the software itself, * if and wherever such third-party acknowledgments normally appear. * * 4. The names "Kannel" and "Kannel Group" must not be used to * endorse or promote products derived from this software without * prior written permission. For written permission, please * contact org@kannel.org. * * 5. Products derived from this software may not be called "Kannel", * nor may "Kannel" appear in their name, without prior written * permission of the Kannel Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE KANNEL GROUP OR ITS CONTRIBUTORS * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Kannel Group. For more information on * the Kannel Group, please see <http://www.kannel.org/>. * * Portions of this software are based upon software originally written at * WapIT Ltd., Helsinki, Finland for the Kannel project. */ /* * smsc_sema.c - implement sms2000 protocal by using X25 access * the data communication layer is implemented by using X28 protocol * * Code implement submit invoke, status invoke, deliver invoke session * there is no internal db for storing delivered and undelivered message * * IA5 is most common line coding scheme. * smsc_sema support only IA5 encoding, hex and binary line encoding is not * supported. * * smsc_sema support IA5 and GSM Data Code Scheme for delivered invoke message * smsc_sema support only IA5 Data Code Scheme for submit invoke message * * Reference : SMS2000 Version 4.0 Open Interface Specification * Open Source WAP Gateway Architecture Design * ESTI GSM 03.40 * * Hao Shi 2000 */#include <errno.h>#include <stdarg.h>#include <stdio.h>#include <stdlib.h>#include <string.h>#include <unistd.h>#include <fcntl.h>#include <termios.h>#include <sys/time.h>#include <sys/types.h>#include <sys/socket.h>#include <sys/param.h>#include <netinet/in.h>#include <netdb.h>#include "gwlib/gwlib.h"#include "smsc.h"#include "smsc_p.h"#include "alt_charsets.h"#include "smsc_sema.h"#include "sms.h"#ifndef CRTSCTS#define CRTSCTS 0#endifstatic unsigned char sema_counter[4] = "0000";static int sema_wait_report = 1;static int x28_data_mode = X28_COMMAND_MODE;SMSCenter * sema_open(char* smscnua, char* homenua, char* serialdevice, int waitreport){ SMSCenter *smsc; int nret = -1; smsc = smscenter_construct(); if(smsc == NULL) goto error; sprintf(smsc->name, "SEMA:X28:"); smsc->type = SMSC_TYPE_SEMA_X28; smsc->sema_smscnua = gw_strdup(smscnua); smsc->sema_homenua = gw_strdup(homenua); smsc->sema_serialdevice = gw_strdup(serialdevice); sema_wait_report = waitreport; smsc->sema_mt = sema_msglist_new(); if(smsc->sema_mt == NULL) goto error; smsc->sema_mo = sema_msglist_new(); if(smsc->sema_mo == NULL) goto error; /* Open the device properly. Remember to set the access codes correctly. */ debug("smsc.sema", 0, "sema_open: open datalink"); smsc->sema_fd = X28_open_data_link(smsc->sema_serialdevice); if(smsc->sema_fd == -1) goto error; /* test the outgoing callX28 to smsc center */ debug("smsc.sema", 0, "sema_open: test send link"); nret = X28_open_send_link(smsc->sema_fd, smsc->sema_smscnua); if(nret < 1){ sleep(2); nret = X28_open_send_link(smsc->sema_fd, smsc->sema_smscnua); if(nret < 1) goto error; } X28_close_send_link(smsc->sema_fd); return smsc;error: error(0, "sema_open: could not open"); smscenter_destruct(smsc); return NULL;}int sema_reopen(SMSCenter *smsc){ int nret = 0; debug("smsc.sema", 0, "reopening the connection"); /*deallocate*/ sema_msglist_free(smsc->sema_mt); sema_msglist_free(smsc->sema_mo); /*reallocate*/ smsc->sema_mt = sema_msglist_new(); if(smsc->sema_mt == NULL) goto error; smsc->sema_mo = sema_msglist_new(); if(smsc->sema_mo == NULL) goto error; memset(smsc->buffer,0,sizeof(smsc->buffer)); /* Open the device properly. Remember to set the access codes correctly. */ smsc->sema_fd = X28_reopen_data_link(smsc->sema_fd, smsc->sema_serialdevice); if(smsc->sema_fd == -1){ error(0,"sema_reopen_data_link: device file error"); goto error; } /*test outgoing call to the smsc */ nret = X28_open_send_link(smsc->sema_fd, smsc->sema_smscnua); if(nret < 1){ error(0,"test send data link failed"); goto error; } X28_close_send_link(smsc->sema_fd); return 0;error: error(0, "sema_reopen_data_link: failed"); return -1; }int sema_close(SMSCenter *smsc){ if(smsc->sema_fd > 0) close(smsc->sema_fd); /*deallocate*/ sema_msglist_free(smsc->sema_mt); sema_msglist_free(smsc->sema_mo); return 0;}int sema_submit_msg(SMSCenter *smsc, Msg *msg){ int nret = 0; struct sema_msg *lmsg = NULL; struct sm_submit_invoke *submit_sm = NULL; char x28sender[2] = "A3"; /* Validate msg */ if(smsc == NULL){ error(0,"sema_submit_msg: SMSC is empty"); goto error; } if(msg == NULL){ error(0, "sema_submit_msg: Msg is empty"); goto error; } if(msg_type(msg) != sms) { error(0, "sema_submit_sms: Msg is WRONG TYPE"); goto error; } /* user data header is not supported in sm2000 X25 access if(msg->sms.coding == DC_7BIT ...|| DC_UNDEF?){ error(0, "sema_submit_sms: submit invoke support in IA5 encoding(8 bits chars)"); goto error; } if(octstr_len(msg->sms.udhdata)){ error(0, "sema_submit_sms: submit invoke not support in IA5 encoding "); goto error; } */ lmsg = sema_msg_new(); submit_sm = gw_malloc(sizeof(struct sm_submit_invoke)); memset(submit_sm, 0, sizeof(struct sm_submit_invoke)); lmsg->type = 'S'; lmsg->encodetype = LINE_ENCODE_IA5; /* set operation reference */ increment_counter(); memcpy(lmsg->optref,sema_counter,4); /*set sme reference number*/ increment_counter(); memcpy(submit_sm->smerefnum, sema_counter, 4); /*we send as not key type*/ submit_sm->smereftype= 2; /*key type is 1*/ /*we set prority as normal*/ submit_sm->priority = 1; /*0 is high*/ /*set valid period type as relative*/ submit_sm->validperiodtype = 2; /* 1 is absolute */ /*time*/ submit_sm->validperiodrela = 1; /* from 0 to 143 , fomula is (V+1)*5 min*/ /*send msg without 00 header*/ submit_sm->msisdnlen= octstr_len(msg->sms.receiver); submit_sm->msisdn = octstr_copy(msg->sms.receiver,0,submit_sm->msisdnlen); /* X25 access will always append sender during data transfer */ submit_sm->origaddlen= 2; /* we need only to orignate address type */ submit_sm->origadd = octstr_create_from_data(x28sender,2); /*data encoding scheme ,support only IA5 in current version*/ submit_sm->DCS = 15; /*gsm is 0 ,IA5 is 15*/ /*protocal ,support only default value 0 in current version*/ submit_sm->protocal = 0; /*replypath*/ submit_sm->replypath= 0; /*gateway do not pay for reply*/ /*status report*/ if(sema_wait_report > 0) submit_sm->statusreportrequest =4; /* deliver success, in bin form 00000100*/ else submit_sm->statusreportrequest = 0;/* no report */ /* we support submit invoke only in IA5 line encoding*/ submit_sm->textsizeoctect = submit_sm->textsizeseptet = octstr_len(msg->sms.msgdata); /*copy msg buffer*/ submit_sm->shortmsg = octstr_copy(msg->sms.msgdata, 0, submit_sm->textsizeoctect); memset(submit_sm->smscrefnum,0,sizeof(submit_sm->smscrefnum)); /*pack the message body in 2kmsg*/ lmsg->msgbody = submit_sm; nret = sema_msg_session_mt(smsc, lmsg); gw_free(submit_sm); submit_sm = NULL; sema_msg_free(lmsg); lmsg = NULL; if(nret == SESSION_MT_RECEIVE_SUCCESS){ debug("smsc.sema", 0, "sema_submit_msg: message is successfully delivered"); return 1; /*success*/ } else if(nret == SESSION_MT_RECEIVE_TIMEOUT){ info(0, "sema_submit msg: session timed out without return"); return 0; } else if(nret == SESSION_MT_RECEIVE_ERR){ info(0, "sema_submit msg: smsc says submit failed!"); return 0; } return 1; error: if(submit_sm) gw_free(submit_sm); if(lmsg) sema_msg_free(lmsg); return -1;}int sema_receive_msg(SMSCenter *smsc, Msg **msg){ struct sema_msg *rmsg = NULL; struct sm_deliver_invoke *recieve_sm = NULL; while(sema_msglist_pop(smsc->sema_mo, &rmsg) == 1 ) { *msg = msg_create(sms); if(*msg==NULL) goto error; recieve_sm = (struct sm_deliver_invoke*) rmsg->msgbody; if(recieve_sm==NULL) goto error; /* as IA5(8 bit character) is the default line encoding used by X28 * and we do not support other line encoding scheme like binary or * hex encoding */ (*msg)->sms.coding = DC_8BIT; /* OIS in X28 implementation does not include udh field */ (*msg)->sms.sender = octstr_create_from_data( octstr_get_cstr(recieve_sm->origadd) +2, octstr_len(recieve_sm->origadd)-2); (*msg)->sms.receiver = octstr_create_from_data( octstr_get_cstr(recieve_sm->destadd) +2, octstr_len(recieve_sm->destadd)-2); (*msg)->sms.msgdata = octstr_duplicate(recieve_sm->shortmsg); (*msg)->sms.udhdata = octstr_create(""); gw_free(recieve_sm); sema_msg_free(rmsg); rmsg = NULL; } return 1;error: error(0, "sema_receive_msg: can not create Smart Msg"); return -1;}int sema_pending_smsmessage(SMSCenter *smsc){ char data[1024]; int ret = 0; char clrbuff[]="CLR\0"; char errbuff[]="ERR\0"; /* struct sema_msg* smsg = NULL;*/ /* Receive raw data */ ret = X28_data_read(smsc->sema_fd, smsc->buffer); if(ret == -1) { ret = X28_reopen_data_link(smsc->sema_fd, smsc->sema_serialdevice); if(ret == -1) goto error; return 0; } /* Interpret the raw data */ memset(data,0,sizeof(data)); while(X28_msg_pop(smsc->buffer, data) == 0 ) { if(strlen(data) > 0){ if(strstr(data,clrbuff) != NULL || strstr(data,errbuff) != NULL){ debug("smsc.sema", 0, "sema_pending_msg: Radio Pad Command line-%s",data); } else{ ret = sema_msg_session_mo(smsc, data); if(ret == -1) goto error; } memset(data,0,sizeof(data)); } } /* Signal that we got a MO message if mo list is not empty*/ if(smsc->sema_mo->first != NULL){ return 1; } return 0;error: error(0,"sema_pending message: device file error"); return -1;}static sema_msg* sema_msg_new(void){ struct sema_msg *msg = NULL; msg = gw_malloc(sizeof(struct sema_msg)); memset(msg, 0, sizeof(struct sema_msg)); return msg;}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -