170 likes | 322 Views
CCL MGCP Protocol Stack. Shang-Chih Tsai Sctsai@itri.org.tw. Features of the Stack. The Stack currently supports both Win32 and Solaris platform. The Stack provides a C language API.
E N D
CCL MGCP Protocol Stack Shang-Chih Tsai Sctsai@itri.org.tw
Features of the Stack • The Stack currently supports both Win32 and Solaris platform. • The Stack provides a C language API. • The Stack implemented the "At-Most-Once" functionality (section 3.6.1 of RFC 2705). Also, it implemented a retransmission mechanism (section 3.6.3 of RFC2705 ) while sending messages with UDP.
MGCP1.0 APIs • mgcMsg : APIs for messages • mgcAck : APIs for acknowledgements • mgcLoop : APIs for waiting incoming messages and sending outgoing messages(or acknowledgments) • mgcSock • mgcHash • mgcStr
Programming Model • Incoming messages Application process and generate acknowledgement Application MGCP calls application defined MSG callback function Ack Another MGCP process mgcLoop Message CCL’s MGCP protocol stack
Initialize mgcLoop int main(int argc, char**argv) { struct mgcExtEvents events[2]; struct timeval timeOut = {60,0}; mgcInit(); events[0].fd = 0; events[0].cb = NULL; /* no user-defined events */ mgcLoopSetDelay(50000); /* initial resend delay = 50 msec */ mgcLoop(2427, doMsg, doAck, events, &timeOut, doTimeout); }
Message Callback Function int doMsg(mgcMsg msg) { /* handle incoming command messages */ switch( mgcMsgGetType(msg) ) { case mgcCreatConn: handleCreatConn(); break; default: break; } } mgcMsgFree(msg); /* responsible (could pass on) */ return 0; }
Programming Model • Outgoing messages External Event Application process and generate MGCP message Application MGCP calls application defined ACK callback function Message Another MGCP process mgcLoop Ack CCL’s MGCP protocol stack
Send Message mgcSockAddr dst_addr; mgcMsg mgcComm; /* set destination address */ dst_addr = mgcSockAddrNewDom(“gw.ccl.itri.org.tw”, 2427); /* set the MGCP command verb, endpoint and TID */ mgcComm = mgcMsgNew(mgcCreatConn); mgcMsgSetEPt(mgcComm, “20@gw.ccl.itri.org.tw”); mgcMsgSetTId(mgcComm,”1007”); / * set command parameters */ mgcMsgAddParm(mgcComm, "C", “1”); /* call ID */ mgcMsgAddParm(mgcComm, "X", ”5”); /* request ID */ mgcMsgAddParm(mgcComm, "L", “P:3-4,A:G.711,B:32-64,E:ON”); mgcMsgAddParm(mgcComm, "M", “SENDRECEV”); mgcMsgAddParm(mgcComm, "S", “RT”); mgcMsgSend(mgcComm, dst_addr); CRCX 1007 20@gw.ccl.itri.org.tw MGCP 1.0 X:5 L:P:3-4,A:G.711,B:32-64,E:ON M:SENDRECV S:RG C:1
Send Acknowledge /* callback function that informing us an incoming MGCP command */ int doMsg(mgcMsg msg) { mgcAck ack = NULL; /* process the command here */ /* send the response to the command */ ack = mgcAckNew(mgcAckOK); mgcAckSetTId(ack, mgcMsgGetTId(msg)); mgcAckAddParm(ack, "I", “ABCDEFGHIJ11” ); mgcAckSend(ack, mgcMsgGetAddr(msg)); … } 200 1007 OK I: ABCDEFGHIJ11
mgcStr MGCP_API mgcStr mgcStrNew(void); MGCP_API int mgcStrLen(mgcStr); MGCP_API void mgcStrClr(mgcStr); MGCP_API void mgcStrFree(mgcStr); MGCP_API void mgcStrCat(mgcStr, char*); MGCP_API void mgcStrCatN(mgcStr, char*, int); MGCP_API char* mgcStrAsCStr(mgcStr); struct mgcStrObj { char* text; long len, alloced; }; mgcStr mgcStrNew() { mgcStr _this; _this = malloc(sizeof *_this); /* ErrorCheck */ _this->len = 0; _this->alloced = MINALLOC; // MINALLOC = 200 _this->text = malloc(MINALLOC); mgcStrClr(_this); return _this; }
mgcHash struct mgcHashObj { Entry* table; int CELLS, elements; int keysUpper, strings; Entry iterNext; /* next entry in current bucket */ int bucketNext; /* next bucket to search */ }; typedef struct EntryObj *Entry; struct EntryObj { char* key; char* val; Entry next; }; table iterNext /* * CELLs = number of entries in table (may grow) * keysUpper: bool should keys be mapped to upper case * strings: mgcHashType should val be copied (cstrings and ints) * by mgcHashAdd * keys are always strings and always copied */ bucketNext Entrys
mgcHash API • MGCP_API mgcHash mgcHashNew(int initSize, int keysUpper, mgcHashType strings); • MGCP_API void mgcHashFree(mgcHash, void (*freeVal)(void*)); • /* add pair key/val to hash, return old value */ MGCP_API void* mgcHashAdd(mgcHash, char* key, void* val); • MGCP_API void* mgcHashDel(mgcHash, char* key); • /* return val for key in hash. NULL if not found. */ MGCP_API void* mgcHashItem(mgcHash, char* key); • MGCP_API void mgcStartKeys(mgcHash); • MGCP_API char* mgcNextKeys(mgcHash); • MGCP_API int mgcHashSize(mgcHash);
mgcSock struct mgcSockAddrObj { char* domain_; int port_; struct sockaddr_in addr_; mgcSockAddr next_; }; freeList MGCP_API mgcSockAddr mgcSockAddrNewDom(char* domain, int port); MGCP_API mgcSockAddr mgcSockAddrDup(mgcSockAddr); MGCP_API int mgcSockAddrBind(mgcSockAddr, int fd); MGCP_API int mgcSockAddrSendTo(mgcSockAddr, int fd, mgcStr); MGCP_API mgcSockAddr mgcSockAddrRecvFrom(int fd, mgcStr); MGCP_API void mgcSockAddrFree(mgcSockAddr); MGCP_API char* mgcSockAddrGetDomain(mgcSockAddr); MGCP_API int mgcSockNew(void);
mgcMsg struct mgcMsgObj { mgcMsgType type_; mgcStr asStr_; mgcHash parms_; char* tId_; char* ePt_; mgcStr sesParms_; mgcSockAddr srcAddr_; }; CRCX100720@gw.ccl.itri.org.tw MGCP 1.0 X:5 L:P:3-4,A:G.711,B:32-64,E:ON M:SENDRECV S:RG C:1
mgcAck struct mgcAckObj { mgcAckType type_; mgcStr asStr_; char* tId_; mgcHash parms_; mgcStr sesParms_; mgcSockAddr srcAddr_; }; 2001007 OK I: ABCDEFGHIJ11
mgcLoop • Trace code mgcLoop.c • ackNrecv: outstanding sent messages not yet acknowledged :maps message Tid to the count of messages sent • msgActv: stores active messages received yet to be acknowledged: maps message Tid to a dummy • msgComp1: moves messages from the active list to the completed list maps message Tid to the duplicate acknowledgement to be sent • msgComp2: mirror image of msgComp1 delayed by 30 seconds
mgcAlarm Start Time: 12345000 ms HEAP 10 End Time: 12345005 ms 30 20 new 40 70 50 15 HEAP Start Time: 12345005 ms 5 Set timer = 5 25 10 35 65 45 15