📄 mgc_user.c
字号:
extern void mgc_user_terminate(CORBA_Environment* s_env, CORBA_Environment* r_env) { VERBOSE( ("mgc user terminate\n") );}/************************************************************ * Setup Transport ************************************************************/static void setup_transport() { Megaco_ReceiveHandle rh; MegacoSessionIp_IpOption port; MegacoSessionIp_IpOptions ipOptions; V( ("setup transport\n") ); rh.localMid = mid; /* Setup text port for both UDP and TCP */ port._d = MegacoSessionIp_Ip_port; port._u.port = 2944; ipOptions._buffer = &port; ipOptions._length = 1; ipOptions._maximum = 1; prepare_udp(&dummy); /* prepare receive handle for udp text */ rh.encodingMod = "megaco_pretty_text_encoder"; rh.encodingConfig = ""; rh.sendMod = "megaco_udp"; V( ("open UDP text (port 2944) connection\n") ); MegacoSessionUdp_open(NULL, ref_counter, &session_user_pid, &rh, &ipOptions, send_env); ASSERT_SEND(); prepare_tcp(&dummy); /* prepare receive handle for tcp text */ rh.sendMod = "megaco_tcp"; V( ("open TCP text (port 2944) connection\n") ); MegacoSessionTcp_listen(NULL, ref_counter, &session_user_pid, &rh, &ipOptions, send_env); ASSERT_SEND(); /* Setup binary port for both UDP and TCP */ port._u.port = 2945; prepare_udp(&dummy); rh.encodingMod = "megaco_binary_encoder"; rh.encodingConfig = ""; rh.sendMod = "megaco_udp"; V( ("open UDP binary (port 2945) connection\n") ); MegacoSessionUdp_open(NULL, ref_counter, &session_user_pid, &rh, &ipOptions, send_env); ASSERT_SEND(); prepare_tcp(&dummy); /* prepare receive handle for tcp binary */ rh.sendMod = "megaco_tcp"; V( ("open TCP binary (port 2945) connection\n") ); MegacoSessionTcp_listen(NULL, ref_counter, &session_user_pid, &rh, &ipOptions, send_env); ASSERT_SEND(); V( ("requests sent - now await response\n") );}/************************************************************ * Session User Callback Functions ************************************************************/Megaco_SessionUser_startSessionResponse__rs* Megaco_SessionUser_startSessionResponse__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, Megaco_Status *status, erlang_pid *pid, CORBA_Environment *oe_env) { Megaco_UserInfoValues uiv; V( ("received startSessionResponse\n") ); ASSERT_OK(status); /* Now we have got the id of the session process, */ session_pid.num = pid->num; session_pid.serial = pid->serial; session_pid.creation = pid->creation; strcpy(session_pid.node, pid->node); /* Create the user info values * The following values should be set: * reply_timer & resend_timer */ uiv._maximum = 0; uiv._length = 0; uiv._buffer = NULL; prepare_session(&dummy, pid); V( ("send startUser\n") ); Megaco_Session_startUser(NULL, *ref, &session_user_pid, &mid, &uiv, send_env); ASSERT_SEND(); free((void*)status); return (Megaco_SessionUser_startSessionResponse__rs*)NULL;}Megaco_SessionUser_sessionsResponse__rs* Megaco_SessionUser_sessionsResponse__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, Megaco_Status *status, Megaco_SessionRefList *reflist, CORBA_Environment *oe_env) { VERBOSE( ("received sessionResponse\n") ); free((void*)status); free((void*)reflist); return (Megaco_SessionUser_sessionsResponse__rs*)NULL;}Megaco_SessionUser_stopSessionResponse__rs* Megaco_SessionUser_stopSessionResponse__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, Megaco_Status *status, CORBA_Environment *oe_env) { VERBOSE( ("received stopSessionResponse\n") ); free((void*)status); return (Megaco_SessionUser_stopSessionResponse__rs*)NULL;}Megaco_SessionUser_handleConnect__rs* Megaco_SessionUser_handleConnect__cb(Megaco_SessionUser oe_obj, CORBA_long* ref, erlang_pid* pid, Megaco_ConnHandle* handle, CORBA_unsigned_short* XXX, CORBA_Environment* oe_env) { Megaco_Status result; int res; V( ("received handleConnect\n") ); /* * We should perhaps do some checking here, to see if this * is an accepted MG, but since this is a simple example * we assume that it is ok. */ print_pid("pid: ", pid); print_mid("localMid: ", &handle->localMid); print_mid("remoteMid: ", &handle->remoteMid); switch ((res = mg_connect(&handle->remoteMid))) { case MG_OK: case MG_CONNECTED: /* With UDP the MG can go and come without us knowing it, unless we * implement some sort of polling mechanism (which we don't in this * wery simple example), such as audit on the root termination. * We just assume this is OK, and start the MG starting sequence... */ V( ("connected (%d)\n", res) ); result._d = Megaco_ok; break; default: VERBOSE( ("connect failed: %dn", res) ); result._d = Megaco_errorDesc; result._u.desc.code = MEGACO_INSUFFICIENT_RESOURCES; result._u.desc.text._d = TRUE; result._u.desc.text._u.val = "Cannot allocate more than " MAX_MG_STRING; } prepare_session(&dummy, pid); V( ("send handleConnectResponse\n") ); Megaco_Session_handleConnectResponse(NULL, *ref, &result, send_env); free((void*)handle); return (Megaco_SessionUser_handleConnect__rs*)NULL;}Megaco_SessionUser_handleDisconnect__rs* Megaco_SessionUser_handleDisconnect__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, erlang_pid *pid, Megaco_ConnHandle *handle, CORBA_unsigned_short *XXX, CORBA_char *XXX2, CORBA_Environment *oe_env) { int res; V( ("received handleDisconnect\n") ); print_pid("pid: ", pid); print_mid("localMid: ", &handle->localMid); print_mid("remoteMid: ", &handle->remoteMid); if ((res = mg_disconnect(&handle->remoteMid)) != MG_OK) { VERBOSE( ("disconnect error %d from MG\n", res) ); } free((void*)handle); free((void*)XXX2); return (Megaco_SessionUser_handleDisconnect__rs*)NULL;}Megaco_SessionUser_handleSyntaxError__rs* Megaco_SessionUser_handleSyntaxError__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, erlang_pid *pid, Megaco_ReceiveHandle *handle, CORBA_unsigned_short *XXX, MegacoMessage_ErrorDescriptor *error, CORBA_Environment *oe_env) { VERBOSE( ("received handleSyntaxError\n") ); print_pid("pid: ", pid); print_error_desc("syntax error: ", error); free((void*)handle); free((void*)error); return (Megaco_SessionUser_handleSyntaxError__rs*)NULL;}Megaco_SessionUser_handleMessageError__rs* Megaco_SessionUser_handleMessageError__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, erlang_pid *pid, Megaco_ConnHandle *handle, CORBA_unsigned_short *XXX, MegacoMessage_ErrorDescriptor *error, CORBA_Environment *oe_env) { VERBOSE( ("received handleMessageError\n") ); print_pid("pid: ", pid); print_mid("localMid: ", &handle->localMid); print_mid("remoteMid: ", &handle->remoteMid); print_error_desc("message error: ", error); free((void*)handle); free((void*)error); return (Megaco_SessionUser_handleMessageError__rs*)NULL;}Megaco_SessionUser_handleTransRequest__rs* Megaco_SessionUser_handleTransRequest__cb(Megaco_SessionUser oe_obj, CORBA_long *ref, erlang_pid *pid, Megaco_ConnHandle *handle, CORBA_unsigned_short *XXX, Megaco_ActionRequests *action, CORBA_Environment *oe_env) { Megaco_Status result; Megaco_ActionReplies actReplies; MgInfo* mgP; int res; V( ("received handleTransRequest\n") ); print_pid("pid: ", pid); print_mid("localMid: ", &handle->localMid); print_mid("remoteMid: ", &handle->remoteMid); switch ((res = mg_lookup(&handle->remoteMid, &mgP))) { case MG_OK: V( ("handle transaction\n") ); result._d = Megaco_ok; handle_transaction_requests(mgP, action, &result, &actReplies); break; default: V( ("lookup failed: %d\n", res) ); result._d = Megaco_errorDesc; result._u.desc.code = MEGACO_INTERNAL_GATEWAY_ERROR; result._u.desc.text._d = TRUE; result._u.desc.text._u.val = "MG not yet connected"; actReplies._maximum = 0; actReplies._length = 0; actReplies._buffer = NULL; break; } prepare_session(&dummy, pid); V( ("send handleTransRequestResponse\n") ); Megaco_Session_handleTransRequestResponse(NULL, *ref, &result, FALSE, &actReplies, send_env); free_action_replies(&actReplies); free((void*)handle); free((void*)action); return (Megaco_SessionUser_handleTransRequest__rs*)NULL;}/* AAAARRRG, UGLY */static void free_action_replies(Megaco_ActionReplies* actRepliesP) { int i; for( i = 0 ; i < actRepliesP->_length ; i++) { free(actRepliesP->_buffer[i].commandReply._buffer); } free(actRepliesP->_buffer);}static void handle_transaction_requests(MgInfo* mgP, Megaco_ActionRequests *actRequestsP, Megaco_Status* statusP, Megaco_ActionReplies* actRepliesP) { int i; V( ("trans request for Mg '%s' in state %d\n", mgP->mid, mgP->state) ); statusP->_d = Megaco_ok; actRepliesP->_maximum = actRequestsP->_maximum; actRepliesP->_length = actRequestsP->_length; if (actRepliesP->_length == 0) { actRepliesP->_buffer = NULL; return; } actRepliesP->_buffer = malloc((actRepliesP->_length) * sizeof(MegacoMessage_ActionReply)); if (actRepliesP->_buffer == NULL) { V( ("(act) memory alloc failed\n") ); mgc_exit(send_env, receive_env); } /* * The proper way to do this would of course be to send a reply for * each action request. But since this is a simple example we abort * as soon as status is not ok. */ for (i = 0 ; (i < actRepliesP->_length) && (statusP->_d == Megaco_ok) ; i++) { handle_transaction_request(mgP, &actRequestsP->_buffer[i], statusP, &actRepliesP->_buffer[i]); } /* * If result is not Megaco_ok, then we send an "empty" ActionReply */ if (statusP->_d != Megaco_ok) { V( ("(act) abort transaction\n") ); actRepliesP->_maximum = 0; actRepliesP->_length = 0; free(actRepliesP->_buffer); }}static void handle_transaction_request(MgInfo* mgP, MegacoMessage_ActionRequest* actRequestP, Megaco_Status* statusP, MegacoMessage_ActionReply* actReplyP) { MegacoMessage_ActionRequest_commandRequests* cmdReqP = &actRequestP->commandRequests; MegacoMessage_ActionReply_commandReply* cmdRepP = &actReplyP->commandReply; V( ("context id: %d\n", (int) actRequestP->id) ); actReplyP->id = actRequestP->id; // If any command goes wrong we abort everything (simple...) actReplyP->errorDescriptor._d = FALSE; actReplyP->contextReply._d = FALSE; cmdRepP->_maximum = cmdReqP->_maximum; cmdRepP->_length = cmdReqP->_length; if (cmdRepP->_length == 0) { V( ("no command requests found\n") ); cmdRepP->_buffer = NULL; return; } cmdRepP->_buffer = malloc((cmdRepP->_length) * sizeof(MegacoMessage_ActionReply)); if (cmdRepP->_buffer == NULL) { V( ("(cmd) memory alloc failed\n") ); mgc_exit(send_env, receive_env); } /* * The proper way to do this would of course be to send a reply for * each command request. But since this is a simple example we abort * as soon as status is not ok. */ { int i; for(i = 0 ; (i < cmdRepP->_length) && (statusP->_d == Megaco_ok) ; i++) { handle_command_request(mgP, actRequestP->id, &cmdReqP->_buffer[i], &cmdRepP->_buffer[i], statusP); } } /* If result is not Megaco_ok, then we send an "empty" command reply */ if (statusP->_d != Megaco_ok) { V( ("(cmd) abort transaction\n") ); cmdRepP->_maximum = 0; cmdRepP->_length = 0; free(cmdRepP->_buffer); }}static void handle_command_request(MgInfo* mgP,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -