SOCKET BRANCH:
[lcr.git] / action.cpp
index 0bb68cd..ab8e586 100644 (file)
@@ -9,63 +9,11 @@
 **                                                                           **
 \*****************************************************************************/ 
 
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <poll.h>
 #include "main.h"
-#include "linux/isdnif.h"
 
 extern char **environ;
 
 
-/* create caller id from digits by comparing with national and international
- * prefixes.
- */
-char *nationalize_callerinfo(char *string, int *ntype)
-{
-       if (!strncmp(options.international, string, strlen(options.international)))
-       {
-               *ntype = INFO_NTYPE_INTERNATIONAL;
-               return(string+strlen(options.international)); 
-       }
-       if (!strncmp(options.national, string, strlen(options.national)))
-       {
-               *ntype = INFO_NTYPE_NATIONAL;
-               return(string+strlen(options.national)); 
-       }
-       *ntype = INFO_NTYPE_SUBSCRIBER;
-       return(string);
-}
-
-/* create number (including access codes) from caller id
- * prefixes.
- */
-char *numberrize_callerinfo(char *string, int ntype)
-{
-       static char result[256];
-
-       switch(ntype)
-       {
-               case INFO_NTYPE_INTERNATIONAL:
-               UCPY(result, options.international);
-               SCAT(result, string);
-               return(result);
-               break;
-
-               case INFO_NTYPE_NATIONAL:
-               UCPY(result, options.national);
-               SCAT(result, string);
-               return(result);
-               break;
-
-               default:
-               return(string);
-       }
-}
-
-
 /*
  * process init 'internal' / 'external' / 'remote' / 'vbox-record' / 'partyline'...
  */
@@ -121,12 +69,13 @@ void EndpointAppPBX::action_init_remote(void)
 {
        struct route_param      *rparam;
        struct port_list        *portlist = ea_endpoint->ep_portlist;
-       struct message          *message;
+       struct lcr_msg          *message;
        struct capa_info        capainfo;
        struct caller_info      callerinfo;
        struct redir_info       redirinfo;
        struct dialing_info     dialinginfo;
-       char remote[32];
+       char                    exten[128] = "";
+       char                    remote[32];
 
        if (!(rparam = routeparam(e_action, PARAM_APPLICATION)))
        {
@@ -146,16 +95,23 @@ void EndpointAppPBX::action_init_remote(void)
        memcpy(&redirinfo, &e_redirinfo, sizeof(redirinfo));
        memset(&dialinginfo, 0, sizeof(dialinginfo));
 
+       if ((rparam = routeparam(e_action, PARAM_EXTEN)))
+       {
+               SCPY(exten, rparam->string_value);
+       }
        /* send setup to remote */
        trace_header("ACTION remote (setup)", DIRECTION_NONE);
        add_trace("number", NULL, dialinginfo.id);
        add_trace("remote", NULL, remote);
+       if (exten[0])
+               add_trace("exten", NULL, remote);
        end_trace();
        message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_join_id, EPOINT_TO_JOIN, MESSAGE_SETUP);
        memcpy(&message->param.setup.dialinginfo, &dialinginfo, sizeof(struct dialing_info));
        memcpy(&message->param.setup.redirinfo, &redirinfo, sizeof(struct redir_info));
        memcpy(&message->param.setup.callerinfo, &callerinfo, sizeof(struct caller_info));
        memcpy(&message->param.setup.capainfo, &capainfo, sizeof(struct capa_info));
+       SCPY(message->param.setup.exten, exten);
        message_put(message);
 }
 
@@ -169,7 +125,7 @@ void EndpointAppPBX::action_dialing_internal(void)
        struct redir_info       redirinfo;
        struct dialing_info     dialinginfo;
        struct port_list        *portlist = ea_endpoint->ep_portlist;
-       struct message          *message;
+       struct lcr_msg          *message;
        struct extension        ext;
        struct route_param      *rparam;
 
@@ -277,7 +233,7 @@ void EndpointAppPBX::action_dialing_external(void)
        struct dialing_info dialinginfo;
        char *p;
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        struct route_param *rparam;
 
        /* special processing of delete characters '*' and '#' */
@@ -438,7 +394,7 @@ void EndpointAppPBX::action_dialing_external(void)
 
 void EndpointAppPBX::action_dialing_remote(void)
 {
-       struct message *message;
+       struct lcr_msg *message;
        struct dialing_info dialinginfo;
 //     struct route_param *rparam;
 
@@ -465,7 +421,7 @@ void EndpointAppPBX::action_dialing_vbox_record(void)
 {
        struct dialing_info dialinginfo;
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        struct extension ext;
        struct route_param *rparam;
 
@@ -546,7 +502,7 @@ void EndpointAppPBX::action_init_partyline(void)
        class Join *join;
        class JoinPBX *joinpbx;
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        struct route_param *rparam;
        int partyline, jingle = 0;
        struct join_relation *relation;
@@ -647,7 +603,7 @@ void EndpointAppPBX::action_hangup_call(void)
 void EndpointAppPBX::action_dialing_login(void)
 {
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        char *extension;
        struct route_param *rparam;
 
@@ -839,7 +795,7 @@ void EndpointAppPBX::_action_callerid_calleridnext(int next)
                                (!next)?e_ext.callerid_type:e_ext.id_next_call_type = INFO_NTYPE_UNKNOWN;
                        } else
                        {
-                               SCPY((!next)?e_ext.callerid:e_ext.id_next_call, nationalize_callerinfo(callerid,&((!next)?e_ext.callerid_type:e_ext.id_next_call_type)));
+                               SCPY((!next)?e_ext.callerid:e_ext.id_next_call, nationalize_callerinfo(callerid,&((!next)?e_ext.callerid_type:e_ext.id_next_call_type), options.national, options.international));
                        }
                        if (!next) e_ext.id_next_call_type = -1;
                        PDEBUG(DEBUG_EPOINT, "EPOINT(%d): nationalized callerid: '%s' type=%d\n", ea_endpoint->ep_serial, (!next)?e_ext.callerid:e_ext.id_next_call, (!next)?e_ext.callerid_type:e_ext.id_next_call_type);
@@ -855,9 +811,9 @@ void EndpointAppPBX::_action_callerid_calleridnext(int next)
                trace_header("ACTION change-callerid (only next call)", DIRECTION_NONE);
        else
                trace_header("ACTION change-callerid (all future calls)", DIRECTION_NONE);
-       add_trace("old", "caller id", "%s", numberrize_callerinfo(old_id, old_type));
+       add_trace("old", "caller id", "%s", numberrize_callerinfo(old_id, old_type, options.national, options.international));
        add_trace("old", "present", "%s", (old_present==INFO_PRESENT_RESTRICTED)?"restricted":"allowed");
-       add_trace("new", "caller id", "%s", numberrize_callerinfo(new_id, new_type));
+       add_trace("new", "caller id", "%s", numberrize_callerinfo(new_id, new_type, options.national, options.international));
        add_trace("new", "present", "%s", (new_present==INFO_PRESENT_RESTRICTED)?"restricted":"allowed");
        end_trace();
        message_disconnect_port(portlist, CAUSE_NORMAL, LOCATION_PRIVATE_LOCAL, "");
@@ -991,7 +947,7 @@ void EndpointAppPBX::action_init_redial_reply(void)
 */
 void EndpointAppPBX::_action_redial_reply(int in)
 {
-       struct message *message;
+       struct lcr_msg *message;
        char *last;
        struct route_param *rparam;
 
@@ -1090,7 +1046,7 @@ void EndpointAppPBX::action_dialing_reply(void)
 void EndpointAppPBX::action_dialing_powerdial(void)
 {
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        struct route_param *rparam;
 
        /* power dialing only possible if we have a last dialed number */
@@ -1321,7 +1277,7 @@ void EndpointAppPBX::action_dialing_test(void)
        unsigned int cause;
        char causestr[16];
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        class Port *port;
        char testcode[32] = "";
        struct route_param *rparam;
@@ -1533,7 +1489,7 @@ void EndpointAppPBX::action_init_play(void)
 void EndpointAppPBX::action_dialing_calculator(void)
 {
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        double value1, value2, v, sign1;
        int komma1, komma2, k, state, mode, first;
        char *p;
@@ -1837,13 +1793,18 @@ void EndpointAppPBX::_action_goto_menu(int mode)
        trace_header("ACTION goto/menu (change to)", DIRECTION_NONE);
        add_trace("ruleset", NULL, "%s", e_ruleset->name);
        if (e_dialinginfo.id[0])
+       {
                add_trace("dialing", NULL, "%s", e_dialinginfo.id);
+       }
        if ((rparam = routeparam(e_action, PARAM_SAMPLE)))
        {
                add_trace("sample", NULL, "%s", rparam->string_value);
+               end_trace();
                set_tone(ea_endpoint->ep_portlist, rparam->string_value);
+       } else
+       {
+               end_trace();
        }
-       end_trace();
 
        /* do dialing with new ruleset */
        e_action = NULL;
@@ -1872,7 +1833,7 @@ void EndpointAppPBX::action_dialing_disconnect(void)
 {
        struct route_param *rparam;
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        int cause = CAUSE_NORMAL; /* normal call clearing */
        int location = LOCATION_PRIVATE_LOCAL;
        char cause_string[256] = "", display[84] = "";
@@ -1942,7 +1903,7 @@ void EndpointAppPBX::action_dialing_help(void)
        struct numbering *numbering = numbering_int;
        char dialing[sizeof(e_dialinginfo.id)];
        int i;
-       struct message *message;
+       struct lcr_msg *message;
        struct route_param *rparam;
 
        /* in case we have no menu (this should never happen) */
@@ -2035,8 +1996,9 @@ void EndpointAppPBX::action_dialing_setforward(void)
 void EndpointAppPBX::action_hangup_execute(void)
 {
        struct route_param *rparam;
+       pid_t pid;
        char *command = "", isdn_port[10];
-       char *argv[7+1]; /* check also number of args below */
+       char *argv[11]; /* check also number of args below */
        int i = 0;
 
        /* get script / command */
@@ -2048,26 +2010,35 @@ void EndpointAppPBX::action_hangup_execute(void)
                end_trace();
                return;
        }
-       trace_header("ACTION execute", DIRECTION_NONE);
-       add_trace("command", NULL, "%s", command);
-       end_trace();
-
-       argv[0] = command;
-       while(strchr(argv[0], '/'))
-               argv[0] = strchr(argv[0], '/')+1;
+       argv[i++] = "/bin/sh";
+       argv[i++] = "-c";
+       argv[i++] = command;
+       argv[i++] = command;
        if ((rparam = routeparam(e_action, PARAM_PARAM)))
        {
-               argv[1] = rparam->string_value;
-               i++;
+               argv[i++] = rparam->string_value;
        }
-       argv[1+i] = e_extdialing;
-       argv[2+i] = numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype);
-       argv[3+i] = e_callerinfo.extension;
-       argv[4+i] = e_callerinfo.name;
+       argv[i++] = e_extdialing;
+       argv[i++] = numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype, options.national, options.international);
+       argv[i++] = e_callerinfo.extension;
+       argv[i++] = e_callerinfo.name;
        SPRINT(isdn_port, "%d", e_callerinfo.isdn_port);
-       argv[5+i] = isdn_port;
-       argv[6+i] = NULL; /* check also number of args above */
-       execve("/bin/sh", argv, environ);
+       argv[i++] = isdn_port;
+       argv[i++] = NULL; /* check also number of args above */
+       switch (pid = fork ()) {
+               case -1:
+                       trace_header("ACTION execute (fork failed)", DIRECTION_NONE);
+                       end_trace();
+                       break;
+               case 0:
+                       execve("/bin/sh", argv, environ);
+                       break;
+               default:
+                       trace_header("ACTION execute", DIRECTION_NONE);
+                       add_trace("command", NULL, "%s", command);
+                       end_trace();
+                       break;
+       }
 }
 
 
@@ -2207,7 +2178,7 @@ void EndpointAppPBX::action_dialing_password_wr(void)
 void EndpointAppPBX::process_dialing(void)
 {
        struct port_list *portlist = ea_endpoint->ep_portlist;
-       struct message *message;
+       struct lcr_msg *message;
        struct route_param *rparam;
 
 //#warning Due to HANG-BUG somewhere here, I added some HANG-BUG-DEBUGGING output that cannot be disabled. after bug has been found, this will be removed.
@@ -2276,7 +2247,7 @@ void EndpointAppPBX::process_dialing(void)
        if (e_state!=EPOINT_STATE_IN_SETUP
         && e_state!=EPOINT_STATE_IN_OVERLAP)
        {
-               PDEBUG(DEBUG_EPOINT, "EPOINT(%d): we are not in incomming setup/overlap state, so we ignore init/dialing process.\n", ea_endpoint->ep_serial, e_rule_nesting);
+               PDEBUG(DEBUG_EPOINT, "EPOINT(%d): we are not in incoming setup/overlap state, so we ignore init/dialing process.\n", ea_endpoint->ep_serial, e_rule_nesting);
                e_match_timeout = 0;
                goto end;
        }
@@ -2444,7 +2415,7 @@ void EndpointAppPBX::process_dialing(void)
                if (e_state!=EPOINT_STATE_IN_SETUP
                 && e_state!=EPOINT_STATE_IN_OVERLAP)
                {
-                       PDEBUG(DEBUG_EPOINT, "EPOINT(%d): AFTER init process: we are not in incomming setup/overlap state anymore, so we ignore further dialing process.\n", ea_endpoint->ep_serial, e_rule_nesting);
+                       PDEBUG(DEBUG_EPOINT, "EPOINT(%d): AFTER init process: we are not in incoming setup/overlap state anymore, so we ignore further dialing process.\n", ea_endpoint->ep_serial, e_rule_nesting);
                        goto display_action;
                }
        }
@@ -2533,7 +2504,7 @@ void EndpointAppPBX::process_hangup(int cause, int location)
                }
 
                if (e_callerinfo.id[0])
-                       SPRINT(callertext, "%s", numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype));
+                       SPRINT(callertext, "%s", numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype, options.national, options.international));
                else
                        SPRINT(callertext, "unknown");
                /* allpy restriction */
@@ -2544,14 +2515,14 @@ void EndpointAppPBX::process_hangup(int cause, int location)
                write_log(e_ext.number, callertext, dialingtext, e_start, e_stop, 0, cause, location);
 
                /* store last received call for reply-list */
-               if (e_origin == 1) // outgoing to phone is incomming for user
+               if (e_origin == 1) // outgoing to phone is incoming for user
                if (e_callerinfo.id[0] || e_callerinfo.extension[0])
                if (e_ext.anon_ignore || e_callerinfo.present!=INFO_PRESENT_RESTRICTED)
                {
                        if (e_callerinfo.extension[0])
                                SPRINT(callertext, "intern:%s", e_callerinfo.extension);
                        else
-                               SPRINT(callertext, "extern:%s", numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype));
+                               SPRINT(callertext, "extern:%s", numberrize_callerinfo(e_callerinfo.id, e_callerinfo.ntype, options.national, options.international));
                        if (!!strcmp(callertext, e_ext.last_in[0]))
                        {
                                i = MAX_REMEMBER-1;
@@ -2568,7 +2539,7 @@ void EndpointAppPBX::process_hangup(int cause, int location)
                }
 
                /* store last made call for reply-list */
-               if (e_origin == 0) // incomming from phone is outgoing for user
+               if (e_origin == 0) // incoming from phone is outgoing for user
                if (e_dialinginfo.id[0])
                {
                        if (!!strcmp(e_dialinginfo.id, e_ext.last_out[0]))