1 /*****************************************************************************\
5 **---------------------------------------------------------------------------**
6 ** Copyright: Andreas Eversberg **
10 \*****************************************************************************/
15 #include <sys/types.h>
16 //#include <sys/stat.h>
21 #include <sys/ioctl.h>
22 //#include <sys/file.h>
24 //#include <sys/mman.h>
25 //#include <sys/resource.h>
26 #include <sys/socket.h>
32 char *socket_name = SOCKET_NAME;
34 struct sockaddr_un sock_address;
36 struct admin_list *admin_list = NULL;
39 * initialize admin socket
45 /* open and bind socket */
46 if ((sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
48 PERROR("Failed to create admin socket. (errno=%d)\n", errno);
52 memset(&sock_address, 0, sizeof(sock_address));
53 sock_address.sun_family = AF_UNIX;
54 UCPY(sock_address.sun_path, socket_name);
56 if (bind(sock, (struct sockaddr *)(&sock_address), SUN_LEN(&sock_address)) < 0)
62 PERROR("Failed to bind admin socket to \"%s\". (errno=%d)\n", sock_address.sun_path, errno);
65 if (listen(sock, 5) < 0)
71 PERROR("Failed to listen to socket \"%s\". (errno=%d)\n", sock_address.sun_path, errno);
74 if (ioctl(sock, FIONBIO, (unsigned char *)(&on)) < 0)
80 PERROR("Failed to set socket \"%s\" into non-blocking mode. (errno=%d)\n", sock_address.sun_path, errno);
90 void free_connection(struct admin_list *admin)
92 struct admin_queue *response;
100 // printf("new\n", response);
101 response = admin->response;
105 // printf("%x\n", response);
106 temp = response->next;
109 response = (struct admin_queue *)temp;
111 // printf("new2\n", response);
113 // printf("new3\n", response);
119 * cleanup admin socket
121 void admin_cleanup(void)
123 struct admin_list *admin, *next;;
130 free_connection(admin);
143 * do interface reload
145 int admin_interface(struct admin_queue **responsep)
147 struct admin_queue *response; /* response pointer */
151 if (read_interfaces())
154 free_interfaces(interface_first);
155 interface_first = interface_newlist;
156 interface_newlist = NULL;
159 err_txt = interface_error;
162 /* create state response */
163 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
167 memset(response, 0, sizeof(admin_queue));
170 response->am[0].message = ADMIN_RESPONSE_CMD_INTERFACE;
172 response->am[0].u.x.error = err;
174 SCPY(response->am[0].u.x.message, err_txt);
175 /* attach to response chain */
176 *responsep = response;
177 responsep = &response->next;
186 int admin_route(struct admin_queue **responsep)
188 struct route_ruleset *ruleset_new;
189 struct admin_queue *response; /* response pointer */
190 char err_txt[256] = "";
195 class EndpointAppPBX *apppbx;
199 apppbx = apppbx_first;
203 apppbx = apppbx->next;
207 SPRINT(err_txt, "Cannot reload routing, because %d endpoints active\n", n);
212 if (!(ruleset_new = ruleset_parse()))
214 SPRINT(err_txt, ruleset_error);
218 ruleset_free(ruleset_first);
219 ruleset_first = ruleset_new;
220 ruleset_main = getrulesetbyname("main");
223 SPRINT(err_txt, "Ruleset reloaded, but rule 'main' not found.\n");
226 apppbx = apppbx_first;
229 if (apppbx->e_action)
231 switch(apppbx->e_action->index)
233 case ACTION_INTERNAL:
234 apppbx->e_action = &action_internal;
236 case ACTION_EXTERNAL:
237 apppbx->e_action = &action_external;
240 apppbx->e_action = &action_chan;
242 case ACTION_VBOX_RECORD:
243 apppbx->e_action = &action_vbox;
245 case ACTION_PARTYLINE:
246 apppbx->e_action = &action_partyline;
251 } else if (apppbx->e_state != EPOINT_STATE_CONNECT)
254 apppbx->e_callback = 0;
255 apppbx->e_action = NULL;
256 apppbx->release(RELEASE_ALL, LOCATION_PRIVATE_LOCAL, CAUSE_NORMAL, LOCATION_PRIVATE_LOCAL, CAUSE_NORMAL);
257 printlog("%3d endpoint ADMIN Kicking due to reload of routing.\n", apppbx->ea_endpoint->ep_serial);
260 apppbx->e_action_timeout = NULL;
261 apppbx->e_rule = NULL;
262 apppbx->e_ruleset = NULL;
264 apppbx = apppbx->next;
268 /* create state response */
269 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
273 memset(response, 0, sizeof(admin_queue));
276 response->am[0].message = ADMIN_RESPONSE_CMD_ROUTE;
278 response->am[0].u.x.error = err;
280 SCPY(response->am[0].u.x.message, err_txt);
281 /* attach to response chain */
282 *responsep = response;
283 responsep = &response->next;
292 int admin_dial(struct admin_queue **responsep, char *message)
294 struct extension ext; /* temporary extension's settings */
295 struct admin_queue *response; /* response pointer */
296 char *p; /* pointer to dialing digits */
298 /* create state response */
299 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
303 memset(response, 0, sizeof(admin_queue));
306 response->am[0].message = ADMIN_RESPONSE_CMD_DIAL;
308 /* process request */
309 if (!(p = strchr(message,':')))
311 response->am[0].u.x.error = -EINVAL;
312 SPRINT(response->am[0].u.x.message, "no seperator ':' in message to seperate number from extension");
317 /* modify extension */
318 if (!read_extension(&ext, message))
320 response->am[0].u.x.error = -EINVAL;
321 SPRINT(response->am[0].u.x.message, "extension doesn't exist");
325 write_extension(&ext, message);
328 /* attach to response chain */
329 *responsep = response;
330 responsep = &response->next;
338 int admin_release(struct admin_queue **responsep, char *message)
341 struct admin_queue *response; /* response pointer */
342 class EndpointAppPBX *apppbx;
344 /* create state response */
345 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
349 memset(response, 0, sizeof(admin_queue));
352 response->am[0].message = ADMIN_RESPONSE_CMD_RELEASE;
355 apppbx = apppbx_first;
358 if (apppbx->ea_endpoint->ep_serial == id)
360 apppbx = apppbx->next;
364 response->am[0].u.x.error = -EINVAL;
365 SPRINT(response->am[0].u.x.message, "Given endpoint %d doesn't exist.", id);
369 apppbx->e_callback = 0;
370 apppbx->release(RELEASE_ALL, LOCATION_PRIVATE_LOCAL, CAUSE_NORMAL, LOCATION_PRIVATE_LOCAL, CAUSE_NORMAL);
373 /* attach to response chain */
374 *responsep = response;
375 responsep = &response->next;
383 int admin_call(struct admin_list *admin, struct admin_message *msg)
385 class Endpoint *epoint;
386 class EndpointAppPBX *apppbx;
388 if (!(epoint = new Endpoint(0,0)))
391 if (!(epoint->ep_app = apppbx = new DEFAULT_ENDPOINT_APP(epoint)))
393 PERROR("no memory for application\n");
396 apppbx->e_adminid = admin->sockserial;
397 admin->epointid = epoint->ep_serial;
398 SCPY(apppbx->e_callerinfo.id, nationalize_callerinfo(msg->u.call.callerid, &apppbx->e_callerinfo.ntype));
399 if (msg->u.call.present)
400 apppbx->e_callerinfo.present = INFO_PRESENT_ALLOWED;
402 apppbx->e_callerinfo.present = INFO_PRESENT_RESTRICTED;
403 apppbx->e_callerinfo.screen = INFO_SCREEN_NETWORK;
405 //printf("hh=%d\n", apppbx->e_capainfo.hlc);
407 apppbx->e_capainfo.bearer_capa = msg->u.call.bc_capa;
408 apppbx->e_capainfo.bearer_mode = msg->u.call.bc_mode;
409 apppbx->e_capainfo.bearer_info1 = msg->u.call.bc_info1;
410 apppbx->e_capainfo.hlc = msg->u.call.hlc;
411 apppbx->e_capainfo.exthlc = msg->u.call.exthlc;
412 SCPY(apppbx->e_dialinginfo.number, msg->u.call.dialing);
413 SCPY(apppbx->e_dialinginfo.interfaces, msg->u.call.interface);
414 apppbx->e_dialinginfo.sending_complete = 1;
416 apppbx->new_state(PORT_STATE_OUT_SETUP);
423 * this function is called for response whenever a call state changes.
425 void admin_call_response(int adminid, int message, char *connected, int cause, int location, int notify)
427 struct admin_list *admin;
428 struct admin_queue *response, **responsep; /* response pointer */
430 /* searching for admin id
431 * maybe there is no admin instance, because the calling port was not
432 * initiated by admin_call */
436 if (adminid == admin->sockserial)
443 /* seek to end of response list */
444 response = admin->response;
445 responsep = &admin->response;
448 responsep = &response->next;
449 response = response->next;
452 /* create state response */
453 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
457 memset(response, 0, sizeof(admin_queue));
460 response->am[0].message = message;
461 // printf("MESSAGE: %d\n", message);
463 SCPY(response->am[0].u.call.callerid, connected);
464 response->am[0].u.call.cause = cause;
465 response->am[0].u.call.location = location;
466 response->am[0].u.call.notify = notify;
468 /* attach to response chain */
469 *responsep = response;
470 responsep = &response->next;
477 int admin_state(struct admin_queue **responsep)
481 class EndpointAppPBX *apppbx;
484 struct mISDNport *mISDNport;
488 struct admin_queue *response;
490 /* create state response */
491 response = (struct admin_queue *)malloc(sizeof(struct admin_queue)+sizeof(admin_message));
495 memset(response, 0, sizeof(admin_queue));
498 response->am[0].message = ADMIN_RESPONSE_STATE;
500 SCPY(response->am[0].u.s.version_string, VERSION_STRING);
502 memcpy(&response->am[0].u.s.tm, now_tm, sizeof(struct tm));
504 SCPY(response->am[0].u.s.logfile, options.log);
505 /* interface count */
506 mISDNport = mISDNport_first;
511 mISDNport = mISDNport->next;
513 response->am[0].u.s.interfaces = i;
522 response->am[0].u.s.calls = i;
524 apppbx = apppbx_first;
529 apppbx = apppbx->next;
531 response->am[0].u.s.epoints = i;
540 response->am[0].u.s.ports = i;
541 /* attach to response chain */
542 *responsep = response;
543 responsep = &response->next;
545 /* create response for all interfaces */
546 num = (response->am[0].u.s.interfaces)+(response->am[0].u.s.calls)+(response->am[0].u.s.epoints)+(response->am[0].u.s.ports);
547 response = (struct admin_queue *)malloc(sizeof(admin_queue)+(num*sizeof(admin_message)));
551 memset(response, 0, sizeof(admin_queue)+(num*sizeof(admin_queue)));
553 *responsep = response;
554 responsep = &response->next;
555 mISDNport = mISDNport_first;
560 response->am[num].message = ADMIN_RESPONSE_S_INTERFACE;
562 response->am[num].u.i.portnum = mISDNport->portnum;
564 SCPY(response->am[num].u.i.interface_name, mISDNport->interface_name);
566 response->am[num].u.i.iftype = mISDNport->iftype;
568 response->am[num].u.i.ptp = mISDNport->ptp;
570 response->am[num].u.i.ntmode = mISDNport->ntmode;
572 response->am[num].u.i.pri = mISDNport->pri;
574 response->am[num].u.i.use = mISDNport->use;
576 response->am[num].u.i.l1link = mISDNport->l1link;
578 response->am[num].u.i.l2link = mISDNport->l2link;
580 response->am[num].u.i.channels = mISDNport->b_num;
584 while(i < mISDNport->b_num)
586 response->am[num].u.i.busy[i] = mISDNport->b_state[i];
587 if (mISDNport->b_port[i])
588 response->am[num].u.i.port[i] = mISDNport->b_port[i]->p_serial;
591 mISDNport = mISDNport->next;
595 /* create response for all calls */
600 response->am[num].message = ADMIN_RESPONSE_S_CALL;
602 response->am[num].u.c.serial = call->c_serial;
604 if (call->c_type == CALL_TYPE_PBX)
605 response->am[num].u.c.partyline = ((class CallPBX *)call)->c_partyline;
611 /* create response for all endpoint */
612 apppbx = apppbx_first;
616 response->am[num].message = ADMIN_RESPONSE_S_EPOINT;
618 response->am[num].u.e.serial = apppbx->ea_endpoint->ep_serial;
620 response->am[num].u.e.call = apppbx->ea_endpoint->ep_call_id;
621 /* rx notification */
622 response->am[num].u.e.rx_state = apppbx->e_rx_state;
623 /* tx notification */
624 response->am[num].u.e.tx_state = apppbx->e_tx_state;
626 switch(apppbx->e_state)
628 case EPOINT_STATE_IN_SETUP:
629 response->am[num].u.e.state = ADMIN_STATE_IN_SETUP;
631 case EPOINT_STATE_OUT_SETUP:
632 response->am[num].u.e.state = ADMIN_STATE_OUT_SETUP;
634 case EPOINT_STATE_IN_OVERLAP:
635 response->am[num].u.e.state = ADMIN_STATE_IN_OVERLAP;
637 case EPOINT_STATE_OUT_OVERLAP:
638 response->am[num].u.e.state = ADMIN_STATE_OUT_OVERLAP;
640 case EPOINT_STATE_IN_PROCEEDING:
641 response->am[num].u.e.state = ADMIN_STATE_IN_PROCEEDING;
643 case EPOINT_STATE_OUT_PROCEEDING:
644 response->am[num].u.e.state = ADMIN_STATE_OUT_PROCEEDING;
646 case EPOINT_STATE_IN_ALERTING:
647 response->am[num].u.e.state = ADMIN_STATE_IN_ALERTING;
649 case EPOINT_STATE_OUT_ALERTING:
650 response->am[num].u.e.state = ADMIN_STATE_OUT_ALERTING;
652 case EPOINT_STATE_CONNECT:
653 response->am[num].u.e.state = ADMIN_STATE_CONNECT;
655 case EPOINT_STATE_IN_DISCONNECT:
656 response->am[num].u.e.state = ADMIN_STATE_IN_DISCONNECT;
658 case EPOINT_STATE_OUT_DISCONNECT:
659 response->am[num].u.e.state = ADMIN_STATE_OUT_DISCONNECT;
662 response->am[num].u.e.state = ADMIN_STATE_IDLE;
665 SCPY(response->am[num].u.e.terminal, apppbx->e_ext.number);
667 SCPY(response->am[num].u.e.callerid, apppbx->e_callerinfo.id);
669 SCPY(response->am[num].u.e.dialing, apppbx->e_dialinginfo.number);
671 if (apppbx->e_action)
672 SCPY(response->am[num].u.e.action, action_defs[apppbx->e_action->index].name);
673 // if (apppbx->e_action)
674 // printf("action=%s\n",action_defs[apppbx->e_action->index].name);
676 response->am[num].u.e.park = apppbx->ea_endpoint->ep_park;
677 if (apppbx->ea_endpoint->ep_park && apppbx->ea_endpoint->ep_park_len && apppbx->ea_endpoint->ep_park_len<=(int)sizeof(response->am[num].u.e.park_callid))
678 memcpy(response->am[num].u.e.park_callid, apppbx->ea_endpoint->ep_park_callid, apppbx->ea_endpoint->ep_park_len);
679 response->am[num].u.e.park_len = apppbx->ea_endpoint->ep_park_len;
681 if (apppbx->e_crypt == CRYPT_ON)
682 response->am[num].u.e.crypt = 1;
684 apppbx = apppbx->next;
688 /* create response for all ports */
693 response->am[num].message = ADMIN_RESPONSE_S_PORT;
695 response->am[num].u.p.serial = port->p_serial;
697 SCPY(response->am[num].u.p.name, port->p_name);
699 response->am[num].u.p.epoint = ACTIVE_EPOINT(port->p_epointlist);
701 switch(port->p_state)
703 case PORT_STATE_IN_SETUP:
704 response->am[num].u.p.state = ADMIN_STATE_IN_SETUP;
706 case PORT_STATE_OUT_SETUP:
707 response->am[num].u.p.state = ADMIN_STATE_OUT_SETUP;
709 case PORT_STATE_IN_OVERLAP:
710 response->am[num].u.p.state = ADMIN_STATE_IN_OVERLAP;
712 case PORT_STATE_OUT_OVERLAP:
713 response->am[num].u.p.state = ADMIN_STATE_OUT_OVERLAP;
715 case PORT_STATE_IN_PROCEEDING:
716 response->am[num].u.p.state = ADMIN_STATE_IN_PROCEEDING;
718 case PORT_STATE_OUT_PROCEEDING:
719 response->am[num].u.p.state = ADMIN_STATE_OUT_PROCEEDING;
721 case PORT_STATE_IN_ALERTING:
722 response->am[num].u.p.state = ADMIN_STATE_IN_ALERTING;
724 case PORT_STATE_OUT_ALERTING:
725 response->am[num].u.p.state = ADMIN_STATE_OUT_ALERTING;
727 case PORT_STATE_CONNECT:
728 response->am[num].u.p.state = ADMIN_STATE_CONNECT;
730 case PORT_STATE_IN_DISCONNECT:
731 response->am[num].u.p.state = ADMIN_STATE_IN_DISCONNECT;
733 case PORT_STATE_OUT_DISCONNECT:
734 response->am[num].u.p.state = ADMIN_STATE_OUT_DISCONNECT;
737 response->am[num].u.p.state = ADMIN_STATE_IDLE;
740 if ((port->p_type&PORT_CLASS_mISDN_MASK) == PORT_CLASS_mISDN_DSS1)
742 response->am[num].u.p.isdn = 1;
743 pdss1 = (class Pdss1 *)port;
744 response->am[num].u.p.isdn_chan = pdss1->p_m_b_channel;
745 response->am[num].u.p.isdn_hold = pdss1->p_m_hold;
746 response->am[num].u.p.isdn_ces = pdss1->p_m_d_ces;
755 int sockserial = 1; // must start with 1, because 0 is used if no serial is set
757 * handle admin socket (non blocking)
759 int admin_handle(void)
761 struct admin_list *admin, **adminp;
763 struct admin_message msg;
766 socklen_t sock_len = sizeof(sock_address);
767 unsigned long on = 1;
768 int work = 0; /* if work was done */
769 struct Endpoint *epoint;
774 /* check for new incomming connections */
775 if ((new_sock = accept(sock, (struct sockaddr *)&sock_address, &sock_len)) >= 0)
778 /* insert new socket */
779 admin = (struct admin_list *)malloc(sizeof(struct admin_list));
782 if (ioctl(new_sock, FIONBIO, (unsigned char *)(&on)) >= 0)
785 // PERROR("DEBUG incomming socket %d, serial=%d\n", new_sock, sockserial);
788 memset(admin, 0, sizeof(struct admin_list));
789 admin->sockserial = sockserial++;
790 admin->next = admin_list;
792 admin->sock = new_sock;
801 if (errno != EWOULDBLOCK)
803 PERROR("Failed to accept connection from socket \"%s\". (errno=%d) Closing socket.\n", sock_address.sun_path, errno);
809 /* loop all current socket connections */
811 adminp = &admin_list;
815 len = read(admin->sock, &msg, sizeof(msg));
818 if (errno != EWOULDBLOCK)
822 printf("Broken pipe on socket %d. (errno=%d).\n", admin->sock, errno);
823 PDEBUG(DEBUG_LOG, "Broken pipe on socket %d. (errno=%d).\n", admin->sock, errno);
824 *adminp = admin->next;
825 free_connection(admin);
833 //PERROR("DEBUG socket %d got data. serial=%d\n", admin->sock, admin->sockserial);
838 /*release endpoint if exists */
841 epoint = find_epoint_id(admin->epointid);
844 ((class DEFAULT_ENDPOINT_APP *)epoint->ep_app)->
845 release(RELEASE_ALL, CAUSE_NORMAL, LOCATION_PRIVATE_LOCAL, 0, 0);
850 //PERROR("DEBUG socket %d closed by remote.\n", admin->sock);
851 *adminp = admin->next;
852 free_connection(admin);
854 //PERROR("DEBUG (admin_list=%x)\n", admin_list);
857 if (len != sizeof(msg))
859 PERROR("Short/long read on socket %d. (len=%d != size=%d).\n", admin->sock, len, sizeof(msg));
860 *adminp = admin->next;
861 free_connection(admin);
865 /* process socket command */
868 PERROR("Data from socket %d while sending response.\n", admin->sock);
869 *adminp = admin->next;
870 free_connection(admin);
876 case ADMIN_REQUEST_CMD_INTERFACE:
877 if (admin_interface(&admin->response) < 0)
879 PERROR("Failed to create dial response for socket %d.\n", admin->sock);
884 case ADMIN_REQUEST_CMD_ROUTE:
885 if (admin_route(&admin->response) < 0)
887 PERROR("Failed to create dial response for socket %d.\n", admin->sock);
892 case ADMIN_REQUEST_CMD_DIAL:
893 if (admin_dial(&admin->response, msg.u.x.message) < 0)
895 PERROR("Failed to create dial response for socket %d.\n", admin->sock);
900 case ADMIN_REQUEST_CMD_RELEASE:
901 if (admin_release(&admin->response, msg.u.x.message) < 0)
903 PERROR("Failed to create release response for socket %d.\n", admin->sock);
908 case ADMIN_REQUEST_STATE:
909 if (admin_state(&admin->response) < 0)
911 PERROR("Failed to create state response for socket %d.\n", admin->sock);
914 case ADMIN_REQUEST_MESSAGE:
915 if (admin_message(&admin->response) < 0)
917 PERROR("Failed to create message response for socket %d.\n", admin->sock);
919 *adminp = admin->next;
920 free_connection(admin);
927 struct admin_queue *response;
929 response = admin->response;
932 printf("%c", '0'+response->am[0].message);
933 response=response->next;
940 case ADMIN_CALL_SETUP:
941 if (admin_call(admin, &msg))
943 PERROR("Failed to create call for socket %d.\n", admin->sock);
949 PERROR("Invalid message %d from socket %d.\n", msg.message, admin->sock);
950 *adminp = admin->next;
951 free_connection(admin);
960 //PERROR("DEBUG socket %d sending data.\n", admin->sock);
961 len = write(admin->sock, ((unsigned char *)(admin->response->am))+admin->response->offset, sizeof(struct admin_message)*(admin->response->num)-admin->response->offset);
964 if (errno != EWOULDBLOCK)
974 if (len < (int)(sizeof(struct admin_message)*(admin->response->num)-admin->response->offset))
976 admin->response->offset+=len;
980 temp = admin->response;
981 admin->response = admin->response->next;
986 /* done with socket instance */
988 adminp = &admin->next;