#include "asterisk.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <sys/ioctl.h>
#include <net/if.h>
#include <errno.h>
#include <fcntl.h>
#include <netdb.h>
#include <arpa/inet.h>
#include <sys/signal.h>
#include <signal.h>
#include <ctype.h>
#include "asterisk/lock.h"
#include "asterisk/channel.h"
#include "asterisk/config.h"
#include "asterisk/logger.h"
#include "asterisk/module.h"
#include "asterisk/pbx.h"
#include "asterisk/options.h"
#include "asterisk/sched.h"
#include "asterisk/io.h"
#include "asterisk/rtp.h"
#include "asterisk/acl.h"
#include "asterisk/callerid.h"
#include "asterisk/cli.h"
#include "asterisk/say.h"
#include "asterisk/cdr.h"
#include "asterisk/astdb.h"
#include "asterisk/features.h"
#include "asterisk/app.h"
#include "asterisk/musiconhold.h"
#include "asterisk/utils.h"
#include "asterisk/dsp.h"
#include "asterisk/stringfields.h"
#include "asterisk/astobj.h"
#include "asterisk/abstract_jb.h"
#include "asterisk/threadstorage.h"
Go to the source code of this file.
Data Structures | |
struct | activate_call_plane_message |
struct | alarm_message |
struct | button_definition |
struct | button_definition_template |
struct | button_template_res_message |
struct | call_info_message |
struct | call_state_message |
struct | capabilities_res_message |
struct | clear_prompt_message |
struct | close_receive_channel_message |
struct | definetimedate_message |
struct | dialed_number_message |
struct | display_notify_message |
struct | display_prompt_status_message |
struct | displaytext_message |
struct | enbloc_call_message |
struct | keypad_button_message |
struct | line_stat_res_message |
struct | line_state_req_message |
struct | media_qualifier |
struct | offhook_message |
struct | onhook_message |
struct | open_receive_channel_ack_message |
struct | open_receive_channel_message |
struct | register_ack_message |
struct | register_message |
struct | register_rej_message |
struct | reset_message |
struct | select_soft_keys_message |
struct | server_identifier |
struct | server_res_message |
struct | set_lamp_message |
struct | set_microphone_message |
struct | set_ringer_message |
struct | set_speaker_message |
struct | skinny_addon |
union | skinny_data |
struct | skinny_device |
struct | skinny_line |
struct | skinny_paging_device |
struct | skinny_req |
struct | skinny_speeddial |
struct | skinny_subchannel |
struct | skinnysession |
struct | soft_key_definitions |
struct | soft_key_event_message |
struct | soft_key_set_definition |
struct | soft_key_set_res_message |
struct | soft_key_template_definition |
struct | soft_key_template_res_message |
struct | speed_dial_stat_req_message |
struct | speed_dial_stat_res_message |
struct | start_media_transmission_message |
struct | start_tone_message |
struct | station_capabilities |
struct | stimulus_message |
struct | stop_media_transmission_message |
struct | stop_tone_message |
struct | version_res_message |
Defines | |
#define | ACTIVATE_CALL_PLANE_MESSAGE 0x0116 |
#define | ALARM_MESSAGE 0x0020 |
#define | BT_AUTOANSWER STIMULUS_AUTOANSWER |
#define | BT_CALLPARK STIMULUS_CALLPARK |
#define | BT_CALLPICKUP STIMULUS_CALLPICKUP |
#define | BT_CONFERENCE STIMULUS_CONFERENCE |
#define | BT_CUST_HINT 0xB1 |
#define | BT_CUST_LINESPEEDDIAL 0xB0 |
#define | BT_DISPLAY STIMULUS_DISPLAY |
#define | BT_FORWARDALL STIMULUS_FORWARDALL |
#define | BT_FORWARDBUSY STIMULUS_FORWARDBUSY |
#define | BT_FORWARDNOANSWER STIMULUS_FORWARDNOANSWER |
#define | BT_HOLD STIMULUS_HOLD |
#define | BT_LINE STIMULUS_LINE |
#define | BT_NONE 0x00 |
#define | BT_REDIAL STIMULUS_REDIAL |
#define | BT_SPEEDDIAL STIMULUS_SPEEDDIAL |
#define | BT_TRANSFER STIMULUS_TRANSFER |
#define | BT_VOICEMAIL STIMULUS_VOICEMAIL |
#define | BUTTON_TEMPLATE_REQ_MESSAGE 0x000E |
#define | BUTTON_TEMPLATE_RES_MESSAGE 0x0097 |
#define | CALL_INFO_MESSAGE 0x008F |
#define | CALL_STATE_MESSAGE 0x0111 |
#define | CAPABILITIES_REQ_MESSAGE 0x009B |
#define | CAPABILITIES_RES_MESSAGE 0x0010 |
#define | CLEAR_DISPLAY_MESSAGE 0x009A |
#define | CLEAR_NOTIFY_MESSAGE 0x0115 |
#define | CLEAR_PROMPT_MESSAGE 0x0113 |
#define | CLOSE_RECEIVE_CHANNEL_MESSAGE 0x0106 |
#define | CONTROL2STR_BUFSIZE 100 |
#define | DEFAULT_AUTH_LIMIT 50 |
#define | DEFAULT_AUTH_TIMEOUT 30 |
#define | DEFAULT_SKINNY_BACKLOG 2 |
#define | DEFAULT_SKINNY_PORT 2000 |
#define | DEFINETIMEDATE_MESSAGE 0x0094 |
#define | DEVICE2STR_BUFSIZE 15 |
#define | DIALED_NUMBER_MESSAGE 0x011D |
#define | DISPLAY_NOTIFY_MESSAGE 0x0114 |
#define | DISPLAY_PROMPT_STATUS_MESSAGE 0x0112 |
#define | DISPLAYTEXT_MESSAGE 0x0099 |
#define | ENBLOC_CALL_MESSAGE 0x0004 |
#define | HEADSET_STATUS_MESSAGE 0x002B |
#define | htolel(x) (x) |
#define | htoles(x) (x) |
#define | IP_PORT_MESSAGE 0x0002 |
#define | KEEP_ALIVE_ACK_MESSAGE 0x0100 |
#define | KEEP_ALIVE_MESSAGE 0x0000 |
#define | KEYDEF_CONNECTED 1 |
#define | KEYDEF_CONNWITHCONF 7 |
#define | KEYDEF_CONNWITHTRANS 5 |
#define | KEYDEF_DADFD 6 |
#define | KEYDEF_OFFHOOK 4 |
#define | KEYDEF_OFFHOOKWITHFEAT 9 |
#define | KEYDEF_ONHOLD 2 |
#define | KEYDEF_ONHOOK 0 |
#define | KEYDEF_RINGIN 3 |
#define | KEYDEF_RINGOUT 8 |
#define | KEYDEF_UNKNOWN 10 |
#define | KEYPAD_BUTTON_MESSAGE 0x0003 |
#define | letohl(x) (x) |
#define | letohs(x) (x) |
#define | LINE_STAT_RES_MESSAGE 0x0092 |
#define | LINE_STATE_REQ_MESSAGE 0x000B |
#define | OFFHOOK_MESSAGE 0x0006 |
#define | ONHOOK_MESSAGE 0x0007 |
#define | OPEN_RECEIVE_CHANNEL_ACK_MESSAGE 0x0022 |
#define | OPEN_RECEIVE_CHANNEL_MESSAGE 0x0105 |
#define | REGISTER_ACK_MESSAGE 0x0081 |
#define | REGISTER_AVAILABLE_LINES_MESSAGE 0x002D |
#define | REGISTER_MESSAGE 0x0001 |
#define | REGISTER_REJ_MESSAGE 0x009D |
#define | RESET_MESSAGE 0x009F |
#define | SELECT_SOFT_KEYS_MESSAGE 0x0110 |
#define | SERVER_REQUEST_MESSAGE 0x0012 |
#define | SERVER_RES_MESSAGE 0x009E |
#define | SET_LAMP_MESSAGE 0x0086 |
#define | SET_MICROPHONE_MESSAGE 0x0089 |
#define | SET_RINGER_MESSAGE 0x0085 |
#define | SET_SPEAKER_MESSAGE 0x0088 |
#define | SKINNY_ALERT 0x24 |
#define | SKINNY_BUSY 6 |
#define | SKINNY_BUSYTONE 0x23 |
#define | SKINNY_CALLWAIT 9 |
#define | SKINNY_CALLWAITTONE 0x2D |
#define | SKINNY_CONGESTION 7 |
#define | SKINNY_CONNECTED 5 |
#define | SKINNY_CX_CONF 3 |
#define | SKINNY_CX_CONFERENCE 3 |
#define | SKINNY_CX_INACTIVE 4 |
#define | SKINNY_CX_MUTE 4 |
#define | SKINNY_CX_RECVONLY 1 |
#define | SKINNY_CX_SENDONLY 0 |
#define | SKINNY_CX_SENDRECV 2 |
#define | SKINNY_DEVICE_12 4 |
#define | SKINNY_DEVICE_12SP 3 |
#define | SKINNY_DEVICE_12SPPLUS 2 |
#define | SKINNY_DEVICE_30SPPLUS 1 |
#define | SKINNY_DEVICE_30VIP 5 |
#define | SKINNY_DEVICE_7902 30008 |
#define | SKINNY_DEVICE_7905 20000 |
#define | SKINNY_DEVICE_7906 369 |
#define | SKINNY_DEVICE_7910 6 |
#define | SKINNY_DEVICE_7911 307 |
#define | SKINNY_DEVICE_7912 30007 |
#define | SKINNY_DEVICE_7914 124 |
#define | SKINNY_DEVICE_7920 30002 |
#define | SKINNY_DEVICE_7921 365 |
#define | SKINNY_DEVICE_7931 348 |
#define | SKINNY_DEVICE_7935 9 |
#define | SKINNY_DEVICE_7936 30019 |
#define | SKINNY_DEVICE_7937 431 |
#define | SKINNY_DEVICE_7940 8 |
#define | SKINNY_DEVICE_7941 115 |
#define | SKINNY_DEVICE_7941GE 309 |
#define | SKINNY_DEVICE_7942 434 |
#define | SKINNY_DEVICE_7945 435 |
#define | SKINNY_DEVICE_7960 7 |
#define | SKINNY_DEVICE_7961 30018 |
#define | SKINNY_DEVICE_7961GE 308 |
#define | SKINNY_DEVICE_7962 404 |
#define | SKINNY_DEVICE_7965 436 |
#define | SKINNY_DEVICE_7970 30006 |
#define | SKINNY_DEVICE_7971 119 |
#define | SKINNY_DEVICE_7975 437 |
#define | SKINNY_DEVICE_7985 302 |
#define | SKINNY_DEVICE_ATA186 12 |
#define | SKINNY_DEVICE_CIPC 30016 |
#define | SKINNY_DEVICE_NONE 0 |
#define | SKINNY_DEVICE_SCCPGATEWAY_AN 30027 |
#define | SKINNY_DEVICE_SCCPGATEWAY_BRI 30028 |
#define | SKINNY_DEVICE_UNKNOWN -1 |
#define | SKINNY_DIALTONE 0x21 |
#define | SKINNY_HOLD 8 |
#define | SKINNY_INVALID 14 |
#define | SKINNY_LAMP_BLINK 5 |
#define | SKINNY_LAMP_FLASH 4 |
#define | SKINNY_LAMP_OFF 1 |
#define | SKINNY_LAMP_ON 2 |
#define | SKINNY_LAMP_WINK 3 |
#define | SKINNY_MAX_CAPABILITIES 18 |
#define | SKINNY_MAX_PACKET 1000 |
#define | SKINNY_MICOFF 2 |
#define | SKINNY_MICON 1 |
#define | SKINNY_NOTONE 0x7F |
#define | SKINNY_OFFHOOK 1 |
#define | SKINNY_ONHOOK 2 |
#define | SKINNY_PARK 11 |
#define | SKINNY_PROGRESS 12 |
#define | SKINNY_REORDER 0x25 |
#define | SKINNY_RING_FEATURE 4 |
#define | SKINNY_RING_INSIDE 2 |
#define | SKINNY_RING_OFF 1 |
#define | SKINNY_RING_OUTSIDE 3 |
#define | SKINNY_RINGIN 4 |
#define | SKINNY_RINGOUT 3 |
#define | SKINNY_SILENCE 0x00 |
#define | SKINNY_SPEAKEROFF 2 |
#define | SKINNY_SPEAKERON 1 |
#define | SKINNY_TRANSFER 10 |
#define | SOFT_KEY_EVENT_MESSAGE 0x0026 |
#define | SOFT_KEY_SET_REQ_MESSAGE 0x0025 |
#define | SOFT_KEY_SET_RES_MESSAGE 0x0109 |
#define | SOFT_KEY_TEMPLATE_REQ_MESSAGE 0x0028 |
#define | SOFT_KEY_TEMPLATE_RES_MESSAGE 0x0108 |
#define | SOFTKEY_ANSWER 0x0B |
#define | SOFTKEY_BKSPC 0x08 |
#define | SOFTKEY_CFWDALL 0x05 |
#define | SOFTKEY_CFWDBUSY 0x06 |
#define | SOFTKEY_CFWDNOANSWER 0x07 |
#define | SOFTKEY_CONFRN 0x0D |
#define | SOFTKEY_ENDCALL 0x09 |
#define | SOFTKEY_GPICKUP 0x12 |
#define | SOFTKEY_HOLD 0x03 |
#define | SOFTKEY_INFO 0x0C |
#define | SOFTKEY_JOIN 0x0F |
#define | SOFTKEY_MEETME 0x10 |
#define | SOFTKEY_NEWCALL 0x02 |
#define | SOFTKEY_NONE 0x00 |
#define | SOFTKEY_PARK 0x0E |
#define | SOFTKEY_PICKUP 0x11 |
#define | SOFTKEY_REDIAL 0x01 |
#define | SOFTKEY_RESUME 0x0A |
#define | SOFTKEY_TRNSFER 0x04 |
#define | SPEED_DIAL_STAT_REQ_MESSAGE 0x000A |
#define | SPEED_DIAL_STAT_RES_MESSAGE 0x0091 |
#define | START_MEDIA_TRANSMISSION_MESSAGE 0x008A |
#define | START_TONE_MESSAGE 0x0082 |
#define | STIMULUS_AUTOANSWER 0x11 |
#define | STIMULUS_CALLPARK 0x7E |
#define | STIMULUS_CALLPICKUP 0x7F |
#define | STIMULUS_CONFERENCE 0x7D |
#define | STIMULUS_DISPLAY 0x08 |
#define | STIMULUS_FORWARDALL 0x05 |
#define | STIMULUS_FORWARDBUSY 0x06 |
#define | STIMULUS_FORWARDNOANSWER 0x07 |
#define | STIMULUS_HOLD 0x03 |
#define | STIMULUS_LINE 0x09 |
#define | STIMULUS_MESSAGE 0x0005 |
#define | STIMULUS_NONE 0xFF |
#define | STIMULUS_REDIAL 0x01 |
#define | STIMULUS_SPEEDDIAL 0x02 |
#define | STIMULUS_TRANSFER 0x04 |
#define | STIMULUS_VOICEMAIL 0x0F |
#define | STOP_MEDIA_TRANSMISSION_MESSAGE 0x008B |
#define | STOP_TONE_MESSAGE 0x0083 |
#define | TIME_DATE_REQ_MESSAGE 0x000D |
#define | TYPE_LINE 2 |
#define | TYPE_TRUNK 1 |
#define | UNREGISTER_MESSAGE 0x0027 |
#define | VERSION_REQ_MESSAGE 0x000F |
#define | VERSION_RES_MESSAGE 0x0098 |
Enumerations | |
enum | skinny_codecs { SKINNY_CODEC_ALAW = 2, SKINNY_CODEC_ULAW = 4, SKINNY_CODEC_G723_1 = 9, SKINNY_CODEC_G729A = 12, SKINNY_CODEC_G726_32 = 82, SKINNY_CODEC_H261 = 100, SKINNY_CODEC_H263 = 101 } |
Functions | |
static void | __reg_module (void) |
static void | __unreg_module (void) |
static void * | accept_thread (void *ignore) |
static struct skinny_device * | build_device (const char *cat, struct ast_variable *v) |
static int | codec_ast2skinny (int astcodec) |
static int | codec_skinny2ast (enum skinny_codecs skinnycodec) |
static char * | complete_skinny_reset (const char *line, const char *word, int pos, int state) |
static char * | control2str (int ind) |
static void | control2str_threadbuf_init (void) |
static void | delete_devices (void) |
static void | destroy_session (struct skinnysession *s) |
static char * | device2str (int type) |
static void | device2str_threadbuf_init (void) |
static void | do_housekeeping (struct skinnysession *s) |
static void * | do_monitor (void *data) |
static struct skinny_line * | find_line_by_instance (struct skinny_device *d, int instance) |
static struct skinny_line * | find_line_by_name (const char *dest) |
static struct skinny_speeddial * | find_speeddial_by_instance (struct skinny_device *d, int instance) |
static struct skinny_subchannel * | find_subchannel_by_instance_reference (struct skinny_device *d, int instance, int reference) |
static struct skinny_subchannel * | find_subchannel_by_reference (struct skinny_device *d, int reference) |
static void * | get_button_template (struct skinnysession *s, struct button_definition_template *btn) |
static int | get_input (struct skinnysession *s) |
static int | handle_alarm_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_button_template_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_capabilities_res_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_enbloc_call_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_headset_status_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_ip_port_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_keep_alive_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_keypad_button_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_line_state_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_offhook_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_onhook_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_open_receive_channel_ack_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_register_available_lines_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_register_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_server_request_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_soft_key_event_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_soft_key_set_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_soft_key_template_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_speed_dial_stat_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_stimulus_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_time_date_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_unregister_message (struct skinny_req *req, struct skinnysession *s) |
static int | handle_version_req_message (struct skinny_req *req, struct skinnysession *s) |
static int | load_module (void) |
static int | reload_config (void) |
static struct skinny_req * | req_alloc (size_t size, int response_message) |
static int | restart_monitor (void) |
static int | skinny_answer (struct ast_channel *ast) |
static int | skinny_call (struct ast_channel *ast, char *dest, int timeout) |
static int | skinny_do_debug (int fd, int argc, char *argv[]) |
static int | skinny_fixup (struct ast_channel *oldchan, struct ast_channel *newchan) |
static enum ast_rtp_get_result | skinny_get_rtp_peer (struct ast_channel *c, struct ast_rtp **rtp) |
static enum ast_rtp_get_result | skinny_get_vrtp_peer (struct ast_channel *c, struct ast_rtp **rtp) |
static int | skinny_hangup (struct ast_channel *ast) |
static int | skinny_hold (struct skinny_subchannel *sub) |
static int | skinny_indicate (struct ast_channel *ast, int ind, const void *data, size_t datalen) |
static struct ast_channel * | skinny_new (struct skinny_line *l, int state) |
static void * | skinny_newcall (void *data) |
static int | skinny_no_debug (int fd, int argc, char *argv[]) |
static struct ast_frame * | skinny_read (struct ast_channel *ast) |
static int | skinny_register (struct skinny_req *req, struct skinnysession *s) |
static struct skinny_req * | skinny_req_parse (struct skinnysession *s) |
static struct ast_channel * | skinny_request (const char *type, int format, void *data, int *cause) |
static int | skinny_reset_device (int fd, int argc, char *argv[]) |
static struct ast_frame * | skinny_rtp_read (struct skinny_subchannel *sub) |
static int | skinny_senddigit_begin (struct ast_channel *ast, char digit) |
static int | skinny_senddigit_end (struct ast_channel *ast, char digit, unsigned int duration) |
static void * | skinny_session (void *data) |
static int | skinny_set_rtp_peer (struct ast_channel *c, struct ast_rtp *rtp, struct ast_rtp *vrtp, int codecs, int nat_active) |
static int | skinny_show_devices (int fd, int argc, char *argv[]) |
static int | skinny_show_lines (int fd, int argc, char *argv[]) |
static void * | skinny_ss (void *data) |
static int | skinny_unhold (struct skinny_subchannel *sub) |
static int | skinny_unregister (struct skinny_req *req, struct skinnysession *s) |
static int | skinny_write (struct ast_channel *ast, struct ast_frame *frame) |
static void | start_rtp (struct skinny_subchannel *sub) |
static void | transmit_callinfo (struct skinnysession *s, const char *fromname, const char *fromnum, const char *toname, const char *tonum, int instance, int callid, int calltype) |
static void | transmit_callstate (struct skinnysession *s, int instance, int state, unsigned callid) |
static void | transmit_connect (struct skinnysession *s, struct skinny_subchannel *sub) |
static void | transmit_dialednumber (struct skinnysession *s, const char *text, int instance, int callid) |
static void | transmit_displaymessage (struct skinnysession *s, const char *text, int instance, int reference) |
static void | transmit_displaynotify (struct skinnysession *s, const char *text, int t) |
static void | transmit_displaypromptstatus (struct skinnysession *s, const char *text, int t, int instance, int callid) |
static void | transmit_lamp_indication (struct skinnysession *s, int stimulus, int instance, int indication) |
static int | transmit_response (struct skinnysession *s, struct skinny_req *req) |
static void | transmit_ringer_mode (struct skinnysession *s, int mode) |
static void | transmit_selectsoftkeys (struct skinnysession *s, int instance, int callid, int softkey) |
static void | transmit_speaker_mode (struct skinnysession *s, int mode) |
static void | transmit_tone (struct skinnysession *s, int tone, int instance, int reference) |
static int | unload_module (void) |
Variables | |
static struct ast_module_info | __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "Skinny Client Control Protocol (Skinny)" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "361d7bb937402d51e4658efb5b4d76e4" , .load = load_module, .unload = unload_module, } |
static struct in_addr | __ourip |
static pthread_t | accept_t |
static char | accountcode [AST_MAX_ACCOUNT_CODE] = "" |
ast_hostent | ahp |
static int | amaflags = 0 |
static const struct ast_module_info * | ast_module_info = &__mod_info |
static int | auth_limit = DEFAULT_AUTH_LIMIT |
static int | auth_timeout = DEFAULT_AUTH_TIMEOUT |
static struct sockaddr_in | bindaddr |
static int | callnums = 1 |
static int | callreturn = 0 |
static int | callwaiting = 0 |
static int | cancallforward = 0 |
static char | cid_name [AST_MAX_EXTENSION] = "" |
static char | cid_num [AST_MAX_EXTENSION] = "" |
static struct ast_cli_entry | cli_skinny [] |
static const char | config [] = "skinny.conf" |
static char | context [AST_MAX_CONTEXT] = "default" |
static struct ast_threadstorage | control2str_threadbuf = { .once = PTHREAD_ONCE_INIT , .key_init = control2str_threadbuf_init , } |
static ast_group_t | cur_callergroup = 0 |
static ast_group_t | cur_pickupgroup = 0 |
static char | date_format [6] = "D-M-Y" |
static char | debug_usage [] |
static int | default_capability = AST_FORMAT_ULAW | AST_FORMAT_ALAW |
static struct ast_jb_conf | default_jbconf |
static struct ast_codec_pref | default_prefs |
static struct ast_threadstorage | device2str_threadbuf = { .once = PTHREAD_ONCE_INIT , .key_init = device2str_threadbuf_init , } |
static ast_mutex_t | devicelock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) |
static struct skinny_device * | devices |
static int | firstdigittimeout = 16000 |
static int | gendigittimeout = 8000 |
static struct ast_jb_conf | global_jbconf |
hostent * | hp |
static int | immediate = 0 |
static struct io_context * | io |
static int | keep_alive = 120 |
static char | language [MAX_LANGUAGE] = "" |
static char | linelabel [AST_MAX_EXTENSION] = "" |
static char | mailbox [AST_MAX_EXTENSION] |
static int | matchdigittimeout = 3000 |
static char | mohinterpret [MAX_MUSICCLASS] = "default" |
static char | mohsuggest [MAX_MUSICCLASS] = "" |
static pthread_t | monitor_thread = AST_PTHREADT_NULL |
static ast_mutex_t | monlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) |
static int | mwiblink = 0 |
static int | nat = 0 |
static ast_mutex_t | netlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) |
static char | no_debug_usage [] |
static char | ourhost [256] |
static int | ourport |
static char | reset_usage [] |
static struct sched_context * | sched = NULL |
static ast_mutex_t | sessionlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) |
static struct skinnysession * | sessions |
static char | show_devices_usage [] |
static char | show_lines_usage [] |
int | skinny_header_size = 12 |
static struct ast_rtp_protocol | skinny_rtp |
static struct ast_channel_tech | skinny_tech |
static int | skinnydebug = 0 |
static int | skinnysock = -1 |
static const uint8_t | soft_key_default_connected [] |
static const uint8_t | soft_key_default_connwithconf [] |
static const uint8_t | soft_key_default_connwithtrans [] |
static const uint8_t | soft_key_default_dadfd [] |
static struct soft_key_definitions | soft_key_default_definitions [] |
static const uint8_t | soft_key_default_offhook [] |
static const uint8_t | soft_key_default_offhookwithfeat [] |
static const uint8_t | soft_key_default_onhold [] |
static const uint8_t | soft_key_default_onhook [] |
static const uint8_t | soft_key_default_ringin [] |
static const uint8_t | soft_key_default_ringout [] |
static const uint8_t | soft_key_default_unknown [] |
soft_key_template_definition | soft_key_template_default [] |
static const char | tdesc [] = "Skinny Client Control Protocol (Skinny)" |
static int | threewaycalling = 0 |
static int | transfer = 0 |
static int | unauth_sessions = 0 |
static char | version_id [16] = "P002F202" |
Definition in file chan_skinny.c.
#define ACTIVATE_CALL_PLANE_MESSAGE 0x0116 |
Definition at line 710 of file chan_skinny.c.
Referenced by skinny_hold(), skinny_unhold(), and transmit_callstate().
#define ALARM_MESSAGE 0x0020 |
#define BT_AUTOANSWER STIMULUS_AUTOANSWER |
Definition at line 426 of file chan_skinny.c.
#define BT_CALLPARK STIMULUS_CALLPARK |
#define BT_CALLPICKUP STIMULUS_CALLPICKUP |
Definition at line 429 of file chan_skinny.c.
#define BT_CONFERENCE STIMULUS_CONFERENCE |
#define BT_CUST_HINT 0xB1 |
#define BT_CUST_LINESPEEDDIAL 0xB0 |
Definition at line 435 of file chan_skinny.c.
Referenced by get_button_template(), and handle_button_template_req_message().
#define BT_DISPLAY STIMULUS_DISPLAY |
#define BT_FORWARDALL STIMULUS_FORWARDALL |
#define BT_FORWARDBUSY STIMULUS_FORWARDBUSY |
Definition at line 421 of file chan_skinny.c.
#define BT_FORWARDNOANSWER STIMULUS_FORWARDNOANSWER |
Definition at line 422 of file chan_skinny.c.
#define BT_HOLD STIMULUS_HOLD |
#define BT_LINE STIMULUS_LINE |
Definition at line 424 of file chan_skinny.c.
Referenced by get_button_template(), and handle_button_template_req_message().
#define BT_NONE 0x00 |
Definition at line 430 of file chan_skinny.c.
Referenced by get_button_template(), and handle_button_template_req_message().
#define BT_REDIAL STIMULUS_REDIAL |
#define BT_SPEEDDIAL STIMULUS_SPEEDDIAL |
Definition at line 417 of file chan_skinny.c.
Referenced by get_button_template(), and handle_button_template_req_message().
#define BT_TRANSFER STIMULUS_TRANSFER |
#define BT_VOICEMAIL STIMULUS_VOICEMAIL |
#define BUTTON_TEMPLATE_REQ_MESSAGE 0x000E |
#define BUTTON_TEMPLATE_RES_MESSAGE 0x0097 |
#define CALL_INFO_MESSAGE 0x008F |
#define CALL_STATE_MESSAGE 0x0111 |
#define CAPABILITIES_REQ_MESSAGE 0x009B |
#define CAPABILITIES_RES_MESSAGE 0x0010 |
#define CLEAR_DISPLAY_MESSAGE 0x009A |
#define CLEAR_NOTIFY_MESSAGE 0x0115 |
Definition at line 455 of file chan_skinny.c.
#define CLEAR_PROMPT_MESSAGE 0x0113 |
#define CLOSE_RECEIVE_CHANNEL_MESSAGE 0x0106 |
Definition at line 494 of file chan_skinny.c.
Referenced by skinny_hold(), and transmit_callstate().
#define CONTROL2STR_BUFSIZE 100 |
#define DEFAULT_AUTH_LIMIT 50 |
#define DEFAULT_AUTH_TIMEOUT 30 |
#define DEFAULT_SKINNY_BACKLOG 2 |
#define DEFAULT_SKINNY_PORT 2000 |
#define DEFINETIMEDATE_MESSAGE 0x0094 |
#define DEVICE2STR_BUFSIZE 15 |
#define DIALED_NUMBER_MESSAGE 0x011D |
#define DISPLAY_NOTIFY_MESSAGE 0x0114 |
#define DISPLAY_PROMPT_STATUS_MESSAGE 0x0112 |
#define DISPLAYTEXT_MESSAGE 0x0099 |
#define ENBLOC_CALL_MESSAGE 0x0004 |
#define HEADSET_STATUS_MESSAGE 0x002B |
#define htolel | ( | x | ) | (x) |
Definition at line 112 of file chan_skinny.c.
Referenced by get_input(), handle_button_template_req_message(), handle_open_receive_channel_ack_message(), handle_register_message(), handle_server_request_message(), handle_soft_key_set_req_message(), handle_soft_key_template_req_message(), handle_speed_dial_stat_req_message(), handle_time_date_req_message(), load_module(), req_alloc(), skinny_hold(), skinny_unhold(), transmit_callinfo(), transmit_callstate(), transmit_connect(), transmit_dialednumber(), transmit_displaynotify(), transmit_displaypromptstatus(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), transmit_speaker_mode(), and transmit_tone().
#define htoles | ( | x | ) | (x) |
Definition at line 113 of file chan_skinny.c.
#define IP_PORT_MESSAGE 0x0002 |
#define KEEP_ALIVE_ACK_MESSAGE 0x0100 |
#define KEEP_ALIVE_MESSAGE 0x0000 |
#define KEYDEF_CONNECTED 1 |
Definition at line 509 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_answer().
#define KEYDEF_CONNWITHCONF 7 |
Definition at line 515 of file chan_skinny.c.
#define KEYDEF_CONNWITHTRANS 5 |
Definition at line 513 of file chan_skinny.c.
#define KEYDEF_DADFD 6 |
Definition at line 514 of file chan_skinny.c.
#define KEYDEF_OFFHOOK 4 |
Definition at line 512 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), and handle_stimulus_message().
#define KEYDEF_OFFHOOKWITHFEAT 9 |
Definition at line 517 of file chan_skinny.c.
#define KEYDEF_ONHOLD 2 |
Definition at line 510 of file chan_skinny.c.
#define KEYDEF_ONHOOK 0 |
Definition at line 508 of file chan_skinny.c.
Referenced by handle_soft_key_set_req_message(), and transmit_callstate().
#define KEYDEF_RINGIN 3 |
#define KEYDEF_RINGOUT 8 |
Definition at line 516 of file chan_skinny.c.
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
#define KEYDEF_UNKNOWN 10 |
Definition at line 518 of file chan_skinny.c.
#define KEYPAD_BUTTON_MESSAGE 0x0003 |
#define letohl | ( | x | ) | (x) |
Definition at line 110 of file chan_skinny.c.
Referenced by get_input(), handle_capabilities_res_message(), handle_keypad_button_message(), handle_line_state_req_message(), handle_message(), handle_offhook_message(), handle_onhook_message(), handle_open_receive_channel_ack_message(), handle_soft_key_event_message(), handle_speed_dial_stat_req_message(), handle_stimulus_message(), skinny_register(), skinny_req_parse(), and transmit_response().
#define letohs | ( | x | ) | (x) |
Definition at line 111 of file chan_skinny.c.
#define LINE_STAT_RES_MESSAGE 0x0092 |
#define LINE_STATE_REQ_MESSAGE 0x000B |
#define OFFHOOK_MESSAGE 0x0006 |
#define ONHOOK_MESSAGE 0x0007 |
#define OPEN_RECEIVE_CHANNEL_ACK_MESSAGE 0x0022 |
#define OPEN_RECEIVE_CHANNEL_MESSAGE 0x0105 |
#define REGISTER_ACK_MESSAGE 0x0081 |
#define REGISTER_AVAILABLE_LINES_MESSAGE 0x002D |
#define REGISTER_MESSAGE 0x0001 |
#define REGISTER_REJ_MESSAGE 0x009D |
#define RESET_MESSAGE 0x009F |
#define SELECT_SOFT_KEYS_MESSAGE 0x0110 |
#define SERVER_REQUEST_MESSAGE 0x0012 |
#define SERVER_RES_MESSAGE 0x009E |
#define SET_LAMP_MESSAGE 0x0086 |
#define SET_MICROPHONE_MESSAGE 0x0089 |
Definition at line 306 of file chan_skinny.c.
#define SET_RINGER_MESSAGE 0x0085 |
#define SET_SPEAKER_MESSAGE 0x0088 |
#define SKINNY_ALERT 0x24 |
#define SKINNY_BUSY 6 |
#define SKINNY_BUSYTONE 0x23 |
#define SKINNY_CALLWAIT 9 |
Definition at line 872 of file chan_skinny.c.
#define SKINNY_CALLWAITTONE 0x2D |
#define SKINNY_CONGESTION 7 |
#define SKINNY_CONNECTED 5 |
Definition at line 868 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_answer().
#define SKINNY_CX_CONF 3 |
Definition at line 904 of file chan_skinny.c.
#define SKINNY_CX_CONFERENCE 3 |
Definition at line 905 of file chan_skinny.c.
#define SKINNY_CX_INACTIVE 4 |
#define SKINNY_CX_MUTE 4 |
Definition at line 906 of file chan_skinny.c.
#define SKINNY_CX_RECVONLY 1 |
Definition at line 902 of file chan_skinny.c.
Referenced by handle_onhook_message(), and handle_soft_key_event_message().
#define SKINNY_CX_SENDONLY 0 |
Definition at line 901 of file chan_skinny.c.
#define SKINNY_CX_SENDRECV 2 |
#define SKINNY_DEVICE_12 4 |
Definition at line 824 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_12SP 3 |
Definition at line 823 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_12SPPLUS 2 |
Definition at line 822 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_30SPPLUS 1 |
Definition at line 821 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_30VIP 5 |
Definition at line 825 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7902 30008 |
Definition at line 851 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7905 20000 |
Definition at line 847 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7906 369 |
Definition at line 840 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7910 6 |
Definition at line 826 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7911 307 |
Definition at line 835 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7912 30007 |
Definition at line 850 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7914 124 |
Definition at line 833 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7920 30002 |
Definition at line 848 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7921 365 |
Definition at line 839 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7931 348 |
Definition at line 838 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7935 9 |
Definition at line 829 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7936 30019 |
Definition at line 854 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7937 431 |
Definition at line 842 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7940 8 |
Definition at line 828 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7941 115 |
Definition at line 831 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7941GE 309 |
Definition at line 837 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7942 434 |
Definition at line 843 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7945 435 |
Definition at line 844 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7960 7 |
Definition at line 827 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7961 30018 |
Definition at line 853 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7961GE 308 |
Definition at line 836 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7962 404 |
Definition at line 841 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7965 436 |
Definition at line 845 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7970 30006 |
Definition at line 849 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7971 119 |
Definition at line 832 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7975 437 |
Definition at line 846 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_7985 302 |
Definition at line 834 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_ATA186 12 |
Definition at line 830 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_CIPC 30016 |
Definition at line 852 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_NONE 0 |
#define SKINNY_DEVICE_SCCPGATEWAY_AN 30027 |
Definition at line 855 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_SCCPGATEWAY_BRI 30028 |
Definition at line 856 of file chan_skinny.c.
Referenced by device2str(), and get_button_template().
#define SKINNY_DEVICE_UNKNOWN -1 |
#define SKINNY_DIALTONE 0x21 |
Definition at line 879 of file chan_skinny.c.
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_ss().
#define SKINNY_HOLD 8 |
Definition at line 871 of file chan_skinny.c.
#define SKINNY_INVALID 14 |
Definition at line 876 of file chan_skinny.c.
#define SKINNY_LAMP_BLINK 5 |
#define SKINNY_LAMP_FLASH 4 |
Definition at line 889 of file chan_skinny.c.
#define SKINNY_LAMP_OFF 1 |
Definition at line 886 of file chan_skinny.c.
Referenced by handle_soft_key_event_message(), handle_stimulus_message(), and skinny_hangup().
#define SKINNY_LAMP_ON 2 |
Definition at line 887 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_unhold().
#define SKINNY_LAMP_WINK 3 |
Definition at line 888 of file chan_skinny.c.
#define SKINNY_MAX_CAPABILITIES 18 |
#define SKINNY_MAX_PACKET 1000 |
Definition at line 98 of file chan_skinny.c.
Referenced by skinny_req_parse(), and transmit_response().
#define SKINNY_MICOFF 2 |
Definition at line 862 of file chan_skinny.c.
#define SKINNY_MICON 1 |
Definition at line 861 of file chan_skinny.c.
#define SKINNY_NOTONE 0x7F |
#define SKINNY_OFFHOOK 1 |
Definition at line 864 of file chan_skinny.c.
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_call(), skinny_hangup(), and transmit_callstate().
#define SKINNY_ONHOOK 2 |
Definition at line 865 of file chan_skinny.c.
Referenced by build_device(), handle_onhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_call(), skinny_hangup(), and transmit_callstate().
#define SKINNY_PARK 11 |
Definition at line 874 of file chan_skinny.c.
#define SKINNY_PROGRESS 12 |
#define SKINNY_REORDER 0x25 |
Definition at line 882 of file chan_skinny.c.
Referenced by skinny_indicate(), skinny_newcall(), and skinny_ss().
#define SKINNY_RING_FEATURE 4 |
Definition at line 895 of file chan_skinny.c.
#define SKINNY_RING_INSIDE 2 |
#define SKINNY_RING_OFF 1 |
Definition at line 892 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_hangup().
#define SKINNY_RING_OUTSIDE 3 |
Definition at line 894 of file chan_skinny.c.
#define SKINNY_RINGIN 4 |
#define SKINNY_RINGOUT 3 |
#define SKINNY_SILENCE 0x00 |
Definition at line 878 of file chan_skinny.c.
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_answer(), skinny_hangup(), skinny_indicate(), and skinny_ss().
#define SKINNY_SPEAKEROFF 2 |
Definition at line 859 of file chan_skinny.c.
Referenced by handle_stimulus_message(), skinny_hangup(), and transmit_callstate().
#define SKINNY_SPEAKERON 1 |
Definition at line 858 of file chan_skinny.c.
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
#define SKINNY_TRANSFER 10 |
Definition at line 873 of file chan_skinny.c.
#define SOFT_KEY_EVENT_MESSAGE 0x0026 |
#define SOFT_KEY_SET_REQ_MESSAGE 0x0025 |
#define SOFT_KEY_SET_RES_MESSAGE 0x0109 |
#define SOFT_KEY_TEMPLATE_REQ_MESSAGE 0x0028 |
#define SOFT_KEY_TEMPLATE_RES_MESSAGE 0x0108 |
#define SOFTKEY_ANSWER 0x0B |
#define SOFTKEY_BKSPC 0x08 |
#define SOFTKEY_CFWDALL 0x05 |
#define SOFTKEY_CFWDBUSY 0x06 |
#define SOFTKEY_CFWDNOANSWER 0x07 |
#define SOFTKEY_CONFRN 0x0D |
#define SOFTKEY_ENDCALL 0x09 |
#define SOFTKEY_GPICKUP 0x12 |
#define SOFTKEY_HOLD 0x03 |
#define SOFTKEY_INFO 0x0C |
#define SOFTKEY_JOIN 0x0F |
#define SOFTKEY_MEETME 0x10 |
#define SOFTKEY_NEWCALL 0x02 |
#define SOFTKEY_NONE 0x00 |
#define SOFTKEY_PARK 0x0E |
#define SOFTKEY_PICKUP 0x11 |
#define SOFTKEY_REDIAL 0x01 |
#define SOFTKEY_RESUME 0x0A |
#define SOFTKEY_TRNSFER 0x04 |
#define SPEED_DIAL_STAT_REQ_MESSAGE 0x000A |
#define SPEED_DIAL_STAT_RES_MESSAGE 0x0091 |
#define START_MEDIA_TRANSMISSION_MESSAGE 0x008A |
Definition at line 311 of file chan_skinny.c.
Referenced by handle_open_receive_channel_ack_message().
#define START_TONE_MESSAGE 0x0082 |
#define STIMULUS_AUTOANSWER 0x11 |
Definition at line 409 of file chan_skinny.c.
#define STIMULUS_CALLPARK 0x7E |
#define STIMULUS_CALLPICKUP 0x7F |
Definition at line 412 of file chan_skinny.c.
#define STIMULUS_CONFERENCE 0x7D |
#define STIMULUS_DISPLAY 0x08 |
#define STIMULUS_FORWARDALL 0x05 |
Definition at line 403 of file chan_skinny.c.
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
#define STIMULUS_FORWARDBUSY 0x06 |
#define STIMULUS_FORWARDNOANSWER 0x07 |
#define STIMULUS_HOLD 0x03 |
#define STIMULUS_LINE 0x09 |
Definition at line 407 of file chan_skinny.c.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_call(), skinny_hangup(), skinny_hold(), and skinny_unhold().
#define STIMULUS_MESSAGE 0x0005 |
#define STIMULUS_NONE 0xFF |
Definition at line 413 of file chan_skinny.c.
#define STIMULUS_REDIAL 0x01 |
#define STIMULUS_SPEEDDIAL 0x02 |
#define STIMULUS_TRANSFER 0x04 |
#define STIMULUS_VOICEMAIL 0x0F |
#define STOP_MEDIA_TRANSMISSION_MESSAGE 0x008B |
Definition at line 330 of file chan_skinny.c.
Referenced by skinny_hold(), and transmit_callstate().
#define STOP_TONE_MESSAGE 0x0083 |
#define TIME_DATE_REQ_MESSAGE 0x000D |
#define TYPE_LINE 2 |
Definition at line 898 of file chan_skinny.c.
#define TYPE_TRUNK 1 |
Definition at line 897 of file chan_skinny.c.
#define UNREGISTER_MESSAGE 0x0027 |
#define VERSION_REQ_MESSAGE 0x000F |
#define VERSION_RES_MESSAGE 0x0098 |
enum skinny_codecs |
SKINNY_CODEC_ALAW | |
SKINNY_CODEC_ULAW | |
SKINNY_CODEC_G723_1 | |
SKINNY_CODEC_G729A | |
SKINNY_CODEC_G726_32 | |
SKINNY_CODEC_H261 | |
SKINNY_CODEC_H263 |
Definition at line 86 of file chan_skinny.c.
00086 { 00087 SKINNY_CODEC_ALAW = 2, 00088 SKINNY_CODEC_ULAW = 4, 00089 SKINNY_CODEC_G723_1 = 9, 00090 SKINNY_CODEC_G729A = 12, 00091 SKINNY_CODEC_G726_32 = 82, /* XXX Which packing order does this translate to? */ 00092 SKINNY_CODEC_H261 = 100, 00093 SKINNY_CODEC_H263 = 101 00094 };
static void __reg_module | ( | void | ) | [static] |
Definition at line 5090 of file chan_skinny.c.
static void __unreg_module | ( | void | ) | [static] |
Definition at line 5090 of file chan_skinny.c.
static void* accept_thread | ( | void * | ignore | ) | [static] |
Definition at line 4608 of file chan_skinny.c.
References ast_atomic_fetchadd_int(), ast_calloc, ast_log(), ast_mutex_init(), ast_mutex_lock(), ast_mutex_unlock(), ast_pthread_create, ast_verbose(), auth_limit, destroy_session(), errno, LOG_ERROR, LOG_NOTICE, LOG_WARNING, s, sessionlock, skinny_session(), skinnydebug, skinnysock, and unauth_sessions.
04609 { 04610 int as; 04611 struct sockaddr_in sin; 04612 socklen_t sinlen; 04613 struct skinnysession *s; 04614 struct protoent *p; 04615 int arg = 1; 04616 pthread_attr_t attr; 04617 pthread_t tcp_thread; 04618 04619 pthread_attr_init(&attr); 04620 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 04621 04622 for (;;) { 04623 sinlen = sizeof(sin); 04624 as = accept(skinnysock, (struct sockaddr *)&sin, &sinlen); 04625 if (as < 0) { 04626 ast_log(LOG_NOTICE, "Accept returned -1: %s\n", strerror(errno)); 04627 continue; 04628 } 04629 04630 if (ast_atomic_fetchadd_int(&unauth_sessions, +1) >= auth_limit) { 04631 close(as); 04632 ast_atomic_fetchadd_int(&unauth_sessions, -1); 04633 continue; 04634 } 04635 04636 p = getprotobyname("tcp"); 04637 if(p) { 04638 if( setsockopt(as, p->p_proto, TCP_NODELAY, (char *)&arg, sizeof(arg) ) < 0 ) { 04639 ast_log(LOG_WARNING, "Failed to set Skinny tcp connection to TCP_NODELAY mode: %s\n", strerror(errno)); 04640 } 04641 } 04642 if (!(s = ast_calloc(1, sizeof(struct skinnysession)))) { 04643 close(as); 04644 ast_atomic_fetchadd_int(&unauth_sessions, -1); 04645 continue; 04646 } 04647 04648 memcpy(&s->sin, &sin, sizeof(sin)); 04649 ast_mutex_init(&s->lock); 04650 s->fd = as; 04651 04652 if(time(&s->start) == -1) { 04653 ast_log(LOG_ERROR, "error executing time(): %s; disconnecting client\n", strerror(errno)); 04654 destroy_session(s); 04655 continue; 04656 } 04657 04658 ast_mutex_lock(&sessionlock); 04659 s->next = sessions; 04660 sessions = s; 04661 ast_mutex_unlock(&sessionlock); 04662 04663 if (ast_pthread_create(&tcp_thread, &attr, skinny_session, s)) { 04664 destroy_session(s); 04665 } 04666 } 04667 if (skinnydebug) 04668 ast_verbose("killing accept thread\n"); 04669 close(as); 04670 pthread_attr_destroy(&attr); 04671 return 0; 04672 }
static struct skinny_device* build_device | ( | const char * | cat, | |
struct ast_variable * | v | |||
) | [static] |
Definition at line 2138 of file chan_skinny.c.
References __ourip, accountcode, skinny_device::addons, skinny_device::addr, amaflags, ast_append_ha(), ast_callerid_split(), ast_calloc, ast_cdr_amaflags2int(), ast_copy_string(), ast_get_group(), ast_get_ip(), ast_log(), ast_mutex_init(), ast_ouraddrfor(), ast_parse_allow_disallow(), ast_strlen_zero(), ast_true(), ast_verbose(), skinny_line::callgroup, skinny_line::callreturn, callreturn, skinny_line::callwaiting, callwaiting, skinny_line::cancallforward, cancallforward, skinny_line::capability, skinny_device::capability, skinny_line::cid_name, cid_name, skinny_line::cid_num, cid_num, skinny_line::context, context, cur_callergroup, cur_pickupgroup, default_capability, default_prefs, DEFAULT_SKINNY_PORT, skinny_device::earlyrtp, skinny_speeddial::exten, exten, free, skinny_device::ha, skinny_line::hookstate, skinny_device::id, skinny_line::immediate, immediate, skinny_line::instance, skinny_speeddial::instance, skinny_line::label, skinny_speeddial::label, skinny_line::language, language, skinny_device::lastlineinstance, linelabel, ast_variable::lineno, skinny_device::lines, skinny_line::lock, skinny_addon::lock, skinny_speeddial::lock, LOG_ERROR, LOG_WARNING, skinny_line::mailbox, mailbox, skinny_line::mohinterpret, mohinterpret, skinny_line::mohsuggest, mohsuggest, skinny_line::msgstate, skinny_line::mwiblink, mwiblink, skinny_line::name, ast_variable::name, skinny_device::name, skinny_line::nat, nat, ast_variable::next, skinny_line::next, skinny_addon::next, skinny_speeddial::next, skinny_line::onhooktime, option_verbose, skinny_device::ourip, skinny_line::parent, skinny_speeddial::parent, skinny_line::pickupgroup, skinny_line::prefs, skinny_device::prefs, SKINNY_ONHOOK, skinny_device::speeddials, skinny_line::threewaycalling, threewaycalling, skinny_line::transfer, transfer, skinny_line::type, skinny_addon::type, TYPE_LINE, TYPE_TRUNK, ast_variable::value, VERBOSE_PREFIX_3, and skinny_device::version_id.
Referenced by reload_config().
02139 { 02140 struct skinny_device *d; 02141 struct skinny_line *l; 02142 struct skinny_speeddial *sd; 02143 struct skinny_addon *a; 02144 int lineInstance = 1; 02145 int speeddialInstance = 1; 02146 int y = 0; 02147 02148 if (!(d = ast_calloc(1, sizeof(struct skinny_device)))) { 02149 return NULL; 02150 } else { 02151 ast_copy_string(d->name, cat, sizeof(d->name)); 02152 d->lastlineinstance = 1; 02153 d->capability = default_capability; 02154 d->prefs = default_prefs; 02155 d->earlyrtp = 1; 02156 while(v) { 02157 if (!strcasecmp(v->name, "host")) { 02158 if (ast_get_ip(&d->addr, v->value)) { 02159 free(d); 02160 return NULL; 02161 } 02162 } else if (!strcasecmp(v->name, "port")) { 02163 d->addr.sin_port = htons(atoi(v->value)); 02164 } else if (!strcasecmp(v->name, "device")) { 02165 ast_copy_string(d->id, v->value, sizeof(d->id)); 02166 } else if (!strcasecmp(v->name, "permit") || !strcasecmp(v->name, "deny")) { 02167 d->ha = ast_append_ha(v->name, v->value, d->ha); 02168 } else if (!strcasecmp(v->name, "context")) { 02169 ast_copy_string(context, v->value, sizeof(context)); 02170 } else if (!strcasecmp(v->name, "allow")) { 02171 ast_parse_allow_disallow(&d->prefs, &d->capability, v->value, 1); 02172 } else if (!strcasecmp(v->name, "disallow")) { 02173 ast_parse_allow_disallow(&d->prefs, &d->capability, v->value, 0); 02174 } else if (!strcasecmp(v->name, "version")) { 02175 ast_copy_string(d->version_id, v->value, sizeof(d->version_id)); 02176 } else if (!strcasecmp(v->name, "earlyrtp")) { 02177 d->earlyrtp = ast_true(v->value); 02178 } else if (!strcasecmp(v->name, "nat")) { 02179 nat = ast_true(v->value); 02180 } else if (!strcasecmp(v->name, "callerid")) { 02181 if (!strcasecmp(v->value, "asreceived")) { 02182 cid_num[0] = '\0'; 02183 cid_name[0] = '\0'; 02184 } else { 02185 ast_callerid_split(v->value, cid_name, sizeof(cid_name), cid_num, sizeof(cid_num)); 02186 } 02187 } else if (!strcasecmp(v->name, "language")) { 02188 ast_copy_string(language, v->value, sizeof(language)); 02189 } else if (!strcasecmp(v->name, "accountcode")) { 02190 ast_copy_string(accountcode, v->value, sizeof(accountcode)); 02191 } else if (!strcasecmp(v->name, "amaflags")) { 02192 y = ast_cdr_amaflags2int(v->value); 02193 if (y < 0) { 02194 ast_log(LOG_WARNING, "Invalid AMA flags: %s at line %d\n", v->value, v->lineno); 02195 } else { 02196 amaflags = y; 02197 } 02198 } else if (!strcasecmp(v->name, "mohinterpret") || !strcasecmp(v->name, "musiconhold")) { 02199 ast_copy_string(mohinterpret, v->value, sizeof(mohinterpret)); 02200 } else if (!strcasecmp(v->name, "mohsuggest")) { 02201 ast_copy_string(mohsuggest, v->value, sizeof(mohsuggest)); 02202 } else if (!strcasecmp(v->name, "callgroup")) { 02203 cur_callergroup = ast_get_group(v->value); 02204 } else if (!strcasecmp(v->name, "pickupgroup")) { 02205 cur_pickupgroup = ast_get_group(v->value); 02206 } else if (!strcasecmp(v->name, "immediate")) { 02207 immediate = ast_true(v->value); 02208 } else if (!strcasecmp(v->name, "cancallforward")) { 02209 cancallforward = ast_true(v->value); 02210 } else if (!strcasecmp(v->name, "mailbox")) { 02211 ast_copy_string(mailbox, v->value, sizeof(mailbox)); 02212 } else if (!strcasecmp(v->name, "hasvoicemail")) { 02213 if (ast_true(v->value) && ast_strlen_zero(mailbox)) { 02214 ast_copy_string(mailbox, cat, sizeof(mailbox)); 02215 } 02216 } else if (!strcasecmp(v->name, "callreturn")) { 02217 callreturn = ast_true(v->value); 02218 } else if (!strcasecmp(v->name, "callwaiting")) { 02219 callwaiting = ast_true(v->value); 02220 } else if (!strcasecmp(v->name, "transfer")) { 02221 transfer = ast_true(v->value); 02222 } else if (!strcasecmp(v->name, "threewaycalling")) { 02223 threewaycalling = ast_true(v->value); 02224 } else if (!strcasecmp(v->name, "mwiblink")) { 02225 mwiblink = ast_true(v->value); 02226 } else if (!strcasecmp(v->name, "linelabel")) { 02227 ast_copy_string(linelabel, v->value, sizeof(linelabel)); 02228 } else if (!strcasecmp(v->name, "speeddial")) { 02229 if (!(sd = ast_calloc(1, sizeof(struct skinny_speeddial)))) { 02230 return NULL; 02231 } else { 02232 char *stringp, *exten, *label; 02233 stringp = v->value; 02234 exten = strsep(&stringp, ","); 02235 label = strsep(&stringp, ","); 02236 ast_mutex_init(&sd->lock); 02237 ast_copy_string(sd->exten, exten, sizeof(sd->exten)); 02238 if (label) 02239 ast_copy_string(sd->label, label, sizeof(sd->label)); 02240 else 02241 ast_copy_string(sd->label, exten, sizeof(sd->label)); 02242 sd->instance = speeddialInstance++; 02243 02244 sd->parent = d; 02245 02246 sd->next = d->speeddials; 02247 d->speeddials = sd; 02248 } 02249 } else if (!strcasecmp(v->name, "addon")) { 02250 if (!(a = ast_calloc(1, sizeof(struct skinny_addon)))) { 02251 return NULL; 02252 } else { 02253 ast_mutex_init(&a->lock); 02254 ast_copy_string(a->type, v->value, sizeof(a->type)); 02255 02256 a->next = d->addons; 02257 d->addons = a; 02258 } 02259 } else if (!strcasecmp(v->name, "trunk") || !strcasecmp(v->name, "line")) { 02260 if (!(l = ast_calloc(1, sizeof(struct skinny_line)))) { 02261 return NULL; 02262 } else { 02263 ast_mutex_init(&l->lock); 02264 ast_copy_string(l->name, v->value, sizeof(l->name)); 02265 02266 /* XXX Should we check for uniqueness?? XXX */ 02267 ast_copy_string(l->context, context, sizeof(l->context)); 02268 ast_copy_string(l->cid_num, cid_num, sizeof(l->cid_num)); 02269 ast_copy_string(l->cid_name, cid_name, sizeof(l->cid_name)); 02270 ast_copy_string(l->label, linelabel, sizeof(l->label)); 02271 ast_copy_string(l->language, language, sizeof(l->language)); 02272 ast_copy_string(l->mohinterpret, mohinterpret, sizeof(l->mohinterpret)); 02273 ast_copy_string(l->mohsuggest, mohsuggest, sizeof(l->mohsuggest)); 02274 ast_copy_string(l->mailbox, mailbox, sizeof(l->mailbox)); 02275 if (!ast_strlen_zero(mailbox)) { 02276 if (option_verbose > 2) 02277 ast_verbose(VERBOSE_PREFIX_3 "Setting mailbox '%s' on %s@%s\n", mailbox, d->name, l->name); 02278 } 02279 l->msgstate = -1; 02280 l->capability = d->capability; 02281 l->prefs = d->prefs; 02282 l->parent = d; 02283 if (!strcasecmp(v->name, "trunk")) { 02284 l->type = TYPE_TRUNK; 02285 } else { 02286 l->type = TYPE_LINE; 02287 } 02288 l->immediate = immediate; 02289 l->callgroup = cur_callergroup; 02290 l->pickupgroup = cur_pickupgroup; 02291 l->callreturn = callreturn; 02292 l->cancallforward = cancallforward; 02293 l->callwaiting = callwaiting; 02294 l->transfer = transfer; 02295 l->threewaycalling = threewaycalling; 02296 l->mwiblink = mwiblink; 02297 l->onhooktime = time(NULL); 02298 l->instance = lineInstance++; 02299 /* ASSUME we're onhook at this point */ 02300 l->hookstate = SKINNY_ONHOOK; 02301 l->nat = nat; 02302 02303 l->next = d->lines; 02304 d->lines = l; 02305 } 02306 } else { 02307 ast_log(LOG_WARNING, "Don't know keyword '%s' at line %d\n", v->name, v->lineno); 02308 } 02309 v = v->next; 02310 } 02311 02312 if (!d->lines) { 02313 ast_log(LOG_ERROR, "A Skinny device must have at least one line!\n"); 02314 return NULL; 02315 } 02316 if (/*d->addr.sin_addr.s_addr && */!ntohs(d->addr.sin_port)) { 02317 d->addr.sin_port = htons(DEFAULT_SKINNY_PORT); 02318 } 02319 #if 0 02320 /* I don't think we need this anymore at all, since d->ourip is set in skinny_register now */ 02321 if (d->addr.sin_addr.s_addr) { 02322 /* XXX See note above, in 'host' option. */ 02323 if (ast_ouraddrfor(&d->addr.sin_addr, &d->ourip)) { 02324 d->ourip = __ourip; 02325 } 02326 } else { 02327 d->ourip = __ourip; 02328 } 02329 #endif 02330 } 02331 return d; 02332 }
static int codec_ast2skinny | ( | int | astcodec | ) | [static] |
Definition at line 1398 of file chan_skinny.c.
References AST_FORMAT_ALAW, AST_FORMAT_G723_1, AST_FORMAT_G726_AAL2, AST_FORMAT_G729A, AST_FORMAT_H261, AST_FORMAT_H263, AST_FORMAT_ULAW, SKINNY_CODEC_ALAW, SKINNY_CODEC_G723_1, SKINNY_CODEC_G726_32, SKINNY_CODEC_G729A, SKINNY_CODEC_H261, SKINNY_CODEC_H263, and SKINNY_CODEC_ULAW.
Referenced by handle_open_receive_channel_ack_message(), and transmit_connect().
01399 { 01400 switch (astcodec) { 01401 case AST_FORMAT_ALAW: 01402 return SKINNY_CODEC_ALAW; 01403 case AST_FORMAT_ULAW: 01404 return SKINNY_CODEC_ULAW; 01405 case AST_FORMAT_G723_1: 01406 return SKINNY_CODEC_G723_1; 01407 case AST_FORMAT_G729A: 01408 return SKINNY_CODEC_G729A; 01409 case AST_FORMAT_G726_AAL2: /* XXX Is this right? */ 01410 return SKINNY_CODEC_G726_32; 01411 case AST_FORMAT_H261: 01412 return SKINNY_CODEC_H261; 01413 case AST_FORMAT_H263: 01414 return SKINNY_CODEC_H263; 01415 default: 01416 return 0; 01417 } 01418 }
static int codec_skinny2ast | ( | enum skinny_codecs | skinnycodec | ) | [static] |
Definition at line 1376 of file chan_skinny.c.
References AST_FORMAT_ALAW, AST_FORMAT_G723_1, AST_FORMAT_G726_AAL2, AST_FORMAT_G729A, AST_FORMAT_H261, AST_FORMAT_H263, AST_FORMAT_ULAW, SKINNY_CODEC_ALAW, SKINNY_CODEC_G723_1, SKINNY_CODEC_G726_32, SKINNY_CODEC_G729A, SKINNY_CODEC_H261, SKINNY_CODEC_H263, and SKINNY_CODEC_ULAW.
Referenced by handle_capabilities_res_message().
01377 { 01378 switch (skinnycodec) { 01379 case SKINNY_CODEC_ALAW: 01380 return AST_FORMAT_ALAW; 01381 case SKINNY_CODEC_ULAW: 01382 return AST_FORMAT_ULAW; 01383 case SKINNY_CODEC_G723_1: 01384 return AST_FORMAT_G723_1; 01385 case SKINNY_CODEC_G729A: 01386 return AST_FORMAT_G729A; 01387 case SKINNY_CODEC_G726_32: 01388 return AST_FORMAT_G726_AAL2; /* XXX Is this right? */ 01389 case SKINNY_CODEC_H261: 01390 return AST_FORMAT_H261; 01391 case SKINNY_CODEC_H263: 01392 return AST_FORMAT_H263; 01393 default: 01394 return 0; 01395 } 01396 }
static char* complete_skinny_reset | ( | const char * | line, | |
const char * | word, | |||
int | pos, | |||
int | state | |||
) | [static] |
Definition at line 1889 of file chan_skinny.c.
References ast_strdup, devices, skinny_device::id, and skinny_device::next.
01890 { 01891 struct skinny_device *d; 01892 01893 char *result = NULL; 01894 int wordlen = strlen(word); 01895 int which = 0; 01896 01897 if (pos == 2) { 01898 for (d = devices; d && !result; d = d->next) { 01899 if (!strncasecmp(word, d->id, wordlen) && ++which > state) 01900 result = ast_strdup(d->id); 01901 } 01902 } 01903 01904 return result; 01905 }
static char* control2str | ( | int | ind | ) | [static] |
Definition at line 2741 of file chan_skinny.c.
References AST_CONTROL_ANSWER, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_FLASH, AST_CONTROL_HANGUP, AST_CONTROL_HOLD, AST_CONTROL_OFFHOOK, AST_CONTROL_OPTION, AST_CONTROL_PROCEEDING, AST_CONTROL_PROGRESS, AST_CONTROL_RADIO_KEY, AST_CONTROL_RADIO_UNKEY, AST_CONTROL_RING, AST_CONTROL_RINGING, AST_CONTROL_TAKEOFFHOOK, AST_CONTROL_UNHOLD, AST_CONTROL_WINK, ast_threadstorage_get(), CONTROL2STR_BUFSIZE, and control2str_threadbuf.
02741 { 02742 char *tmp; 02743 02744 switch (ind) { 02745 case AST_CONTROL_HANGUP: 02746 return "Other end has hungup"; 02747 case AST_CONTROL_RING: 02748 return "Local ring"; 02749 case AST_CONTROL_RINGING: 02750 return "Remote end is ringing"; 02751 case AST_CONTROL_ANSWER: 02752 return "Remote end has answered"; 02753 case AST_CONTROL_BUSY: 02754 return "Remote end is busy"; 02755 case AST_CONTROL_TAKEOFFHOOK: 02756 return "Make it go off hook"; 02757 case AST_CONTROL_OFFHOOK: 02758 return "Line is off hook"; 02759 case AST_CONTROL_CONGESTION: 02760 return "Congestion (circuits busy)"; 02761 case AST_CONTROL_FLASH: 02762 return "Flash hook"; 02763 case AST_CONTROL_WINK: 02764 return "Wink"; 02765 case AST_CONTROL_OPTION: 02766 return "Set a low-level option"; 02767 case AST_CONTROL_RADIO_KEY: 02768 return "Key Radio"; 02769 case AST_CONTROL_RADIO_UNKEY: 02770 return "Un-Key Radio"; 02771 case AST_CONTROL_PROGRESS: 02772 return "Remote end is making Progress"; 02773 case AST_CONTROL_PROCEEDING: 02774 return "Remote end is proceeding"; 02775 case AST_CONTROL_HOLD: 02776 return "Hold"; 02777 case AST_CONTROL_UNHOLD: 02778 return "Unhold"; 02779 case -1: 02780 return "Stop tone"; 02781 default: 02782 if (!(tmp = ast_threadstorage_get(&control2str_threadbuf, CONTROL2STR_BUFSIZE))) 02783 return "Unknown"; 02784 snprintf(tmp, CONTROL2STR_BUFSIZE, "UNKNOWN-%d", ind); 02785 return tmp; 02786 } 02787 }
static void control2str_threadbuf_init | ( | void | ) | [static] |
static void delete_devices | ( | void | ) | [static] |
Definition at line 4932 of file chan_skinny.c.
References ast_mutex_destroy(), ast_mutex_lock(), devicelock, devices, free, skinny_device::lines, skinny_speeddial::lock, skinny_line::lock, skinny_speeddial::next, skinny_line::next, and skinny_device::speeddials.
Referenced by unload_module().
04933 { 04934 struct skinny_device *d, *dlast; 04935 struct skinny_line *l, *llast; 04936 struct skinny_speeddial *sd, *sdlast; 04937 struct skinny_addon *a, *alast; 04938 04939 ast_mutex_lock(&devicelock); 04940 04941 /* Delete all devices */ 04942 for (d=devices;d;) { 04943 /* Delete all lines for this device */ 04944 for (l=d->lines;l;) { 04945 llast = l; 04946 l = l->next; 04947 ast_mutex_destroy(&llast->lock); 04948 free(llast); 04949 } 04950 /* Delete all speeddials for this device */ 04951 for (sd=d->speeddials;sd;) { 04952 sdlast = sd; 04953 sd = sd->next; 04954 ast_mutex_destroy(&sdlast->lock); 04955 free(sdlast); 04956 } 04957 /* Delete all addons for this device */ 04958 for (a=d->addons;a;) { 04959 alast = a; 04960 a = a->next; 04961 ast_mutex_destroy(&alast->lock); 04962 free(alast); 04963 } 04964 dlast = d; 04965 d = d->next; 04966 free(dlast); 04967 } 04968 devices=NULL; 04969 ast_mutex_unlock(&devicelock); 04970 }
static void destroy_session | ( | struct skinnysession * | s | ) | [static] |
Definition at line 4416 of file chan_skinny.c.
References ast_atomic_fetchadd_int(), ast_log(), ast_mutex_destroy(), ast_mutex_lock(), ast_mutex_unlock(), free, LOG_WARNING, skinnysession::next, s, sessionlock, and unauth_sessions.
04417 { 04418 struct skinnysession *cur, *prev = NULL; 04419 ast_mutex_lock(&sessionlock); 04420 cur = sessions; 04421 while(cur) { 04422 if (cur == s) { 04423 break; 04424 } 04425 prev = cur; 04426 cur = cur->next; 04427 } 04428 if (cur) { 04429 if (prev) { 04430 prev->next = cur->next; 04431 } else { 04432 sessions = cur->next; 04433 } 04434 if (s->fd > -1) { 04435 close(s->fd); 04436 } 04437 if (!s->device) { 04438 ast_atomic_fetchadd_int(&unauth_sessions, -1); 04439 } 04440 ast_mutex_destroy(&s->lock); 04441 free(s); 04442 } else { 04443 ast_log(LOG_WARNING, "Trying to delete nonexistent session %p?\n", s); 04444 } 04445 ast_mutex_unlock(&sessionlock); 04446 }
static char* device2str | ( | int | type | ) | [static] |
Definition at line 1943 of file chan_skinny.c.
References ast_threadstorage_get(), DEVICE2STR_BUFSIZE, device2str_threadbuf, SKINNY_DEVICE_12, SKINNY_DEVICE_12SP, SKINNY_DEVICE_12SPPLUS, SKINNY_DEVICE_30SPPLUS, SKINNY_DEVICE_30VIP, SKINNY_DEVICE_7902, SKINNY_DEVICE_7905, SKINNY_DEVICE_7906, SKINNY_DEVICE_7910, SKINNY_DEVICE_7911, SKINNY_DEVICE_7912, SKINNY_DEVICE_7914, SKINNY_DEVICE_7920, SKINNY_DEVICE_7921, SKINNY_DEVICE_7931, SKINNY_DEVICE_7935, SKINNY_DEVICE_7936, SKINNY_DEVICE_7937, SKINNY_DEVICE_7940, SKINNY_DEVICE_7941, SKINNY_DEVICE_7941GE, SKINNY_DEVICE_7942, SKINNY_DEVICE_7945, SKINNY_DEVICE_7960, SKINNY_DEVICE_7961, SKINNY_DEVICE_7961GE, SKINNY_DEVICE_7962, SKINNY_DEVICE_7965, SKINNY_DEVICE_7970, SKINNY_DEVICE_7971, SKINNY_DEVICE_7975, SKINNY_DEVICE_7985, SKINNY_DEVICE_ATA186, SKINNY_DEVICE_CIPC, SKINNY_DEVICE_NONE, SKINNY_DEVICE_SCCPGATEWAY_AN, SKINNY_DEVICE_SCCPGATEWAY_BRI, and SKINNY_DEVICE_UNKNOWN.
Referenced by skinny_show_devices().
01944 { 01945 char *tmp; 01946 01947 switch (type) { 01948 case SKINNY_DEVICE_NONE: 01949 return "No Device"; 01950 case SKINNY_DEVICE_30SPPLUS: 01951 return "30SP Plus"; 01952 case SKINNY_DEVICE_12SPPLUS: 01953 return "12SP Plus"; 01954 case SKINNY_DEVICE_12SP: 01955 return "12SP"; 01956 case SKINNY_DEVICE_12: 01957 return "12"; 01958 case SKINNY_DEVICE_30VIP: 01959 return "30VIP"; 01960 case SKINNY_DEVICE_7910: 01961 return "7910"; 01962 case SKINNY_DEVICE_7960: 01963 return "7960"; 01964 case SKINNY_DEVICE_7940: 01965 return "7940"; 01966 case SKINNY_DEVICE_7935: 01967 return "7935"; 01968 case SKINNY_DEVICE_ATA186: 01969 return "ATA186"; 01970 case SKINNY_DEVICE_7941: 01971 return "7941"; 01972 case SKINNY_DEVICE_7971: 01973 return "7971"; 01974 case SKINNY_DEVICE_7914: 01975 return "7914"; 01976 case SKINNY_DEVICE_7985: 01977 return "7985"; 01978 case SKINNY_DEVICE_7911: 01979 return "7911"; 01980 case SKINNY_DEVICE_7961GE: 01981 return "7961GE"; 01982 case SKINNY_DEVICE_7941GE: 01983 return "7941GE"; 01984 case SKINNY_DEVICE_7931: 01985 return "7931"; 01986 case SKINNY_DEVICE_7921: 01987 return "7921"; 01988 case SKINNY_DEVICE_7906: 01989 return "7906"; 01990 case SKINNY_DEVICE_7962: 01991 return "7962"; 01992 case SKINNY_DEVICE_7937: 01993 return "7937"; 01994 case SKINNY_DEVICE_7942: 01995 return "7942"; 01996 case SKINNY_DEVICE_7945: 01997 return "7945"; 01998 case SKINNY_DEVICE_7965: 01999 return "7965"; 02000 case SKINNY_DEVICE_7975: 02001 return "7975"; 02002 case SKINNY_DEVICE_7905: 02003 return "7905"; 02004 case SKINNY_DEVICE_7920: 02005 return "7920"; 02006 case SKINNY_DEVICE_7970: 02007 return "7970"; 02008 case SKINNY_DEVICE_7912: 02009 return "7912"; 02010 case SKINNY_DEVICE_7902: 02011 return "7902"; 02012 case SKINNY_DEVICE_CIPC: 02013 return "IP Communicator"; 02014 case SKINNY_DEVICE_7961: 02015 return "7961"; 02016 case SKINNY_DEVICE_7936: 02017 return "7936"; 02018 case SKINNY_DEVICE_SCCPGATEWAY_AN: 02019 return "SCCPGATEWAY_AN"; 02020 case SKINNY_DEVICE_SCCPGATEWAY_BRI: 02021 return "SCCPGATEWAY_BRI"; 02022 case SKINNY_DEVICE_UNKNOWN: 02023 return "Unknown"; 02024 default: 02025 if (!(tmp = ast_threadstorage_get(&device2str_threadbuf, DEVICE2STR_BUFSIZE))) 02026 return "Unknown"; 02027 snprintf(tmp, DEVICE2STR_BUFSIZE, "UNKNOWN-%d", type); 02028 return tmp; 02029 } 02030 }
static void device2str_threadbuf_init | ( | void | ) | [static] |
static void do_housekeeping | ( | struct skinnysession * | s | ) | [static] |
Definition at line 1796 of file chan_skinny.c.
References handle_time_date_req_message(), and s.
Referenced by handle_keep_alive_message(), handle_onhook_message(), handle_soft_key_event_message(), and skinny_hangup().
01797 { 01798 /* 01799 int new; 01800 int old; 01801 struct skinny_device *d = s->device; 01802 struct skinny_line *l; 01803 */ 01804 01805 /* Update time on device */ 01806 handle_time_date_req_message(NULL, s); 01807 01808 /* 01809 for (l = d->lines; l; l = l->next) { 01810 if (has_voicemail(l)) { 01811 if (skinnydebug) 01812 ast_verbose("Checking for voicemail Skinny %s@%s\n", l->name, d->name); 01813 ast_app_inboxcount(l->mailbox, &new, &old); 01814 if (skinnydebug) 01815 ast_verbose("Skinny %s@%s has voicemail!\n", l->name, d->name); 01816 transmit_lamp_indication(s, STIMULUS_VOICEMAIL, l->instance, l->mwiblink?SKINNY_LAMP_BLINK:SKINNY_LAMP_ON); 01817 } else { 01818 transmit_lamp_indication(s, STIMULUS_VOICEMAIL, l->instance, SKINNY_LAMP_OFF); 01819 } 01820 } 01821 */ 01822 }
static void* do_monitor | ( | void * | data | ) | [static] |
Definition at line 4674 of file chan_skinny.c.
References ast_io_wait(), ast_mutex_lock(), ast_mutex_unlock(), ast_sched_runq(), ast_sched_wait(), io, and monlock.
04675 { 04676 int res; 04677 04678 /* This thread monitors all the interfaces which are not yet in use 04679 (and thus do not have a separate thread) indefinitely */ 04680 /* From here on out, we die whenever asked */ 04681 for(;;) { 04682 pthread_testcancel(); 04683 /* Wait for sched or io */ 04684 res = ast_sched_wait(sched); 04685 if ((res < 0) || (res > 1000)) { 04686 res = 1000; 04687 } 04688 res = ast_io_wait(io, res); 04689 ast_mutex_lock(&monlock); 04690 if (res >= 0) { 04691 ast_sched_runq(sched); 04692 } 04693 ast_mutex_unlock(&monlock); 04694 } 04695 /* Never reached */ 04696 return NULL; 04697 04698 }
static struct skinny_line* find_line_by_instance | ( | struct skinny_device * | d, | |
int | instance | |||
) | [static] |
Definition at line 1257 of file chan_skinny.c.
References ast_log(), skinny_line::instance, skinny_device::lines, LOG_WARNING, skinny_device::name, and skinny_line::next.
Referenced by find_subchannel_by_instance_reference(), handle_enbloc_call_message(), handle_line_state_req_message(), handle_offhook_message(), handle_soft_key_event_message(), and handle_stimulus_message().
01258 { 01259 struct skinny_line *l; 01260 01261 if (!instance) 01262 instance = 1; 01263 01264 for (l = d->lines; l; l = l->next) { 01265 if (l->instance == instance) 01266 break; 01267 } 01268 01269 if (!l) { 01270 ast_log(LOG_WARNING, "Could not find line with instance '%d' on device '%s'\n", instance, d->name); 01271 } 01272 return l; 01273 }
static struct skinny_line* find_line_by_name | ( | const char * | dest | ) | [static] |
Definition at line 1275 of file chan_skinny.c.
References ast_copy_string(), ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), devicelock, devices, skinny_device::lines, LOG_NOTICE, skinny_line::name, skinny_device::name, skinny_line::next, and skinny_device::next.
Referenced by skinny_request().
01276 { 01277 struct skinny_line *l; 01278 struct skinny_device *d; 01279 char line[256]; 01280 char *at; 01281 char *device; 01282 01283 ast_copy_string(line, dest, sizeof(line)); 01284 at = strchr(line, '@'); 01285 if (!at) { 01286 ast_log(LOG_NOTICE, "Device '%s' has no @ (at) sign!\n", dest); 01287 return NULL; 01288 } 01289 *at++ = '\0'; 01290 device = at; 01291 ast_mutex_lock(&devicelock); 01292 for (d = devices; d; d = d->next) { 01293 if (!strcasecmp(d->name, device)) { 01294 if (skinnydebug) 01295 ast_verbose("Found device: %s\n", d->name); 01296 /* Found the device */ 01297 for (l = d->lines; l; l = l->next) { 01298 /* Search for the right line */ 01299 if (!strcasecmp(l->name, line)) { 01300 ast_mutex_unlock(&devicelock); 01301 return l; 01302 } 01303 } 01304 } 01305 } 01306 /* Device not found */ 01307 ast_mutex_unlock(&devicelock); 01308 return NULL; 01309 }
static struct skinny_speeddial* find_speeddial_by_instance | ( | struct skinny_device * | d, | |
int | instance | |||
) | [static] |
Definition at line 1361 of file chan_skinny.c.
References ast_log(), skinny_speeddial::instance, LOG_WARNING, skinny_device::name, skinny_speeddial::next, and skinny_device::speeddials.
Referenced by handle_speed_dial_stat_req_message(), and handle_stimulus_message().
01362 { 01363 struct skinny_speeddial *sd; 01364 01365 for (sd = d->speeddials; sd; sd = sd->next) { 01366 if (sd->instance == instance) 01367 break; 01368 } 01369 01370 if (!sd) { 01371 ast_log(LOG_WARNING, "Could not find speeddial with instance '%d' on device '%s'\n", instance, d->name); 01372 } 01373 return sd; 01374 }
static struct skinny_subchannel* find_subchannel_by_instance_reference | ( | struct skinny_device * | d, | |
int | instance, | |||
int | reference | |||
) | [static] |
Definition at line 1312 of file chan_skinny.c.
References ast_log(), skinny_subchannel::callid, find_line_by_instance(), LOG_WARNING, skinny_device::name, skinny_subchannel::next, and skinny_line::sub.
Referenced by handle_enbloc_call_message(), handle_keypad_button_message(), handle_message(), handle_offhook_message(), handle_onhook_message(), handle_soft_key_event_message(), and handle_stimulus_message().
01313 { 01314 struct skinny_line *l = find_line_by_instance(d, instance); 01315 struct skinny_subchannel *sub; 01316 01317 if (!l) { 01318 return NULL; 01319 } 01320 01321 if (!reference) 01322 sub = l->sub; 01323 else { 01324 for (sub = l->sub; sub; sub = sub->next) { 01325 if (sub->callid == reference) 01326 break; 01327 } 01328 } 01329 01330 if (!sub) { 01331 ast_log(LOG_WARNING, "Could not find subchannel with reference '%d' on '%s'\n", reference, d->name); 01332 } 01333 return sub; 01334 }
static struct skinny_subchannel* find_subchannel_by_reference | ( | struct skinny_device * | d, | |
int | reference | |||
) | [static] |
Definition at line 1337 of file chan_skinny.c.
References ast_log(), skinny_subchannel::callid, skinny_device::lines, LOG_WARNING, skinny_line::name, skinny_device::name, skinny_subchannel::next, skinny_line::next, and skinny_line::sub.
Referenced by handle_open_receive_channel_ack_message().
01338 { 01339 struct skinny_line *l; 01340 struct skinny_subchannel *sub = NULL; 01341 01342 for (l = d->lines; l; l = l->next) { 01343 for (sub = l->sub; sub; sub = sub->next) { 01344 if (sub->callid == reference) 01345 break; 01346 } 01347 if (sub) 01348 break; 01349 } 01350 01351 if (!l) { 01352 ast_log(LOG_WARNING, "Could not find any lines that contained a subchannel with reference '%d' on device '%s'\n", reference, d->name); 01353 } else { 01354 if (!sub) { 01355 ast_log(LOG_WARNING, "Could not find subchannel with reference '%d' on '%s@%s'\n", reference, l->name, d->name); 01356 } 01357 } 01358 return sub; 01359 }
static void* get_button_template | ( | struct skinnysession * | s, | |
struct button_definition_template * | btn | |||
) | [static] |
Definition at line 1107 of file chan_skinny.c.
References skinny_device::addons, ast_log(), BT_CALLPARK, BT_CONFERENCE, BT_CUST_LINESPEEDDIAL, BT_DISPLAY, BT_FORWARDALL, BT_HOLD, BT_LINE, BT_NONE, BT_REDIAL, BT_SPEEDDIAL, BT_TRANSFER, BT_VOICEMAIL, LOG_WARNING, skinny_addon::next, s, SKINNY_DEVICE_12, SKINNY_DEVICE_12SP, SKINNY_DEVICE_12SPPLUS, SKINNY_DEVICE_30SPPLUS, SKINNY_DEVICE_30VIP, SKINNY_DEVICE_7902, SKINNY_DEVICE_7905, SKINNY_DEVICE_7906, SKINNY_DEVICE_7910, SKINNY_DEVICE_7911, SKINNY_DEVICE_7912, SKINNY_DEVICE_7914, SKINNY_DEVICE_7920, SKINNY_DEVICE_7921, SKINNY_DEVICE_7931, SKINNY_DEVICE_7935, SKINNY_DEVICE_7936, SKINNY_DEVICE_7937, SKINNY_DEVICE_7940, SKINNY_DEVICE_7941, SKINNY_DEVICE_7941GE, SKINNY_DEVICE_7942, SKINNY_DEVICE_7945, SKINNY_DEVICE_7960, SKINNY_DEVICE_7961, SKINNY_DEVICE_7961GE, SKINNY_DEVICE_7962, SKINNY_DEVICE_7965, SKINNY_DEVICE_7970, SKINNY_DEVICE_7971, SKINNY_DEVICE_7975, SKINNY_DEVICE_7985, SKINNY_DEVICE_ATA186, SKINNY_DEVICE_CIPC, SKINNY_DEVICE_SCCPGATEWAY_AN, SKINNY_DEVICE_SCCPGATEWAY_BRI, skinny_addon::type, and skinny_device::type.
Referenced by handle_button_template_req_message().
01108 { 01109 struct skinny_device *d = s->device; 01110 struct skinny_addon *a = d->addons; 01111 int i; 01112 01113 switch (d->type) { 01114 case SKINNY_DEVICE_30SPPLUS: 01115 case SKINNY_DEVICE_30VIP: 01116 /* 13 rows, 2 columns */ 01117 for (i = 0; i < 4; i++) 01118 (btn++)->buttonDefinition = BT_LINE; 01119 (btn++)->buttonDefinition = BT_REDIAL; 01120 (btn++)->buttonDefinition = BT_VOICEMAIL; 01121 (btn++)->buttonDefinition = BT_CALLPARK; 01122 (btn++)->buttonDefinition = BT_FORWARDALL; 01123 (btn++)->buttonDefinition = BT_CONFERENCE; 01124 for (i = 0; i < 4; i++) 01125 (btn++)->buttonDefinition = BT_NONE; 01126 for (i = 0; i < 13; i++) 01127 (btn++)->buttonDefinition = BT_SPEEDDIAL; 01128 01129 break; 01130 case SKINNY_DEVICE_12SPPLUS: 01131 case SKINNY_DEVICE_12SP: 01132 case SKINNY_DEVICE_12: 01133 /* 6 rows, 2 columns */ 01134 for (i = 0; i < 2; i++) 01135 (btn++)->buttonDefinition = BT_LINE; 01136 (btn++)->buttonDefinition = BT_REDIAL; 01137 for (i = 0; i < 3; i++) 01138 (btn++)->buttonDefinition = BT_SPEEDDIAL; 01139 (btn++)->buttonDefinition = BT_HOLD; 01140 (btn++)->buttonDefinition = BT_TRANSFER; 01141 (btn++)->buttonDefinition = BT_FORWARDALL; 01142 (btn++)->buttonDefinition = BT_CALLPARK; 01143 (btn++)->buttonDefinition = BT_VOICEMAIL; 01144 (btn++)->buttonDefinition = BT_CONFERENCE; 01145 break; 01146 case SKINNY_DEVICE_7910: 01147 (btn++)->buttonDefinition = BT_LINE; 01148 (btn++)->buttonDefinition = BT_HOLD; 01149 (btn++)->buttonDefinition = BT_TRANSFER; 01150 (btn++)->buttonDefinition = BT_DISPLAY; 01151 (btn++)->buttonDefinition = BT_VOICEMAIL; 01152 (btn++)->buttonDefinition = BT_CONFERENCE; 01153 (btn++)->buttonDefinition = BT_FORWARDALL; 01154 for (i = 0; i < 2; i++) 01155 (btn++)->buttonDefinition = BT_SPEEDDIAL; 01156 (btn++)->buttonDefinition = BT_REDIAL; 01157 break; 01158 case SKINNY_DEVICE_7960: 01159 case SKINNY_DEVICE_7961: 01160 case SKINNY_DEVICE_7961GE: 01161 case SKINNY_DEVICE_7962: 01162 case SKINNY_DEVICE_7965: 01163 for (i = 0; i < 6; i++) 01164 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01165 break; 01166 case SKINNY_DEVICE_7940: 01167 case SKINNY_DEVICE_7941: 01168 case SKINNY_DEVICE_7941GE: 01169 case SKINNY_DEVICE_7942: 01170 case SKINNY_DEVICE_7945: 01171 for (i = 0; i < 2; i++) 01172 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01173 break; 01174 case SKINNY_DEVICE_7935: 01175 case SKINNY_DEVICE_7936: 01176 for (i = 0; i < 2; i++) 01177 (btn++)->buttonDefinition = BT_LINE; 01178 break; 01179 case SKINNY_DEVICE_ATA186: 01180 (btn++)->buttonDefinition = BT_LINE; 01181 break; 01182 case SKINNY_DEVICE_7970: 01183 case SKINNY_DEVICE_7971: 01184 case SKINNY_DEVICE_7975: 01185 case SKINNY_DEVICE_CIPC: 01186 for (i = 0; i < 8; i++) 01187 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01188 break; 01189 case SKINNY_DEVICE_7985: 01190 /* XXX I have no idea what the buttons look like on these. */ 01191 ast_log(LOG_WARNING, "Unsupported device type '%d (7985)' found.\n", d->type); 01192 break; 01193 case SKINNY_DEVICE_7912: 01194 case SKINNY_DEVICE_7911: 01195 case SKINNY_DEVICE_7905: 01196 (btn++)->buttonDefinition = BT_LINE; 01197 (btn++)->buttonDefinition = BT_HOLD; 01198 break; 01199 case SKINNY_DEVICE_7920: 01200 /* XXX I don't know if this is right. */ 01201 for (i = 0; i < 4; i++) 01202 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01203 break; 01204 case SKINNY_DEVICE_7921: 01205 for (i = 0; i < 6; i++) 01206 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01207 break; 01208 case SKINNY_DEVICE_7902: 01209 ast_log(LOG_WARNING, "Unsupported device type '%d (7902)' found.\n", d->type); 01210 break; 01211 case SKINNY_DEVICE_7906: 01212 ast_log(LOG_WARNING, "Unsupported device type '%d (7906)' found.\n", d->type); 01213 break; 01214 case SKINNY_DEVICE_7931: 01215 ast_log(LOG_WARNING, "Unsupported device type '%d (7931)' found.\n", d->type); 01216 break; 01217 case SKINNY_DEVICE_7937: 01218 ast_log(LOG_WARNING, "Unsupported device type '%d (7937)' found.\n", d->type); 01219 break; 01220 case SKINNY_DEVICE_7914: 01221 ast_log(LOG_WARNING, "Unsupported device type '%d (7914)' found. Expansion module registered by itself?\n", d->type); 01222 break; 01223 case SKINNY_DEVICE_SCCPGATEWAY_AN: 01224 case SKINNY_DEVICE_SCCPGATEWAY_BRI: 01225 ast_log(LOG_WARNING, "Unsupported device type '%d (SCCP gateway)' found.\n", d->type); 01226 break; 01227 default: 01228 ast_log(LOG_WARNING, "Unknown device type '%d' found.\n", d->type); 01229 break; 01230 } 01231 01232 for (a = d->addons; a; a = a->next) { 01233 if (!strcasecmp(a->type, "7914")) { 01234 for (i = 0; i < 14; i++) 01235 (btn++)->buttonDefinition = BT_CUST_LINESPEEDDIAL; 01236 } else { 01237 ast_log(LOG_WARNING, "Unknown addon type '%s' found. Skipping.\n", a->type); 01238 } 01239 } 01240 01241 return btn; 01242 }
static int get_input | ( | struct skinnysession * | s | ) | [static] |
Definition at line 4448 of file chan_skinny.c.
References ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_poll, ast_verbose(), auth_timeout, errno, htolel, keep_alive, letohl, LOG_ERROR, LOG_WARNING, s, skinny_unregister(), and skinnydebug.
04449 { 04450 int res; 04451 int dlen = 0; 04452 int timeout = keep_alive * 1100; 04453 time_t now; 04454 int *bufaddr; 04455 struct pollfd fds[1]; 04456 04457 if (!s->device) { 04458 if(time(&now) == -1) { 04459 ast_log(LOG_ERROR, "error executing time(): %s\n", strerror(errno)); 04460 return -1; 04461 } 04462 04463 timeout = (auth_timeout - (now - s->start)) * 1000; 04464 if (timeout < 0) { 04465 /* we have timed out */ 04466 if (skinnydebug) 04467 ast_verbose("Skinny Client failed to authenticate in %d seconds\n", auth_timeout); 04468 return -1; 04469 } 04470 } 04471 04472 fds[0].fd = s->fd; 04473 fds[0].events = POLLIN; 04474 fds[0].revents = 0; 04475 res = ast_poll(fds, 1, timeout); /* If nothing has happen, client is dead */ 04476 /* we add 10% to the keep_alive to deal */ 04477 /* with network delays, etc */ 04478 if (res < 0) { 04479 if (errno != EINTR) { 04480 ast_log(LOG_WARNING, "Select returned error: %s\n", strerror(errno)); 04481 return res; 04482 } 04483 } else if (res == 0) { 04484 if (skinnydebug) { 04485 if (s->device) { 04486 ast_verbose("Skinny Client was lost, unregistering\n"); 04487 } else { 04488 ast_verbose("Skinny Client failed to authenticate in %d seconds\n", auth_timeout); 04489 } 04490 } 04491 skinny_unregister(NULL, s); 04492 return -1; 04493 } 04494 04495 if (fds[0].revents) { 04496 ast_mutex_lock(&s->lock); 04497 memset(s->inbuf,0,sizeof(s->inbuf)); 04498 res = read(s->fd, s->inbuf, 4); 04499 if (res < 0) { 04500 ast_log(LOG_WARNING, "read() returned error: %s\n", strerror(errno)); 04501 04502 if (skinnydebug) 04503 ast_verbose("Skinny Client was lost, unregistering\n"); 04504 04505 skinny_unregister(NULL,s); 04506 ast_mutex_unlock(&s->lock); 04507 return res; 04508 } else if (res != 4) { 04509 ast_log(LOG_WARNING, "Skinny Client sent less data than expected. Expected 4 but got %d.\n", res); 04510 ast_mutex_unlock(&s->lock); 04511 04512 if (res == 0) { 04513 if (skinnydebug) 04514 ast_verbose("Skinny Client was lost, unregistering\n"); 04515 skinny_unregister(NULL, s); 04516 } 04517 04518 return -1; 04519 } 04520 04521 bufaddr = (int *)s->inbuf; 04522 dlen = letohl(*bufaddr); 04523 if (dlen < 4) { 04524 ast_log(LOG_WARNING, "Skinny Client sent invalid data.\n"); 04525 ast_mutex_unlock(&s->lock); 04526 return -1; 04527 } 04528 if (dlen+8 > sizeof(s->inbuf)) { 04529 dlen = sizeof(s->inbuf) - 8; 04530 } 04531 *bufaddr = htolel(dlen); 04532 04533 res = read(s->fd, s->inbuf+4, dlen+4); 04534 ast_mutex_unlock(&s->lock); 04535 if (res < 0) { 04536 ast_log(LOG_WARNING, "read() returned error: %s\n", strerror(errno)); 04537 return res; 04538 } else if (res != (dlen+4)) { 04539 ast_log(LOG_WARNING, "Skinny Client sent less data than expected.\n"); 04540 return -1; 04541 } 04542 return res; 04543 } 04544 return 0; 04545 }
static int handle_alarm_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3796 of file chan_skinny.c.
References skinny_data::alarm, ast_verbose(), skinny_req::data, alarm_message::displayMessage, and skinnydebug.
Referenced by handle_message().
03797 { 03798 /* no response necessary */ 03799 if (skinnydebug) 03800 ast_verbose("Received Alarm Message: %s\n", req->data.alarm.displayMessage); 03801 03802 return 1; 03803 }
static int handle_button_template_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3660 of file chan_skinny.c.
References ast_verbose(), BT_CUST_HINT, BT_CUST_LINESPEEDDIAL, BT_LINE, BT_NONE, BT_SPEEDDIAL, BUTTON_TEMPLATE_RES_MESSAGE, button_definition::buttonDefinition, button_definition_template::buttonDefinition, skinny_data::buttontemplate, skinny_req::data, button_template_res_message::definition, get_button_template(), htolel, skinny_speeddial::instance, skinny_line::instance, button_definition::instanceNumber, skinny_device::lines, skinny_speeddial::next, skinny_line::next, req_alloc(), s, and skinny_device::speeddials.
Referenced by handle_message().
03661 { 03662 struct skinny_device *d = s->device; 03663 struct skinny_line *l; 03664 int i; 03665 03666 struct skinny_speeddial *sd; 03667 struct button_definition_template btn[42]; 03668 int lineInstance = 1; 03669 int speeddialInstance = 1; 03670 int buttonCount = 0; 03671 03672 if (!(req = req_alloc(sizeof(struct button_template_res_message), BUTTON_TEMPLATE_RES_MESSAGE))) 03673 return -1; 03674 03675 memset(&btn, 0, sizeof(btn)); 03676 03677 get_button_template(s, btn); 03678 03679 for (i=0; i<42; i++) { 03680 int btnSet = 0; 03681 switch (btn[i].buttonDefinition) { 03682 case BT_CUST_LINESPEEDDIAL: 03683 /* assume failure */ 03684 req->data.buttontemplate.definition[i].buttonDefinition = BT_NONE; 03685 req->data.buttontemplate.definition[i].instanceNumber = htolel(0); 03686 03687 for (l = d->lines; l; l = l->next) { 03688 if (l->instance == lineInstance) { 03689 ast_verbose("Adding button: %d, %d\n", BT_LINE, lineInstance); 03690 req->data.buttontemplate.definition[i].buttonDefinition = BT_LINE; 03691 req->data.buttontemplate.definition[i].instanceNumber = htolel(lineInstance); 03692 lineInstance++; 03693 buttonCount++; 03694 btnSet = 1; 03695 break; 03696 } 03697 } 03698 03699 if (!btnSet) { 03700 for (sd = d->speeddials; sd; sd = sd->next) { 03701 if (sd->instance == speeddialInstance) { 03702 ast_verbose("Adding button: %d, %d\n", BT_SPEEDDIAL, speeddialInstance); 03703 req->data.buttontemplate.definition[i].buttonDefinition = BT_SPEEDDIAL; 03704 req->data.buttontemplate.definition[i].instanceNumber = htolel(speeddialInstance); 03705 speeddialInstance++; 03706 buttonCount++; 03707 btnSet = 1; 03708 break; 03709 } 03710 } 03711 } 03712 break; 03713 case BT_LINE: 03714 req->data.buttontemplate.definition[i].buttonDefinition = htolel(BT_NONE); 03715 req->data.buttontemplate.definition[i].instanceNumber = htolel(0); 03716 03717 for (l = d->lines; l; l = l->next) { 03718 if (l->instance == lineInstance) { 03719 ast_verbose("Adding button: %d, %d\n", BT_LINE, lineInstance); 03720 req->data.buttontemplate.definition[i].buttonDefinition = BT_LINE; 03721 req->data.buttontemplate.definition[i].instanceNumber = htolel(lineInstance); 03722 lineInstance++; 03723 buttonCount++; 03724 btnSet = 1; 03725 break; 03726 } 03727 } 03728 break; 03729 case BT_SPEEDDIAL: 03730 req->data.buttontemplate.definition[i].buttonDefinition = BT_NONE; 03731 req->data.buttontemplate.definition[i].instanceNumber = 0; 03732 03733 for (sd = d->speeddials; sd; sd = sd->next) { 03734 if (sd->instance == speeddialInstance) { 03735 ast_verbose("Adding button: %d, %d\n", BT_SPEEDDIAL, speeddialInstance); 03736 req->data.buttontemplate.definition[i].buttonDefinition = BT_SPEEDDIAL; 03737 req->data.buttontemplate.definition[i].instanceNumber = htolel(speeddialInstance); 03738 speeddialInstance++; 03739 buttonCount++; 03740 btnSet = 1; 03741 break; 03742 } 03743 } 03744 break; 03745 case BT_CUST_HINT: 03746 break; 03747 case BT_NONE: 03748 break; 03749 default: 03750 ast_verbose("Adding button: %d, %d\n", btn[i].buttonDefinition, 0); 03751 req->data.buttontemplate.definition[i].buttonDefinition = htolel(btn[i].buttonDefinition); 03752 req->data.buttontemplate.definition[i].instanceNumber = htolel(0); 03753 buttonCount++; 03754 btnSet = 1; 03755 break; 03756 } 03757 } 03758 03759 req->data.buttontemplate.buttonOffset = htolel(0); 03760 req->data.buttontemplate.buttonCount = htolel(buttonCount); 03761 req->data.buttontemplate.totalButtonCount = htolel(buttonCount); 03762 03763 if (skinnydebug) 03764 ast_verbose("Sending %d template to %s\n", 03765 d->type, 03766 d->name); 03767 transmit_response(s, req); 03768 return 1; 03769 }
static int handle_capabilities_res_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3547 of file chan_skinny.c.
References ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), skinny_line::capability, skinny_device::capability, capabilities_res_message::caps, skinny_data::caps, station_capabilities::codec, codec_skinny2ast(), capabilities_res_message::count, skinny_req::data, letohl, skinny_device::lines, skinny_line::lock, LOG_WARNING, skinny_line::next, s, SKINNY_MAX_CAPABILITIES, and skinnydebug.
Referenced by handle_message().
03548 { 03549 struct skinny_device *d = s->device; 03550 struct skinny_line *l; 03551 uint32_t count = 0; 03552 int codecs = 0; 03553 int i; 03554 03555 count = letohl(req->data.caps.count); 03556 if (count > SKINNY_MAX_CAPABILITIES) { 03557 count = SKINNY_MAX_CAPABILITIES; 03558 ast_log(LOG_WARNING, "Received more capabilities than we can handle (%d). Ignoring the rest.\n", SKINNY_MAX_CAPABILITIES); 03559 } 03560 03561 for (i = 0; i < count; i++) { 03562 int acodec = 0; 03563 int scodec = 0; 03564 scodec = letohl(req->data.caps.caps[i].codec); 03565 acodec = codec_skinny2ast(scodec); 03566 if (skinnydebug) 03567 ast_verbose("Adding codec capability '%d (%d)'\n", acodec, scodec); 03568 codecs |= acodec; 03569 } 03570 03571 d->capability &= codecs; 03572 ast_verbose("Device capability set to '%d'\n", d->capability); 03573 for (l = d->lines; l; l = l->next) { 03574 ast_mutex_lock(&l->lock); 03575 l->capability = d->capability; 03576 ast_mutex_unlock(&l->lock); 03577 } 03578 03579 return 1; 03580 }
static int handle_enbloc_call_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3874 of file chan_skinny.c.
References ast_copy_string(), ast_hangup(), ast_ignore_pattern(), ast_log(), ast_pthread_create, AST_STATE_DOWN, ast_verbose(), enbloc_call_message::calledParty, skinny_subchannel::callid, ast_channel::context, skinny_req::data, skinny_data::enbloccallmessage, errno, ast_channel::exten, find_line_by_instance(), find_subchannel_by_instance_reference(), skinny_line::hookstate, skinny_line::instance, skinny_device::lastcallreference, skinny_device::lastlineinstance, LOG_WARNING, skinny_device::name, skinny_line::name, skinny_subchannel::parent, s, SKINNY_DIALTONE, skinny_new(), skinny_newcall(), SKINNY_OFFHOOK, SKINNY_SILENCE, skinnydebug, t, ast_channel::tech_pvt, transmit_callstate(), transmit_displaymessage(), and transmit_tone().
Referenced by handle_message().
03875 { 03876 struct skinny_device *d = s->device; 03877 struct skinny_line *l; 03878 struct skinny_subchannel *sub = NULL; 03879 struct ast_channel *c; 03880 pthread_t t; 03881 03882 if (skinnydebug) 03883 ast_verbose("Received Enbloc Call: %s\n", req->data.enbloccallmessage.calledParty); 03884 03885 sub = find_subchannel_by_instance_reference(d, d->lastlineinstance, d->lastcallreference); 03886 03887 if (!sub) { 03888 l = find_line_by_instance(d, d->lastlineinstance); 03889 if (!l) { 03890 return 0; 03891 } 03892 } else { 03893 l = sub->parent; 03894 } 03895 03896 c = skinny_new(l, AST_STATE_DOWN); 03897 03898 if(!c) { 03899 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 03900 } else { 03901 l->hookstate = SKINNY_OFFHOOK; 03902 03903 sub = c->tech_pvt; 03904 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03905 if (skinnydebug) 03906 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 03907 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 03908 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 03909 03910 if (!ast_ignore_pattern(c->context, req->data.enbloccallmessage.calledParty)) { 03911 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 03912 } 03913 ast_copy_string(c->exten, req->data.enbloccallmessage.calledParty, sizeof(c->exten)); 03914 if (ast_pthread_create(&t, NULL, skinny_newcall, c)) { 03915 ast_log(LOG_WARNING, "Unable to create new call thread: %s\n", strerror(errno)); 03916 ast_hangup(c); 03917 } 03918 } 03919 03920 return 1; 03921 }
static int handle_headset_status_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
static int handle_ip_port_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
static int handle_keep_alive_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3046 of file chan_skinny.c.
References do_housekeeping(), KEEP_ALIVE_ACK_MESSAGE, req_alloc(), s, and transmit_response().
Referenced by handle_message().
03047 { 03048 if (!(req = req_alloc(0, KEEP_ALIVE_ACK_MESSAGE))) 03049 return -1; 03050 03051 transmit_response(s, req); 03052 do_housekeeping(s); 03053 return 1; 03054 }
static int handle_keypad_button_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3105 of file chan_skinny.c.
References ast_channel::_state, AST_FRAME_DTMF_BEGIN, AST_FRAME_DTMF_END, ast_log(), ast_queue_frame(), ast_verbose(), keypad_button_message::button, keypad_button_message::callReference, skinny_req::data, f, find_subchannel_by_instance_reference(), skinny_data::keypad, skinny_device::lastcallreference, skinny_device::lastlineinstance, letohl, keypad_button_message::lineInstance, LOG_WARNING, skinny_line::name, skinny_subchannel::next, skinny_subchannel::owner, skinny_subchannel::parent, s, and skinnydebug.
Referenced by handle_message().
03106 { 03107 struct skinny_subchannel *sub = NULL; 03108 struct skinny_line *l; 03109 struct skinny_device *d = s->device; 03110 struct ast_frame f = { 0, }; 03111 char dgt; 03112 int digit; 03113 int lineInstance; 03114 int callReference; 03115 03116 digit = letohl(req->data.keypad.button); 03117 lineInstance = letohl(req->data.keypad.lineInstance); 03118 callReference = letohl(req->data.keypad.callReference); 03119 03120 if (digit == 14) { 03121 dgt = '*'; 03122 } else if (digit == 15) { 03123 dgt = '#'; 03124 } else if (digit >= 0 && digit <= 9) { 03125 dgt = '0' + digit; 03126 } else { 03127 /* digit=10-13 (A,B,C,D ?), or 03128 * digit is bad value 03129 * 03130 * probably should not end up here, but set 03131 * value for backward compatibility, and log 03132 * a warning. 03133 */ 03134 dgt = '0' + digit; 03135 ast_log(LOG_WARNING, "Unsupported digit %d\n", digit); 03136 } 03137 03138 f.subclass = dgt; 03139 03140 f.src = "skinny"; 03141 03142 if (lineInstance && callReference) 03143 sub = find_subchannel_by_instance_reference(d, lineInstance, callReference); 03144 else 03145 sub = find_subchannel_by_instance_reference(d, d->lastlineinstance, d->lastcallreference); 03146 03147 if (!sub) 03148 return 0; 03149 03150 l = sub->parent; 03151 if (sub->owner) { 03152 if (sub->owner->_state == 0) { 03153 f.frametype = AST_FRAME_DTMF_BEGIN; 03154 ast_queue_frame(sub->owner, &f); 03155 } 03156 /* XXX MUST queue this frame to all lines in threeway call if threeway call is active */ 03157 f.frametype = AST_FRAME_DTMF_END; 03158 ast_queue_frame(sub->owner, &f); 03159 /* XXX This seriously needs to be fixed */ 03160 if (sub->next && sub->next->owner) { 03161 if (sub->owner->_state == 0) { 03162 f.frametype = AST_FRAME_DTMF_BEGIN; 03163 ast_queue_frame(sub->next->owner, &f); 03164 } 03165 f.frametype = AST_FRAME_DTMF_END; 03166 ast_queue_frame(sub->next->owner, &f); 03167 } 03168 } else { 03169 if (skinnydebug) 03170 ast_verbose("No owner: %s\n", l->name); 03171 } 03172 return 1; 03173 }
static int handle_line_state_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3607 of file chan_skinny.c.
References ast_mutex_lock(), ast_mutex_unlock(), skinny_req::data, devicelock, find_line_by_instance(), skinny_line::instance, skinny_line::label, letohl, skinny_data::line, LINE_STAT_RES_MESSAGE, line_stat_res_message::lineDirNumber, line_stat_res_message::lineDisplayName, line_stat_res_message::lineNumber, line_state_req_message::lineNumber, skinny_data::linestat, skinny_line::name, req_alloc(), s, and transmit_response().
Referenced by handle_message().
03608 { 03609 struct skinny_device *d = s->device; 03610 struct skinny_line *l; 03611 int instance; 03612 03613 instance = letohl(req->data.line.lineNumber); 03614 03615 ast_mutex_lock(&devicelock); 03616 03617 l = find_line_by_instance(d, instance); 03618 03619 if (!l) { 03620 return 0; 03621 } 03622 03623 ast_mutex_unlock(&devicelock); 03624 03625 if (!(req = req_alloc(sizeof(struct line_stat_res_message), LINE_STAT_RES_MESSAGE))) 03626 return -1; 03627 03628 req->data.linestat.lineNumber = letohl(instance); 03629 memcpy(req->data.linestat.lineDirNumber, l->name, 03630 sizeof(req->data.linestat.lineDirNumber)); 03631 memcpy(req->data.linestat.lineDisplayName, l->label, 03632 sizeof(req->data.linestat.lineDisplayName)); 03633 transmit_response(s,req); 03634 return 1; 03635 }
static int handle_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 4248 of file chan_skinny.c.
References ast_channel::_state, ALARM_MESSAGE, ast_log(), AST_STATE_UP, ast_verbose(), keypad_button_message::button, BUTTON_TEMPLATE_REQ_MESSAGE, keypad_button_message::callReference, CAPABILITIES_RES_MESSAGE, skinny_req::data, skinny_req::e, ENBLOC_CALL_MESSAGE, skinny_device::exten, find_subchannel_by_instance_reference(), free, handle_alarm_message(), handle_button_template_req_message(), handle_capabilities_res_message(), handle_enbloc_call_message(), handle_headset_status_message(), handle_ip_port_message(), handle_keep_alive_message(), handle_keypad_button_message(), handle_line_state_req_message(), handle_offhook_message(), handle_onhook_message(), handle_open_receive_channel_ack_message(), handle_register_available_lines_message(), handle_register_message(), handle_server_request_message(), handle_soft_key_event_message(), handle_soft_key_set_req_message(), handle_soft_key_template_req_message(), handle_speed_dial_stat_req_message(), handle_stimulus_message(), handle_time_date_req_message(), handle_unregister_message(), handle_version_req_message(), HEADSET_STATUS_MESSAGE, IP_PORT_MESSAGE, KEEP_ALIVE_MESSAGE, skinny_data::keypad, KEYPAD_BUTTON_MESSAGE, len(), letohl, LINE_STATE_REQ_MESSAGE, keypad_button_message::lineInstance, LOG_WARNING, register_message::name, OFFHOOK_MESSAGE, ONHOOK_MESSAGE, OPEN_RECEIVE_CHANNEL_ACK_MESSAGE, skinny_subchannel::owner, skinny_data::reg, REGISTER_AVAILABLE_LINES_MESSAGE, REGISTER_MESSAGE, s, SERVER_REQUEST_MESSAGE, skinnydebug, SOFT_KEY_EVENT_MESSAGE, SOFT_KEY_SET_REQ_MESSAGE, SOFT_KEY_TEMPLATE_REQ_MESSAGE, SPEED_DIAL_STAT_REQ_MESSAGE, STIMULUS_MESSAGE, TIME_DATE_REQ_MESSAGE, UNREGISTER_MESSAGE, and VERSION_REQ_MESSAGE.
Referenced by skinny_session().
04249 { 04250 int res = 0; 04251 struct skinny_device *d = s->device; 04252 struct skinny_subchannel *sub; 04253 int lineInstance; 04254 int callReference; 04255 04256 if ((!s->device) && (letohl(req->e) != REGISTER_MESSAGE && letohl(req->e) != ALARM_MESSAGE)) { 04257 ast_log(LOG_WARNING, "Client sent message #%d without first registering.\n", req->e); 04258 free(req); 04259 return 0; 04260 } 04261 04262 switch(letohl(req->e)) { 04263 case KEEP_ALIVE_MESSAGE: 04264 res = handle_keep_alive_message(req, s); 04265 break; 04266 case REGISTER_MESSAGE: 04267 if (skinnydebug) 04268 ast_verbose("Device %s is attempting to register\n", req->data.reg.name); 04269 04270 res = handle_register_message(req, s); 04271 break; 04272 case IP_PORT_MESSAGE: 04273 res = handle_ip_port_message(req, s); 04274 break; 04275 case KEYPAD_BUTTON_MESSAGE: 04276 if (skinnydebug) 04277 ast_verbose("Collected digit: [%d]\n", letohl(req->data.keypad.button)); 04278 04279 lineInstance = letohl(req->data.keypad.lineInstance); 04280 callReference = letohl(req->data.keypad.callReference); 04281 04282 sub = find_subchannel_by_instance_reference(d, lineInstance, callReference); 04283 04284 if (sub && (sub->owner && sub->owner->_state < AST_STATE_UP)) { 04285 char dgt; 04286 int digit = letohl(req->data.keypad.button); 04287 size_t len; 04288 04289 if (digit == 14) { 04290 dgt = '*'; 04291 } else if (digit == 15) { 04292 dgt = '#'; 04293 } else if (digit >= 0 && digit <= 9) { 04294 dgt = '0' + digit; 04295 } else { 04296 /* digit=10-13 (A,B,C,D ?), or 04297 * digit is bad value 04298 * 04299 * probably should not end up here, but set 04300 * value for backward compatibility, and log 04301 * a warning. 04302 */ 04303 dgt = '0' + digit; 04304 ast_log(LOG_WARNING, "Unsupported digit %d\n", digit); 04305 } 04306 04307 len = strlen(d->exten); 04308 if (len < sizeof(d->exten) - 1) { 04309 d->exten[len] = dgt; 04310 d->exten[len+1] = '\0'; 04311 } else { 04312 ast_log(LOG_WARNING, "Dropping digit with value %d because digit queue is full\n", dgt); 04313 } 04314 } else 04315 res = handle_keypad_button_message(req, s); 04316 break; 04317 case ENBLOC_CALL_MESSAGE: 04318 res = handle_enbloc_call_message(req, s); 04319 break; 04320 case STIMULUS_MESSAGE: 04321 res = handle_stimulus_message(req, s); 04322 break; 04323 case OFFHOOK_MESSAGE: 04324 res = handle_offhook_message(req, s); 04325 break; 04326 case ONHOOK_MESSAGE: 04327 res = handle_onhook_message(req, s); 04328 break; 04329 case CAPABILITIES_RES_MESSAGE: 04330 if (skinnydebug) 04331 ast_verbose("Received CapabilitiesRes\n"); 04332 04333 res = handle_capabilities_res_message(req, s); 04334 break; 04335 case SPEED_DIAL_STAT_REQ_MESSAGE: 04336 if (skinnydebug) 04337 ast_verbose("Received SpeedDialStatRequest\n"); 04338 04339 res = handle_speed_dial_stat_req_message(req, s); 04340 break; 04341 case LINE_STATE_REQ_MESSAGE: 04342 if (skinnydebug) 04343 ast_verbose("Received LineStatRequest\n"); 04344 res = handle_line_state_req_message(req, s); 04345 break; 04346 case TIME_DATE_REQ_MESSAGE: 04347 if (skinnydebug) 04348 ast_verbose("Received Time/Date Request\n"); 04349 04350 res = handle_time_date_req_message(req, s); 04351 break; 04352 case BUTTON_TEMPLATE_REQ_MESSAGE: 04353 if (skinnydebug) 04354 ast_verbose("Buttontemplate requested\n"); 04355 04356 res = handle_button_template_req_message(req, s); 04357 break; 04358 case VERSION_REQ_MESSAGE: 04359 if (skinnydebug) 04360 ast_verbose("Version Request\n"); 04361 04362 res = handle_version_req_message(req, s); 04363 break; 04364 case SERVER_REQUEST_MESSAGE: 04365 if (skinnydebug) 04366 ast_verbose("Received Server Request\n"); 04367 04368 res = handle_server_request_message(req, s); 04369 break; 04370 case ALARM_MESSAGE: 04371 res = handle_alarm_message(req, s); 04372 break; 04373 case OPEN_RECEIVE_CHANNEL_ACK_MESSAGE: 04374 if (skinnydebug) 04375 ast_verbose("Received Open Receive Channel Ack\n"); 04376 04377 res = handle_open_receive_channel_ack_message(req, s); 04378 break; 04379 case SOFT_KEY_SET_REQ_MESSAGE: 04380 if (skinnydebug) 04381 ast_verbose("Received SoftKeySetReq\n"); 04382 04383 res = handle_soft_key_set_req_message(req, s); 04384 break; 04385 case SOFT_KEY_EVENT_MESSAGE: 04386 res = handle_soft_key_event_message(req, s); 04387 break; 04388 case UNREGISTER_MESSAGE: 04389 if (skinnydebug) 04390 ast_verbose("Received Unregister Request\n"); 04391 04392 res = handle_unregister_message(req, s); 04393 break; 04394 case SOFT_KEY_TEMPLATE_REQ_MESSAGE: 04395 if (skinnydebug) 04396 ast_verbose("Received SoftKey Template Request\n"); 04397 04398 res = handle_soft_key_template_req_message(req, s); 04399 break; 04400 case HEADSET_STATUS_MESSAGE: 04401 res = handle_headset_status_message(req, s); 04402 break; 04403 case REGISTER_AVAILABLE_LINES_MESSAGE: 04404 res = handle_register_available_lines_message(req, s); 04405 break; 04406 default: 04407 if (skinnydebug) 04408 ast_verbose("RECEIVED UNKNOWN MESSAGE TYPE: %x\n", letohl(req->e)); 04409 break; 04410 } 04411 if (res >= 0 && req) 04412 free(req); 04413 return res; 04414 }
static int handle_offhook_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3414 of file chan_skinny.c.
References AST_CONTROL_ANSWER, ast_hangup(), ast_log(), ast_pthread_create, ast_queue_control(), ast_setstate(), AST_STATE_DOWN, AST_STATE_UP, ast_verbose(), skinny_subchannel::callid, skinny_req::data, errno, find_line_by_instance(), find_subchannel_by_instance_reference(), skinny_line::hookstate, skinny_line::instance, KEYDEF_CONNECTED, KEYDEF_OFFHOOK, skinny_device::lastcallreference, skinny_device::lastlineinstance, letohl, LOG_DEBUG, LOG_WARNING, skinny_device::name, skinny_line::name, ast_channel::name, skinny_data::offhook, skinny_subchannel::onhold, skinny_subchannel::outgoing, skinny_subchannel::owner, skinny_subchannel::parent, s, SKINNY_CONNECTED, SKINNY_DIALTONE, SKINNY_LAMP_ON, skinny_new(), SKINNY_OFFHOOK, SKINNY_RING_OFF, SKINNY_SILENCE, skinny_ss(), skinnydebug, start_rtp(), STIMULUS_LINE, t, ast_channel::tech_pvt, transmit_callstate(), transmit_displaymessage(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), transmit_tone(), offhook_message::unknown1, and offhook_message::unknown2.
Referenced by handle_message().
03415 { 03416 struct skinny_device *d = s->device; 03417 struct skinny_line *l; 03418 struct skinny_subchannel *sub; 03419 struct ast_channel *c; 03420 pthread_t t; 03421 int unknown1; 03422 int unknown2; 03423 03424 unknown1 = letohl(req->data.offhook.unknown1); 03425 unknown2 = letohl(req->data.offhook.unknown2); 03426 03427 sub = find_subchannel_by_instance_reference(d, d->lastlineinstance, d->lastcallreference); 03428 03429 if (!sub) { 03430 l = find_line_by_instance(d, d->lastlineinstance); 03431 if (!l) { 03432 return 0; 03433 } 03434 } else { 03435 l = sub->parent; 03436 } 03437 03438 transmit_ringer_mode(s, SKINNY_RING_OFF); 03439 l->hookstate = SKINNY_OFFHOOK; 03440 03441 if (sub && sub->onhold) { 03442 return 1; 03443 } 03444 03445 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_ON); 03446 03447 if (sub && sub->outgoing) { 03448 /* We're answering a ringing call */ 03449 ast_queue_control(sub->owner, AST_CONTROL_ANSWER); 03450 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03451 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 03452 transmit_callstate(s, l->instance, SKINNY_CONNECTED, sub->callid); 03453 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_CONNECTED); 03454 start_rtp(sub); 03455 ast_setstate(sub->owner, AST_STATE_UP); 03456 } else { 03457 if (sub && sub->owner) { 03458 ast_log(LOG_DEBUG, "Current sub [%s] already has owner\n", sub->owner->name); 03459 } else { 03460 c = skinny_new(l, AST_STATE_DOWN); 03461 if(c) { 03462 sub = c->tech_pvt; 03463 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03464 if (skinnydebug) 03465 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 03466 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 03467 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 03468 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_OFFHOOK); 03469 03470 /* start the switch thread */ 03471 if (ast_pthread_create(&t, NULL, skinny_ss, c)) { 03472 ast_log(LOG_WARNING, "Unable to create switch thread: %s\n", strerror(errno)); 03473 ast_hangup(c); 03474 } 03475 } else { 03476 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 03477 } 03478 } 03479 } 03480 return 1; 03481 }
static int handle_onhook_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3483 of file chan_skinny.c.
References skinny_subchannel::alreadygone, ast_log(), ast_queue_hangup(), ast_verbose(), attempt_transfer(), skinny_subchannel::callid, skinny_subchannel::cxmode, skinny_req::data, do_housekeeping(), find_subchannel_by_instance_reference(), skinny_line::hookstate, skinny_line::instance, skinny_device::lastcallreference, skinny_device::lastlineinstance, letohl, LOG_WARNING, skinny_device::name, skinny_line::name, skinny_subchannel::next, skinny_subchannel::onhold, skinny_data::onhook, skinny_subchannel::outgoing, skinny_subchannel::owner, skinny_subchannel::parent, skinny_subchannel::rtp, s, SKINNY_CX_RECVONLY, SKINNY_ONHOOK, skinnydebug, skinny_line::transfer, transmit_callstate(), onhook_message::unknown1, and onhook_message::unknown2.
Referenced by handle_message().
03484 { 03485 struct skinny_device *d = s->device; 03486 struct skinny_line *l; 03487 struct skinny_subchannel *sub; 03488 int unknown1; 03489 int unknown2; 03490 03491 unknown1 = letohl(req->data.onhook.unknown1); 03492 unknown2 = letohl(req->data.onhook.unknown2); 03493 03494 sub = find_subchannel_by_instance_reference(d, d->lastlineinstance, d->lastcallreference); 03495 03496 if (!sub) { 03497 return 0; 03498 } 03499 l = sub->parent; 03500 03501 if (l->hookstate == SKINNY_ONHOOK) { 03502 /* Something else already put us back on hook */ 03503 return 0; 03504 } 03505 l->hookstate = SKINNY_ONHOOK; 03506 03507 if (sub->onhold) { 03508 return 0; 03509 } 03510 03511 sub->cxmode = SKINNY_CX_RECVONLY; 03512 transmit_callstate(s, l->instance, l->hookstate, sub->callid); 03513 if (skinnydebug) 03514 ast_verbose("Skinny %s@%s went on hook\n", l->name, d->name); 03515 if (l->transfer && (sub->owner && sub->next && sub->next->owner) && ((!sub->outgoing) || (sub->next && !sub->next->outgoing))) { 03516 /* We're allowed to transfer, we have two active calls and 03517 we made at least one of the calls. Let's try and transfer */ 03518 03519 #if 0 03520 if ((res = attempt_transfer(p)) < 0) { 03521 if (sub->next && sub->next->owner) { 03522 sub->next->alreadygone = 1; 03523 ast_queue_hangup(sub->next->owner,1); 03524 } 03525 } else if (res) { 03526 ast_log(LOG_WARNING, "Transfer attempt failed\n"); 03527 return 0; 03528 } 03529 #endif 03530 } else { 03531 /* Hangup the current call */ 03532 /* If there is another active call, skinny_hangup will ring the phone with the other call */ 03533 if (sub->owner) { 03534 sub->alreadygone = 1; 03535 ast_queue_hangup(sub->owner); 03536 } else { 03537 ast_log(LOG_WARNING, "Skinny(%s@%s-%d) channel already destroyed\n", 03538 l->name, d->name, sub->callid); 03539 } 03540 } 03541 if ((l->hookstate == SKINNY_ONHOOK) && (sub->next && !sub->next->rtp)) { 03542 do_housekeeping(s); 03543 } 03544 return 1; 03545 }
static int handle_open_receive_channel_ack_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3805 of file chan_skinny.c.
References ast_best_codec(), ast_codec_pref_getsize(), ast_inet_ntoa(), ast_log(), ast_rtp_get_us(), ast_rtp_set_peer(), ast_verbose(), media_qualifier::bitRate, ast_format_list::bits, skinny_subchannel::callid, skinny_line::capability, codec_ast2skinny(), start_media_transmission_message::conferenceId, ast_format_list::cur_ms, skinny_req::data, find_subchannel_by_reference(), htolel, open_receive_channel_ack_message::ipAddr, letohl, LOG_ERROR, skinny_data::openreceivechannelack, skinny_device::ourip, media_qualifier::packets, start_media_transmission_message::packetSize, skinny_subchannel::parent, open_receive_channel_ack_message::passThruId, start_media_transmission_message::passThruPartyId, start_media_transmission_message::payloadType, open_receive_channel_ack_message::port, media_qualifier::precedence, skinny_line::prefs, start_media_transmission_message::qualifier, start_media_transmission_message::remoteIp, start_media_transmission_message::remotePort, req_alloc(), skinny_subchannel::rtp, s, skinnydebug, START_MEDIA_TRANSMISSION_MESSAGE, skinny_data::startmedia, open_receive_channel_ack_message::status, transmit_response(), and media_qualifier::vad.
Referenced by handle_message().
03806 { 03807 struct skinny_device *d = s->device; 03808 struct skinny_line *l; 03809 struct skinny_subchannel *sub; 03810 struct ast_format_list fmt; 03811 struct sockaddr_in sin; 03812 struct sockaddr_in us; 03813 uint32_t addr; 03814 int port; 03815 int status; 03816 int passthruid; 03817 03818 status = letohl(req->data.openreceivechannelack.status); 03819 if (status) { 03820 ast_log(LOG_ERROR, "Open Receive Channel Failure\n"); 03821 return 0; 03822 } 03823 addr = letohl(req->data.openreceivechannelack.ipAddr); 03824 port = letohl(req->data.openreceivechannelack.port); 03825 passthruid = letohl(req->data.openreceivechannelack.passThruId); 03826 03827 sin.sin_family = AF_INET; 03828 sin.sin_addr.s_addr = addr; 03829 sin.sin_port = htons(port); 03830 03831 sub = find_subchannel_by_reference(d, passthruid); 03832 03833 if (!sub) 03834 return 0; 03835 03836 l = sub->parent; 03837 03838 if (sub->rtp) { 03839 ast_rtp_set_peer(sub->rtp, &sin); 03840 ast_rtp_get_us(sub->rtp, &us); 03841 } else { 03842 ast_log(LOG_ERROR, "No RTP structure, this is very bad\n"); 03843 return 0; 03844 } 03845 03846 if (skinnydebug) { 03847 ast_verbose("ipaddr = %s:%d\n", ast_inet_ntoa(sin.sin_addr), ntohs(sin.sin_port)); 03848 ast_verbose("ourip = %s:%d\n", ast_inet_ntoa(d->ourip), ntohs(us.sin_port)); 03849 } 03850 03851 if (!(req = req_alloc(sizeof(struct start_media_transmission_message), START_MEDIA_TRANSMISSION_MESSAGE))) 03852 return -1; 03853 03854 fmt = ast_codec_pref_getsize(&l->prefs, ast_best_codec(l->capability)); 03855 03856 if (skinnydebug) 03857 ast_verbose("Setting payloadType to '%d' (%d ms)\n", fmt.bits, fmt.cur_ms); 03858 03859 req->data.startmedia.conferenceId = htolel(sub->callid); 03860 req->data.startmedia.passThruPartyId = htolel(sub->callid); 03861 req->data.startmedia.remoteIp = htolel(d->ourip.s_addr); 03862 req->data.startmedia.remotePort = htolel(ntohs(us.sin_port)); 03863 req->data.startmedia.packetSize = htolel(fmt.cur_ms); 03864 req->data.startmedia.payloadType = htolel(codec_ast2skinny(fmt.bits)); 03865 req->data.startmedia.qualifier.precedence = htolel(127); 03866 req->data.startmedia.qualifier.vad = htolel(0); 03867 req->data.startmedia.qualifier.packets = htolel(0); 03868 req->data.startmedia.qualifier.bitRate = htolel(0); 03869 transmit_response(s, req); 03870 03871 return 1; 03872 }
static int handle_register_available_lines_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 4242 of file chan_skinny.c.
Referenced by handle_message().
04243 { 04244 /* XXX I have no clue what this is for, but my phone was sending it, so... */ 04245 return 1; 04246 }
static int handle_register_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3056 of file chan_skinny.c.
References ast_atomic_fetchadd_int(), ast_log(), ast_verbose(), CAPABILITIES_REQ_MESSAGE, skinny_req::data, date_format, register_ack_message::dateTemplate, register_rej_message::errMsg, htolel, keep_alive, register_ack_message::keepAlive, LOG_ERROR, register_message::name, name, option_verbose, skinny_data::reg, skinny_data::regack, REGISTER_ACK_MESSAGE, REGISTER_REJ_MESSAGE, skinny_data::regrej, req_alloc(), register_ack_message::res, skinny_req::res, register_ack_message::res2, s, register_ack_message::secondaryKeepAlive, skinny_register(), skinnydebug, transmit_response(), unauth_sessions, and VERBOSE_PREFIX_3.
Referenced by handle_message().
03057 { 03058 char name[16]; 03059 int res; 03060 03061 memcpy(&name, req->data.reg.name, sizeof(name)); 03062 03063 res = skinny_register(req, s); 03064 if (!res) { 03065 ast_log(LOG_ERROR, "Rejecting Device %s: Device not found\n", name); 03066 if (!(req = req_alloc(sizeof(struct register_rej_message), REGISTER_REJ_MESSAGE))) 03067 return -1; 03068 03069 snprintf(req->data.regrej.errMsg, sizeof(req->data.regrej.errMsg), "No Authority: %s", name); 03070 transmit_response(s, req); 03071 return 0; 03072 } 03073 ast_atomic_fetchadd_int(&unauth_sessions, -1); 03074 if (option_verbose > 2) 03075 ast_verbose(VERBOSE_PREFIX_3 "Device '%s' successfully registered\n", name); 03076 03077 if (!(req = req_alloc(sizeof(struct register_ack_message), REGISTER_ACK_MESSAGE))) 03078 return -1; 03079 03080 req->data.regack.res[0] = '0'; 03081 req->data.regack.res[1] = '\0'; 03082 req->data.regack.keepAlive = htolel(keep_alive); 03083 memcpy(req->data.regack.dateTemplate, date_format, sizeof(req->data.regack.dateTemplate)); 03084 req->data.regack.res2[0] = '0'; 03085 req->data.regack.res2[1] = '\0'; 03086 req->data.regack.secondaryKeepAlive = htolel(keep_alive); 03087 transmit_response(s, req); 03088 if (skinnydebug) 03089 ast_verbose("Requesting capabilities\n"); 03090 03091 if (!(req = req_alloc(0, CAPABILITIES_REQ_MESSAGE))) 03092 return -1; 03093 03094 transmit_response(s, req); 03095 03096 return res; 03097 }
static int handle_server_request_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3782 of file chan_skinny.c.
References skinny_req::data, htolel, ourhost, skinny_device::ourip, ourport, req_alloc(), s, server_res_message::server, SERVER_RES_MESSAGE, server_res_message::serverIpAddr, server_res_message::serverListenPort, server_identifier::serverName, skinny_data::serverres, and transmit_response().
Referenced by handle_message().
03783 { 03784 struct skinny_device *d = s->device; 03785 if (!(req = req_alloc(sizeof(struct server_res_message), SERVER_RES_MESSAGE))) 03786 return -1; 03787 03788 memcpy(req->data.serverres.server[0].serverName, ourhost, 03789 sizeof(req->data.serverres.server[0].serverName)); 03790 req->data.serverres.serverListenPort[0] = htolel(ourport); 03791 req->data.serverres.serverIpAddr[0] = htolel(d->ourip.s_addr); 03792 transmit_response(s, req); 03793 return 1; 03794 }
static int handle_soft_key_event_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3956 of file chan_skinny.c.
References skinny_subchannel::alreadygone, AST_CONTROL_ANSWER, ast_copy_string(), ast_hangup(), ast_ignore_pattern(), ast_log(), ast_pthread_create, ast_queue_control(), ast_queue_hangup(), ast_setstate(), AST_STATE_DOWN, AST_STATE_UP, ast_verbose(), attempt_transfer(), skinny_subchannel::callid, soft_key_event_message::callreference, ast_channel::context, skinny_subchannel::cxmode, skinny_req::data, skinny_line::dnd, do_housekeeping(), errno, ast_channel::exten, find_line_by_instance(), find_subchannel_by_instance_reference(), skinny_line::hookstate, skinny_line::instance, soft_key_event_message::instance, KEYDEF_CONNECTED, KEYDEF_OFFHOOK, KEYDEF_RINGOUT, skinny_device::lastcallreference, skinny_device::lastlineinstance, skinny_line::lastnumberdialed, letohl, LOG_WARNING, skinny_device::name, skinny_line::name, skinny_subchannel::next, skinny_subchannel::onhold, option_verbose, skinny_subchannel::outgoing, skinny_subchannel::owner, skinny_subchannel::rtp, s, SKINNY_CONNECTED, SKINNY_CX_RECVONLY, SKINNY_DIALTONE, skinny_hold(), SKINNY_LAMP_OFF, SKINNY_LAMP_ON, skinny_new(), skinny_newcall(), SKINNY_OFFHOOK, SKINNY_ONHOOK, SKINNY_RING_OFF, SKINNY_SILENCE, SKINNY_SPEAKERON, skinny_ss(), skinny_unhold(), skinnydebug, SOFTKEY_ANSWER, SOFTKEY_BKSPC, SOFTKEY_CFWDALL, SOFTKEY_CFWDBUSY, SOFTKEY_CFWDNOANSWER, SOFTKEY_CONFRN, SOFTKEY_ENDCALL, SOFTKEY_GPICKUP, SOFTKEY_HOLD, SOFTKEY_INFO, SOFTKEY_JOIN, SOFTKEY_MEETME, SOFTKEY_NEWCALL, SOFTKEY_NONE, SOFTKEY_PARK, SOFTKEY_PICKUP, SOFTKEY_REDIAL, SOFTKEY_RESUME, SOFTKEY_TRNSFER, soft_key_event_message::softKeyEvent, skinny_data::softkeyeventmessage, start_rtp(), STIMULUS_FORWARDALL, STIMULUS_LINE, t, ast_channel::tech_pvt, skinny_line::transfer, transmit_callstate(), transmit_displaymessage(), transmit_displaynotify(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), transmit_speaker_mode(), transmit_tone(), and VERBOSE_PREFIX_3.
Referenced by handle_message().
03957 { 03958 struct skinny_device *d = s->device; 03959 struct skinny_line *l; 03960 struct skinny_subchannel *sub = NULL; 03961 struct ast_channel *c; 03962 pthread_t t; 03963 int event; 03964 int instance; 03965 int callreference; 03966 03967 event = letohl(req->data.softkeyeventmessage.softKeyEvent); 03968 instance = letohl(req->data.softkeyeventmessage.instance); 03969 callreference = letohl(req->data.softkeyeventmessage.callreference); 03970 03971 if (instance) { 03972 l = find_line_by_instance(d, instance); 03973 if (callreference) { 03974 sub = find_subchannel_by_instance_reference(d, instance, callreference); 03975 } else { 03976 sub = find_subchannel_by_instance_reference(d, instance, d->lastcallreference); 03977 } 03978 } else { 03979 l = find_line_by_instance(d, d->lastlineinstance); 03980 } 03981 03982 if (!l) { 03983 if (skinnydebug) 03984 ast_verbose("Received Softkey Event: %d(%d/%d)\n", event, instance, callreference); 03985 return 0; 03986 } 03987 03988 switch(event) { 03989 case SOFTKEY_NONE: 03990 if (skinnydebug) 03991 ast_verbose("Received Softkey Event: None(%d/%d)\n", instance, callreference); 03992 break; 03993 case SOFTKEY_REDIAL: 03994 if (skinnydebug) 03995 ast_verbose("Received Softkey Event: Redial(%d/%d)\n", instance, callreference); 03996 03997 #if 0 03998 if (!sub || !sub->owner) { 03999 c = skinny_new(l, AST_STATE_DOWN); 04000 } else { 04001 c = sub->owner; 04002 } 04003 04004 if(!c) { 04005 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 04006 } else { 04007 sub = c->tech_pvt; 04008 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 04009 if (skinnydebug) 04010 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 04011 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 04012 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 04013 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_RINGOUT); 04014 04015 if (!ast_ignore_pattern(c->context, l->lastnumberdialed)) { 04016 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 04017 } 04018 ast_copy_string(c->exten, l->lastnumberdialed, sizeof(c->exten)); 04019 if (ast_pthread_create(&t, NULL, skinny_newcall, c)) { 04020 ast_log(LOG_WARNING, "Unable to create new call thread: %s\n", strerror(errno)); 04021 ast_hangup(c); 04022 } 04023 } 04024 #endif 04025 break; 04026 case SOFTKEY_NEWCALL: /* Actually the DIAL softkey */ 04027 if (skinnydebug) 04028 ast_verbose("Received Softkey Event: New Call(%d/%d)\n", instance, callreference); 04029 04030 if (!sub || !sub->owner) { 04031 c = skinny_new(l, AST_STATE_DOWN); 04032 } else { 04033 c = sub->owner; 04034 } 04035 04036 if (!c) { 04037 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 04038 } else { 04039 sub = c->tech_pvt; 04040 if (l->hookstate == SKINNY_ONHOOK) { 04041 l->hookstate = SKINNY_OFFHOOK; 04042 transmit_speaker_mode(s, SKINNY_SPEAKERON); 04043 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 04044 } 04045 04046 if (skinnydebug) 04047 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 04048 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 04049 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 04050 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_OFFHOOK); 04051 04052 /* start the switch thread */ 04053 if (ast_pthread_create(&t, NULL, skinny_ss, c)) { 04054 ast_log(LOG_WARNING, "Unable to create switch thread: %s\n", strerror(errno)); 04055 ast_hangup(c); 04056 } 04057 } 04058 break; 04059 case SOFTKEY_HOLD: 04060 if (skinnydebug) 04061 ast_verbose("Received Softkey Event: Hold(%d/%d)\n", instance, callreference); 04062 04063 if (sub) { 04064 if (sub->onhold) { 04065 skinny_unhold(sub); 04066 } else { 04067 skinny_hold(sub); 04068 } 04069 } 04070 04071 break; 04072 case SOFTKEY_TRNSFER: 04073 if (skinnydebug) 04074 ast_verbose("Received Softkey Event: Transfer(%d/%d)\n", instance, callreference); 04075 /* XXX figure out how to transfer */ 04076 break; 04077 case SOFTKEY_CFWDALL: 04078 if (skinnydebug) 04079 ast_verbose("Received Softkey Event: Forward All(%d/%d)\n", instance, callreference); 04080 04081 /* Do not disturb */ 04082 if (l->dnd != 0){ 04083 if (option_verbose > 2) 04084 ast_verbose(VERBOSE_PREFIX_3 "Disabling DND on %s@%s\n", l->name, d->name); 04085 l->dnd = 0; 04086 transmit_lamp_indication(s, STIMULUS_FORWARDALL, 1, SKINNY_LAMP_ON); 04087 transmit_displaynotify(s, "DnD disabled", 10); 04088 } else { 04089 if (option_verbose > 2) 04090 ast_verbose(VERBOSE_PREFIX_3 "Enabling DND on %s@%s\n", l->name, d->name); 04091 l->dnd = 1; 04092 transmit_lamp_indication(s, STIMULUS_FORWARDALL, 1, SKINNY_LAMP_OFF); 04093 transmit_displaynotify(s, "DnD enabled", 10); 04094 } 04095 break; 04096 case SOFTKEY_CFWDBUSY: 04097 if (skinnydebug) 04098 ast_verbose("Received Softkey Event: Forward Busy (%d/%d)\n", instance, callreference); 04099 break; 04100 case SOFTKEY_CFWDNOANSWER: 04101 if (skinnydebug) 04102 ast_verbose("Received Softkey Event: Forward No Answer (%d/%d)\n", instance, callreference); 04103 break; 04104 case SOFTKEY_BKSPC: 04105 if (skinnydebug) 04106 ast_verbose("Received Softkey Event: Backspace(%d/%d)\n", instance, callreference); 04107 break; 04108 case SOFTKEY_ENDCALL: 04109 if (skinnydebug) 04110 ast_verbose("Received Softkey Event: End Call(%d/%d)\n", instance, callreference); 04111 04112 if (l->hookstate == SKINNY_ONHOOK) { 04113 /* Something else already put us back on hook */ 04114 break; 04115 } 04116 if (sub) { 04117 sub->cxmode = SKINNY_CX_RECVONLY; 04118 l->hookstate = SKINNY_ONHOOK; 04119 transmit_callstate(s, l->instance, l->hookstate, sub->callid); 04120 if (skinnydebug) 04121 ast_verbose("Skinny %s@%s went on hook\n", l->name, d->name); 04122 if (l->transfer && (sub->owner && sub->next && sub->next->owner) && ((!sub->outgoing) || (sub->next && !sub->next->outgoing))) { 04123 /* We're allowed to transfer, we have two active calls and 04124 we made at least one of the calls. Let's try and transfer */ 04125 04126 #if 0 04127 if ((res = attempt_transfer(p)) < 0) { 04128 if (sub->next && sub->next->owner) { 04129 sub->next->alreadygone = 1; 04130 ast_queue_hangup(sub->next->owner, 1); 04131 } 04132 } else if (res) { 04133 ast_log(LOG_WARNING, "Transfer attempt failed\n"); 04134 break; 04135 } 04136 #endif 04137 } else { 04138 /* Hangup the current call */ 04139 /* If there is another active call, skinny_hangup will ring the phone with the other call */ 04140 if (sub->owner) { 04141 sub->alreadygone = 1; 04142 ast_queue_hangup(sub->owner); 04143 } else { 04144 ast_log(LOG_WARNING, "Skinny(%s@%s-%d) channel already destroyed\n", 04145 l->name, d->name, sub->callid); 04146 } 04147 } 04148 if ((l->hookstate == SKINNY_ONHOOK) && (sub->next && !sub->next->rtp)) { 04149 do_housekeeping(s); 04150 } 04151 } 04152 break; 04153 case SOFTKEY_RESUME: 04154 if (skinnydebug) 04155 ast_verbose("Received Softkey Event: Resume(%d/%d)\n", instance, callreference); 04156 break; 04157 case SOFTKEY_ANSWER: 04158 if (skinnydebug) 04159 ast_verbose("Received Softkey Event: Answer(%d/%d)\n", instance, callreference); 04160 04161 transmit_ringer_mode(s,SKINNY_RING_OFF); 04162 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_ON); 04163 04164 l->hookstate = SKINNY_OFFHOOK; 04165 04166 if (sub && sub->outgoing) { 04167 /* We're answering a ringing call */ 04168 ast_queue_control(sub->owner, AST_CONTROL_ANSWER); 04169 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 04170 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 04171 transmit_callstate(s, l->instance, SKINNY_CONNECTED, sub->callid); 04172 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_CONNECTED); 04173 start_rtp(sub); 04174 ast_setstate(sub->owner, AST_STATE_UP); 04175 } 04176 break; 04177 case SOFTKEY_INFO: 04178 if (skinnydebug) 04179 ast_verbose("Received Softkey Event: Info(%d/%d)\n", instance, callreference); 04180 break; 04181 case SOFTKEY_CONFRN: 04182 if (skinnydebug) 04183 ast_verbose("Received Softkey Event: Conference(%d/%d)\n", instance, callreference); 04184 /* XXX determine the best way to pull off a conference. Meetme? */ 04185 break; 04186 case SOFTKEY_PARK: 04187 if (skinnydebug) 04188 ast_verbose("Received Softkey Event: Park Call(%d/%d)\n", instance, callreference); 04189 /* XXX Park the call */ 04190 break; 04191 case SOFTKEY_JOIN: 04192 if (skinnydebug) 04193 ast_verbose("Received Softkey Event: Join(%d/%d)\n", instance, callreference); 04194 break; 04195 case SOFTKEY_MEETME: 04196 /* XXX How is this different from CONFRN? */ 04197 if (skinnydebug) 04198 ast_verbose("Received Softkey Event: Meetme(%d/%d)\n", instance, callreference); 04199 break; 04200 case SOFTKEY_PICKUP: 04201 if (skinnydebug) 04202 ast_verbose("Received Softkey Event: Pickup(%d/%d)\n", instance, callreference); 04203 break; 04204 case SOFTKEY_GPICKUP: 04205 if (skinnydebug) 04206 ast_verbose("Received Softkey Event: Group Pickup(%d/%d)\n", instance, callreference); 04207 break; 04208 default: 04209 if (skinnydebug) 04210 ast_verbose("Received unknown Softkey Event: %d(%d/%d)\n", event, instance, callreference); 04211 break; 04212 } 04213 return 1; 04214 }
static int handle_soft_key_set_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3924 of file chan_skinny.c.
References soft_key_definitions::count, skinny_req::data, soft_key_definitions::defaults, htolel, KEYDEF_ONHOOK, soft_key_definitions::mode, req_alloc(), s, soft_key_default_definitions, SOFT_KEY_SET_RES_MESSAGE, soft_key_template_default, soft_key_set_definition::softKeyInfoIndex, soft_key_set_res_message::softKeySetCount, soft_key_set_res_message::softKeySetDefinition, soft_key_set_res_message::softKeySetOffset, skinny_data::softkeysets, soft_key_set_res_message::totalSoftKeySetCount, transmit_response(), and transmit_selectsoftkeys().
Referenced by handle_message().
03925 { 03926 int i; 03927 int x; 03928 int y; 03929 const struct soft_key_definitions *softkeymode = soft_key_default_definitions; 03930 03931 if (!(req = req_alloc(sizeof(struct soft_key_set_res_message), SOFT_KEY_SET_RES_MESSAGE))) 03932 return -1; 03933 03934 req->data.softkeysets.softKeySetOffset = htolel(0); 03935 req->data.softkeysets.softKeySetCount = htolel(11); 03936 req->data.softkeysets.totalSoftKeySetCount = htolel(11); 03937 for (x = 0; x < sizeof(soft_key_default_definitions) / sizeof(struct soft_key_definitions); x++) { 03938 const uint8_t *defaults = softkeymode->defaults; 03939 /* XXX I wanted to get the size of the array dynamically, but that wasn't wanting to work. 03940 This will have to do for now. */ 03941 for (y = 0; y < softkeymode->count; y++) { 03942 for (i = 0; i < (sizeof(soft_key_template_default) / sizeof(struct soft_key_template_definition)); i++) { 03943 if (defaults[y] == i+1) { 03944 req->data.softkeysets.softKeySetDefinition[softkeymode->mode].softKeyTemplateIndex[y] = htolel(i+1); 03945 req->data.softkeysets.softKeySetDefinition[softkeymode->mode].softKeyInfoIndex[y] = htolel(i+301); 03946 } 03947 } 03948 } 03949 softkeymode++; 03950 } 03951 transmit_response(s,req); 03952 transmit_selectsoftkeys(s, 0, 0, KEYDEF_ONHOOK); 03953 return 1; 03954 }
static int handle_soft_key_template_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 4221 of file chan_skinny.c.
References skinny_req::data, htolel, req_alloc(), s, soft_key_template_default, SOFT_KEY_TEMPLATE_RES_MESSAGE, soft_key_template_res_message::softKeyCount, soft_key_template_res_message::softKeyOffset, skinny_data::softkeytemplate, soft_key_template_res_message::softKeyTemplateDefinition, soft_key_template_res_message::totalSoftKeyCount, and transmit_response().
Referenced by handle_message().
04222 { 04223 if (!(req = req_alloc(sizeof(struct soft_key_template_res_message), SOFT_KEY_TEMPLATE_RES_MESSAGE))) 04224 return -1; 04225 04226 req->data.softkeytemplate.softKeyOffset = htolel(0); 04227 req->data.softkeytemplate.softKeyCount = htolel(sizeof(soft_key_template_default) / sizeof(struct soft_key_template_definition)); 04228 req->data.softkeytemplate.totalSoftKeyCount = htolel(sizeof(soft_key_template_default) / sizeof(struct soft_key_template_definition)); 04229 memcpy(req->data.softkeytemplate.softKeyTemplateDefinition, 04230 soft_key_template_default, 04231 sizeof(soft_key_template_default)); 04232 transmit_response(s,req); 04233 return 1; 04234 }
static int handle_speed_dial_stat_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3582 of file chan_skinny.c.
References ast_copy_string(), skinny_req::data, skinny_speeddial::exten, find_speeddial_by_instance(), htolel, skinny_speeddial::instance, skinny_speeddial::label, letohl, req_alloc(), s, SPEED_DIAL_STAT_RES_MESSAGE, skinny_data::speeddial, speed_dial_stat_res_message::speedDialDirNumber, speed_dial_stat_res_message::speedDialDisplayName, speed_dial_stat_req_message::speedDialNumber, skinny_data::speeddialreq, and transmit_response().
Referenced by handle_message().
03583 { 03584 struct skinny_device *d = s->device; 03585 struct skinny_speeddial *sd; 03586 int instance; 03587 03588 instance = letohl(req->data.speeddialreq.speedDialNumber); 03589 03590 sd = find_speeddial_by_instance(d, instance); 03591 03592 if (!sd) { 03593 return 0; 03594 } 03595 03596 if (!(req = req_alloc(sizeof(struct speed_dial_stat_res_message), SPEED_DIAL_STAT_RES_MESSAGE))) 03597 return -1; 03598 03599 req->data.speeddialreq.speedDialNumber = htolel(instance); 03600 ast_copy_string(req->data.speeddial.speedDialDirNumber, sd->exten, sizeof(req->data.speeddial.speedDialDirNumber)); 03601 ast_copy_string(req->data.speeddial.speedDialDisplayName, sd->label, sizeof(req->data.speeddial.speedDialDisplayName)); 03602 03603 transmit_response(s, req); 03604 return 1; 03605 }
static int handle_stimulus_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3175 of file chan_skinny.c.
References AST_CONTROL_ANSWER, ast_copy_string(), ast_exists_extension(), ast_hangup(), ast_ignore_pattern(), ast_log(), ast_matchmore_extension(), ast_pthread_create, ast_queue_control(), ast_setstate(), AST_STATE_DOWN, AST_STATE_UP, ast_strlen_zero(), ast_verbose(), skinny_subchannel::callid, stimulus_message::callreference, skinny_line::cid_num, ast_channel::context, skinny_req::data, skinny_line::dnd, errno, ast_channel::exten, find_line_by_instance(), find_speeddial_by_instance(), find_subchannel_by_instance_reference(), skinny_line::hookstate, skinny_line::instance, KEYDEF_CONNECTED, KEYDEF_OFFHOOK, KEYDEF_RINGOUT, skinny_device::lastcallreference, skinny_device::lastlineinstance, skinny_line::lastnumberdialed, letohl, LOG_DEBUG, LOG_WARNING, ast_channel::name, skinny_device::name, skinny_line::name, skinny_subchannel::onhold, option_verbose, skinny_subchannel::outgoing, skinny_subchannel::owner, skinny_subchannel::parent, s, SKINNY_CONNECTED, SKINNY_DIALTONE, skinny_hold(), SKINNY_LAMP_OFF, SKINNY_LAMP_ON, skinny_new(), skinny_newcall(), SKINNY_OFFHOOK, SKINNY_ONHOOK, SKINNY_RING_OFF, SKINNY_SILENCE, SKINNY_SPEAKEROFF, SKINNY_SPEAKERON, skinny_ss(), skinny_unhold(), skinnydebug, start_rtp(), stimulus_message::stimulus, skinny_data::stimulus, STIMULUS_CALLPARK, STIMULUS_CONFERENCE, STIMULUS_DISPLAY, STIMULUS_FORWARDALL, STIMULUS_FORWARDBUSY, STIMULUS_FORWARDNOANSWER, STIMULUS_HOLD, STIMULUS_LINE, STIMULUS_REDIAL, STIMULUS_SPEEDDIAL, STIMULUS_TRANSFER, STIMULUS_VOICEMAIL, stimulus_message::stimulusInstance, t, ast_channel::tech_pvt, transmit_callstate(), transmit_displaymessage(), transmit_displaynotify(), transmit_displaypromptstatus(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), transmit_speaker_mode(), transmit_tone(), and VERBOSE_PREFIX_3.
Referenced by handle_message().
03176 { 03177 struct skinny_device *d = s->device; 03178 struct skinny_line *l; 03179 struct skinny_subchannel *sub; 03180 /*struct skinny_speeddial *sd;*/ 03181 struct ast_channel *c; 03182 pthread_t t; 03183 int event; 03184 int instance; 03185 int callreference; 03186 /*int res = 0;*/ 03187 03188 event = letohl(req->data.stimulus.stimulus); 03189 instance = letohl(req->data.stimulus.stimulusInstance); 03190 callreference = letohl(req->data.stimulus.callreference); 03191 if (skinnydebug) 03192 ast_verbose("callreference in handle_stimulus_message is '%d'\n", callreference); 03193 03194 /* Note that this call should be using the passed in instance and callreference */ 03195 sub = find_subchannel_by_instance_reference(d, d->lastlineinstance, d->lastcallreference); 03196 03197 if (!sub) { 03198 l = find_line_by_instance(d, d->lastlineinstance); 03199 if (!l) { 03200 return 0; 03201 } 03202 } else { 03203 l = sub->parent; 03204 } 03205 03206 switch(event) { 03207 case STIMULUS_REDIAL: 03208 if (skinnydebug) 03209 ast_verbose("Received Stimulus: Redial(%d/%d)\n", instance, callreference); 03210 03211 #if 0 03212 if (ast_strlen_zero(l->lastnumberdialed)) { 03213 ast_log(LOG_WARNING, "Attempted redial, but no previously dialed number found.\n"); 03214 l->hookstate = SKINNY_ONHOOK; 03215 transmit_speaker_mode(s, SKINNY_SPEAKEROFF); 03216 transmit_callstate(s, l->instance, SKINNY_ONHOOK, instance); 03217 break; 03218 } 03219 03220 c = skinny_new(l, AST_STATE_DOWN); 03221 if(!c) { 03222 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 03223 } else { 03224 sub = c->tech_pvt; 03225 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03226 if (skinnydebug) 03227 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 03228 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 03229 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 03230 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_RINGOUT); 03231 03232 if (!ast_ignore_pattern(c->context, l->lastnumberdialed)) { 03233 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 03234 } 03235 ast_copy_string(c->exten, l->lastnumberdialed, sizeof(c->exten)); 03236 if (ast_pthread_create(&t, NULL, skinny_newcall, c)) { 03237 ast_log(LOG_WARNING, "Unable to create new call thread: %s\n", strerror(errno)); 03238 ast_hangup(c); 03239 } 03240 } 03241 #endif 03242 break; 03243 case STIMULUS_SPEEDDIAL: 03244 if (skinnydebug) 03245 ast_verbose("Received Stimulus: SpeedDial(%d/%d)\n", instance, callreference); 03246 03247 #if 0 03248 if (!(sd = find_speeddial_by_instance(d, instance))) { 03249 return 0; 03250 } 03251 03252 if (ast_strlen_zero(l->lastnumberdialed)) { 03253 ast_log(LOG_WARNING, "Attempted redial, but no previously dialed number found.\n"); 03254 l->hookstate = SKINNY_ONHOOK; 03255 transmit_speaker_mode(s, SKINNY_SPEAKEROFF); 03256 transmit_callstate(s, l->instance, SKINNY_ONHOOK, instance); 03257 break; 03258 } 03259 03260 c = skinny_new(l, AST_STATE_DOWN); 03261 if(c) { 03262 sub = c->tech_pvt; 03263 l = sub->parent; 03264 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03265 if (skinnydebug) 03266 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 03267 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 03268 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 03269 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_RINGOUT); 03270 03271 if (!ast_ignore_pattern(c->context, sd->exten)) { 03272 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 03273 } 03274 if (ast_exists_extension(c, c->context, sd->exten, 1, l->cid_num)) { 03275 if (!ast_matchmore_extension(c, c->context, sd->exten, 1, l->cid_num)) { 03276 ast_copy_string(c->exten, sd->exten, sizeof(c->exten)); 03277 ast_copy_string(l->lastnumberdialed, sd->exten, sizeof(l->lastnumberdialed)); 03278 skinny_newcall(c); 03279 break; 03280 } 03281 } 03282 } else { 03283 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 03284 } 03285 #endif 03286 break; 03287 case STIMULUS_HOLD: 03288 if (skinnydebug) 03289 ast_verbose("Received Stimulus: Hold(%d/%d)\n", instance, callreference); 03290 03291 if (!sub) 03292 break; 03293 03294 if (sub->onhold) { 03295 skinny_unhold(sub); 03296 } else { 03297 skinny_hold(sub); 03298 } 03299 break; 03300 case STIMULUS_TRANSFER: 03301 if (skinnydebug) 03302 ast_verbose("Received Stimulus: Transfer(%d/%d)\n", instance, callreference); 03303 /* XXX figure out how to transfer */ 03304 break; 03305 case STIMULUS_CONFERENCE: 03306 if (skinnydebug) 03307 ast_verbose("Received Stimulus: Conference(%d/%d)\n", instance, callreference); 03308 /* XXX determine the best way to pull off a conference. Meetme? */ 03309 break; 03310 case STIMULUS_VOICEMAIL: 03311 if (skinnydebug) 03312 ast_verbose("Received Stimulus: Voicemail(%d/%d)\n", instance, callreference); 03313 /* XXX Find and dial voicemail extension */ 03314 break; 03315 case STIMULUS_CALLPARK: 03316 if (skinnydebug) 03317 ast_verbose("Received Stimulus: Park Call(%d/%d)\n", instance, callreference); 03318 /* XXX Park the call */ 03319 break; 03320 case STIMULUS_FORWARDALL: 03321 if (skinnydebug) 03322 ast_verbose("Received Stimulus: Forward All(%d/%d)\n", instance, callreference); 03323 /* Why is DND under FORWARDALL? */ 03324 /* Because it's the same thing. */ 03325 03326 /* Do not disturb */ 03327 if (l->dnd != 0){ 03328 if (option_verbose > 2) 03329 ast_verbose(VERBOSE_PREFIX_3 "Disabling DND on %s@%s\n", l->name, d->name); 03330 l->dnd = 0; 03331 transmit_lamp_indication(s, STIMULUS_FORWARDALL, 1, SKINNY_LAMP_ON); 03332 transmit_displaynotify(s, "DnD disabled", 10); 03333 } else { 03334 if (option_verbose > 2) 03335 ast_verbose(VERBOSE_PREFIX_3 "Enabling DND on %s@%s\n", l->name, d->name); 03336 l->dnd = 1; 03337 transmit_lamp_indication(s, STIMULUS_FORWARDALL, 1, SKINNY_LAMP_OFF); 03338 transmit_displaynotify(s, "DnD enabled", 10); 03339 } 03340 break; 03341 case STIMULUS_FORWARDBUSY: 03342 if (skinnydebug) 03343 ast_verbose("Received Stimulus: Forward Busy (%d/%d)\n", instance, callreference); 03344 break; 03345 case STIMULUS_FORWARDNOANSWER: 03346 if (skinnydebug) 03347 ast_verbose("Received Stimulus: Forward No Answer (%d/%d)\n", instance, callreference); 03348 break; 03349 case STIMULUS_DISPLAY: 03350 /* Not sure what this is */ 03351 if (skinnydebug) 03352 ast_verbose("Received Stimulus: Display(%d/%d)\n", instance, callreference); 03353 break; 03354 case STIMULUS_LINE: 03355 if (skinnydebug) 03356 ast_verbose("Received Stimulus: Line(%d/%d)\n", instance, callreference); 03357 03358 l = find_line_by_instance(s->device, instance); 03359 03360 if (!l) { 03361 return 0; 03362 } 03363 03364 /* turn the speaker on */ 03365 transmit_speaker_mode(s, SKINNY_SPEAKERON); 03366 transmit_ringer_mode(s, SKINNY_RING_OFF); 03367 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_ON); 03368 03369 l->hookstate = SKINNY_OFFHOOK; 03370 03371 if (sub && sub->outgoing) { 03372 /* We're answering a ringing call */ 03373 ast_queue_control(sub->owner, AST_CONTROL_ANSWER); 03374 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03375 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 03376 transmit_callstate(s, l->instance, SKINNY_CONNECTED, sub->callid); 03377 transmit_displaypromptstatus(s, "Connected", 0, l->instance, sub->callid); 03378 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_CONNECTED); 03379 start_rtp(sub); 03380 ast_setstate(sub->owner, AST_STATE_UP); 03381 } else { 03382 if (sub && sub->owner) { 03383 ast_log(LOG_DEBUG, "Current subchannel [%s] already has owner\n", sub->owner->name); 03384 } else { 03385 c = skinny_new(l, AST_STATE_DOWN); 03386 if(c) { 03387 sub = c->tech_pvt; 03388 transmit_callstate(s, l->instance, SKINNY_OFFHOOK, sub->callid); 03389 if (skinnydebug) 03390 ast_verbose("Attempting to Clear display on Skinny %s@%s\n", l->name, d->name); 03391 transmit_displaymessage(s, NULL, l->instance, sub->callid); /* clear display */ 03392 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 03393 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_OFFHOOK); 03394 03395 /* start the switch thread */ 03396 if (ast_pthread_create(&t, NULL, skinny_ss, c)) { 03397 ast_log(LOG_WARNING, "Unable to create switch thread: %s\n", strerror(errno)); 03398 ast_hangup(c); 03399 } 03400 } else { 03401 ast_log(LOG_WARNING, "Unable to create channel for %s@%s\n", l->name, d->name); 03402 } 03403 } 03404 } 03405 break; 03406 default: 03407 if (skinnydebug) 03408 ast_verbose("RECEIVED UNKNOWN STIMULUS: %d(%d/%d)\n", event, instance, callreference); 03409 break; 03410 } 03411 return 1; 03412 }
static int handle_time_date_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3637 of file chan_skinny.c.
References skinny_req::data, definetimedate_message::day, definetimedate_message::dayofweek, skinny_data::definetimedate, DEFINETIMEDATE_MESSAGE, definetimedate_message::hour, htolel, definetimedate_message::milliseconds, definetimedate_message::minute, definetimedate_message::month, req_alloc(), s, definetimedate_message::seconds, definetimedate_message::timestamp, transmit_response(), and definetimedate_message::year.
Referenced by do_housekeeping(), and handle_message().
03638 { 03639 time_t timer; 03640 struct tm *cmtime; 03641 03642 if (!(req = req_alloc(sizeof(struct definetimedate_message), DEFINETIMEDATE_MESSAGE))) 03643 return -1; 03644 03645 timer = time(NULL); 03646 cmtime = localtime(&timer); 03647 req->data.definetimedate.year = htolel(cmtime->tm_year+1900); 03648 req->data.definetimedate.month = htolel(cmtime->tm_mon+1); 03649 req->data.definetimedate.dayofweek = htolel(cmtime->tm_wday); 03650 req->data.definetimedate.day = htolel(cmtime->tm_mday); 03651 req->data.definetimedate.hour = htolel(cmtime->tm_hour); 03652 req->data.definetimedate.minute = htolel(cmtime->tm_min); 03653 req->data.definetimedate.seconds = htolel(cmtime->tm_sec); 03654 req->data.definetimedate.milliseconds = htolel(0); 03655 req->data.definetimedate.timestamp = htolel(timer); 03656 transmit_response(s, req); 03657 return 1; 03658 }
static int handle_unregister_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 4216 of file chan_skinny.c.
References s, and skinny_unregister().
Referenced by handle_message().
04217 { 04218 return skinny_unregister(req, s); 04219 }
static int handle_version_req_message | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 3771 of file chan_skinny.c.
References ast_copy_string(), skinny_req::data, req_alloc(), s, transmit_response(), version_res_message::version, skinny_data::version, skinny_device::version_id, and VERSION_RES_MESSAGE.
Referenced by handle_message().
03772 { 03773 struct skinny_device *d = s->device; 03774 if (!(req = req_alloc(sizeof(struct version_res_message), VERSION_RES_MESSAGE))) 03775 return -1; 03776 03777 ast_copy_string(req->data.version.version, d->version_id, sizeof(req->data.version.version)); 03778 transmit_response(s, req); 03779 return 1; 03780 }
static int load_module | ( | void | ) | [static] |
Definition at line 4986 of file chan_skinny.c.
References ast_channel_register(), ast_cli_register_multiple(), ast_log(), AST_MODULE_LOAD_DECLINE, ast_rtp_proto_register(), cli_skinny, htolel, io, io_context_create(), LOG_ERROR, LOG_WARNING, reload_config(), restart_monitor(), sched_context_create(), skinny_rtp, skinny_tech, and soft_key_template_default.
04987 { 04988 int res = 0; 04989 04990 for (; res < (sizeof(soft_key_template_default) / sizeof(soft_key_template_default[0])); res++) { 04991 soft_key_template_default[res].softKeyEvent = htolel(soft_key_template_default[res].softKeyEvent); 04992 } 04993 /* load and parse config */ 04994 res = reload_config(); 04995 if (res == -1) { 04996 return AST_MODULE_LOAD_DECLINE; 04997 } 04998 04999 /* Make sure we can register our skinny channel type */ 05000 if (ast_channel_register(&skinny_tech)) { 05001 ast_log(LOG_ERROR, "Unable to register channel class 'Skinny'\n"); 05002 return -1; 05003 } 05004 05005 ast_rtp_proto_register(&skinny_rtp); 05006 ast_cli_register_multiple(cli_skinny, sizeof(cli_skinny) / sizeof(struct ast_cli_entry)); 05007 sched = sched_context_create(); 05008 if (!sched) { 05009 ast_log(LOG_WARNING, "Unable to create schedule context\n"); 05010 } 05011 io = io_context_create(); 05012 if (!io) { 05013 ast_log(LOG_WARNING, "Unable to create I/O context\n"); 05014 } 05015 /* And start the monitor for the first time */ 05016 restart_monitor(); 05017 05018 return res; 05019 }
static int reload_config | ( | void | ) | [static] |
Definition at line 4764 of file chan_skinny.c.
References __ourip, accept_t, accept_thread(), ahp, ast_category_browse(), ast_config_destroy(), ast_config_load(), ast_gethostbyname(), ast_inet_ntoa(), ast_jb_read_conf(), ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_parse_allow_disallow(), ast_pthread_create_background, ast_variable_browse(), ast_verbose(), auth_limit, auth_timeout, bindaddr, build_device(), config, date_format, DEFAULT_AUTH_LIMIT, DEFAULT_AUTH_TIMEOUT, default_capability, default_jbconf, default_prefs, DEFAULT_SKINNY_BACKLOG, DEFAULT_SKINNY_PORT, devicelock, devices, errno, global_jbconf, hp, keep_alive, ast_variable::lineno, LOG_ERROR, LOG_NOTICE, LOG_WARNING, skinny_device::name, ast_variable::name, netlock, skinny_device::next, ast_variable::next, option_verbose, ourhost, ourport, skinnysock, ast_variable::value, VERBOSE_PREFIX_2, and VERBOSE_PREFIX_3.
04765 { 04766 int on = 1; 04767 struct ast_config *cfg; 04768 struct ast_variable *v; 04769 char *cat; 04770 struct skinny_device *d; 04771 int oldport = ntohs(bindaddr.sin_port); 04772 04773 if (gethostname(ourhost, sizeof(ourhost))) { 04774 ast_log(LOG_WARNING, "Unable to get hostname, Skinny disabled\n"); 04775 return 0; 04776 } 04777 cfg = ast_config_load(config); 04778 04779 /* We *must* have a config file otherwise stop immediately */ 04780 if (!cfg) { 04781 ast_log(LOG_NOTICE, "Unable to load config %s, Skinny disabled\n", config); 04782 return -1; 04783 } 04784 memset(&bindaddr, 0, sizeof(bindaddr)); 04785 memset(&default_prefs, 0, sizeof(default_prefs)); 04786 04787 /* Copy the default jb config over global_jbconf */ 04788 memcpy(&global_jbconf, &default_jbconf, sizeof(struct ast_jb_conf)); 04789 04790 /* load the general section */ 04791 v = ast_variable_browse(cfg, "general"); 04792 while (v) { 04793 /* handle jb conf */ 04794 if (!ast_jb_read_conf(&global_jbconf, v->name, v->value)) { 04795 v = v->next; 04796 continue; 04797 } 04798 04799 /* Create the interface list */ 04800 if (!strcasecmp(v->name, "bindaddr")) { 04801 if (!(hp = ast_gethostbyname(v->value, &ahp))) { 04802 ast_log(LOG_WARNING, "Invalid address: %s\n", v->value); 04803 } else { 04804 memcpy(&bindaddr.sin_addr, hp->h_addr, sizeof(bindaddr.sin_addr)); 04805 } 04806 } else if (!strcasecmp(v->name, "keepalive")) { 04807 keep_alive = atoi(v->value); 04808 } else if (!strcasecmp(v->name, "authtimeout")) { 04809 int timeout = atoi(v->value); 04810 04811 if (timeout < 1) { 04812 ast_log(LOG_WARNING, "Invalid authtimeout value '%s', using default value\n", v->value); 04813 auth_timeout = DEFAULT_AUTH_TIMEOUT; 04814 } else { 04815 auth_timeout = timeout; 04816 } 04817 } else if (!strcasecmp(v->name, "authlimit")) { 04818 int limit = atoi(v->value); 04819 04820 if (limit < 1) { 04821 ast_log(LOG_WARNING, "Invalid authlimit value '%s', using default value\n", v->value); 04822 auth_limit = DEFAULT_AUTH_LIMIT; 04823 } else { 04824 auth_limit = limit; 04825 } 04826 } else if (!strcasecmp(v->name, "dateformat")) { 04827 memcpy(date_format, v->value, sizeof(date_format)); 04828 } else if (!strcasecmp(v->name, "allow")) { 04829 ast_parse_allow_disallow(&default_prefs, &default_capability, v->value, 1); 04830 } else if (!strcasecmp(v->name, "disallow")) { 04831 ast_parse_allow_disallow(&default_prefs, &default_capability, v->value, 0); 04832 } else if (!strcasecmp(v->name, "bindport") || !strcasecmp(v->name, "port")) { 04833 if (sscanf(v->value, "%5d", &ourport) == 1) { 04834 bindaddr.sin_port = htons(ourport); 04835 } else { 04836 ast_log(LOG_WARNING, "Invalid bindport '%s' at line %d of %s\n", v->value, v->lineno, config); 04837 } 04838 if (!strcasecmp(v->name, "port")) { /*! \todo Remove 'port' option after 1.4 */ 04839 ast_log(LOG_WARNING, "Option 'port' at line %d of %s has been deprecated. Please use 'bindport' instead.\n", v->lineno, config); 04840 } 04841 } 04842 v = v->next; 04843 } 04844 04845 if (ntohl(bindaddr.sin_addr.s_addr)) { 04846 __ourip = bindaddr.sin_addr; 04847 } else { 04848 hp = ast_gethostbyname(ourhost, &ahp); 04849 if (!hp) { 04850 ast_log(LOG_WARNING, "Unable to get our IP address, Skinny disabled\n"); 04851 ast_config_destroy(cfg); 04852 return 0; 04853 } 04854 memcpy(&__ourip, hp->h_addr, sizeof(__ourip)); 04855 } 04856 if (!ntohs(bindaddr.sin_port)) { 04857 bindaddr.sin_port = ntohs(DEFAULT_SKINNY_PORT); 04858 } 04859 bindaddr.sin_family = AF_INET; 04860 04861 /* load the device sections */ 04862 cat = ast_category_browse(cfg, NULL); 04863 while(cat) { 04864 if (!strcasecmp(cat, "general")) { 04865 /* Nothing to do */ 04866 #if 0 04867 } else if (!strncasecmp(cat, "paging-", 7)) { 04868 p = build_paging_device(cat, ast_variable_browse(cfg, cat)); 04869 if (p) { 04870 } 04871 #endif 04872 } else { 04873 d = build_device(cat, ast_variable_browse(cfg, cat)); 04874 if (d) { 04875 if (option_verbose > 2) 04876 ast_verbose(VERBOSE_PREFIX_3 "Added device '%s'\n", d->name); 04877 ast_mutex_lock(&devicelock); 04878 d->next = devices; 04879 devices = d; 04880 ast_mutex_unlock(&devicelock); 04881 } 04882 } 04883 cat = ast_category_browse(cfg, cat); 04884 } 04885 ast_mutex_lock(&netlock); 04886 if ((skinnysock > -1) && (ntohs(bindaddr.sin_port) != oldport)) { 04887 close(skinnysock); 04888 skinnysock = -1; 04889 } 04890 if (skinnysock < 0) { 04891 skinnysock = socket(AF_INET, SOCK_STREAM, 0); 04892 if(setsockopt(skinnysock, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)) == -1) { 04893 ast_log(LOG_ERROR, "Set Socket Options failed: errno %d, %s\n", errno, strerror(errno)); 04894 ast_config_destroy(cfg); 04895 ast_mutex_unlock(&netlock); 04896 return 0; 04897 } 04898 if (skinnysock < 0) { 04899 ast_log(LOG_WARNING, "Unable to create Skinny socket: %s\n", strerror(errno)); 04900 } else { 04901 if (bind(skinnysock, (struct sockaddr *)&bindaddr, sizeof(bindaddr)) < 0) { 04902 ast_log(LOG_WARNING, "Failed to bind to %s:%d: %s\n", 04903 ast_inet_ntoa(bindaddr.sin_addr), ntohs(bindaddr.sin_port), 04904 strerror(errno)); 04905 close(skinnysock); 04906 skinnysock = -1; 04907 ast_config_destroy(cfg); 04908 ast_mutex_unlock(&netlock); 04909 return 0; 04910 } 04911 if (listen(skinnysock,DEFAULT_SKINNY_BACKLOG)) { 04912 ast_log(LOG_WARNING, "Failed to start listening to %s:%d: %s\n", 04913 ast_inet_ntoa(bindaddr.sin_addr), ntohs(bindaddr.sin_port), 04914 strerror(errno)); 04915 close(skinnysock); 04916 skinnysock = -1; 04917 ast_config_destroy(cfg); 04918 ast_mutex_unlock(&netlock); 04919 return 0; 04920 } 04921 if (option_verbose > 1) 04922 ast_verbose(VERBOSE_PREFIX_2 "Skinny listening on %s:%d\n", 04923 ast_inet_ntoa(bindaddr.sin_addr), ntohs(bindaddr.sin_port)); 04924 ast_pthread_create_background(&accept_t,NULL, accept_thread, NULL); 04925 } 04926 } 04927 ast_mutex_unlock(&netlock); 04928 ast_config_destroy(cfg); 04929 return 1; 04930 }
static struct skinny_req* req_alloc | ( | size_t | size, | |
int | response_message | |||
) | [static] |
Definition at line 1244 of file chan_skinny.c.
References ast_calloc, skinny_req::e, htolel, and skinny_req::len.
Referenced by handle_button_template_req_message(), handle_keep_alive_message(), handle_line_state_req_message(), handle_open_receive_channel_ack_message(), handle_register_message(), handle_server_request_message(), handle_soft_key_set_req_message(), handle_soft_key_template_req_message(), handle_speed_dial_stat_req_message(), handle_time_date_req_message(), handle_version_req_message(), skinny_hold(), skinny_reset_device(), skinny_unhold(), transmit_callinfo(), transmit_callstate(), transmit_connect(), transmit_dialednumber(), transmit_displaymessage(), transmit_displaynotify(), transmit_displaypromptstatus(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), transmit_speaker_mode(), and transmit_tone().
01245 { 01246 struct skinny_req *req; 01247 01248 if (!(req = ast_calloc(1, skinny_header_size + size + 4))) 01249 return NULL; 01250 01251 req->len = htolel(size+4); 01252 req->e = htolel(response_message); 01253 01254 return req; 01255 }
static int restart_monitor | ( | void | ) | [static] |
Definition at line 4700 of file chan_skinny.c.
References ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_pthread_create_background, AST_PTHREADT_NULL, AST_PTHREADT_STOP, do_monitor(), LOG_ERROR, LOG_WARNING, monitor_thread, and monlock.
04701 { 04702 /* If we're supposed to be stopped -- stay stopped */ 04703 if (monitor_thread == AST_PTHREADT_STOP) 04704 return 0; 04705 04706 ast_mutex_lock(&monlock); 04707 if (monitor_thread == pthread_self()) { 04708 ast_mutex_unlock(&monlock); 04709 ast_log(LOG_WARNING, "Cannot kill myself\n"); 04710 return -1; 04711 } 04712 if (monitor_thread != AST_PTHREADT_NULL) { 04713 /* Wake up the thread */ 04714 pthread_kill(monitor_thread, SIGURG); 04715 } else { 04716 /* Start a new monitor */ 04717 if (ast_pthread_create_background(&monitor_thread, NULL, do_monitor, NULL) < 0) { 04718 ast_mutex_unlock(&monlock); 04719 ast_log(LOG_ERROR, "Unable to start monitor thread.\n"); 04720 return -1; 04721 } 04722 } 04723 ast_mutex_unlock(&monlock); 04724 return 0; 04725 }
static int skinny_answer | ( | struct ast_channel * | ast | ) | [static] |
Definition at line 2591 of file chan_skinny.c.
References ast_channel::_state, ast_copy_string(), AST_MAX_EXTENSION, ast_setstate(), AST_STATE_UP, ast_verbose(), skinny_subchannel::callid, ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, skinny_subchannel::cxmode, ast_channel::exten, exten, skinny_line::instance, KEYDEF_CONNECTED, ast_channel::macroexten, skinny_device::name, skinny_line::name, ast_channel::name, skinny_line::parent, skinny_subchannel::parent, skinny_subchannel::rtp, s, S_OR, skinny_device::session, SKINNY_CONNECTED, SKINNY_CX_SENDRECV, SKINNY_SILENCE, skinnydebug, start_rtp(), skinny_line::sub, ast_channel::tech_pvt, transmit_callinfo(), transmit_callstate(), transmit_dialednumber(), transmit_displaypromptstatus(), transmit_selectsoftkeys(), and transmit_tone().
02592 { 02593 int res = 0; 02594 struct skinny_subchannel *sub = ast->tech_pvt; 02595 struct skinny_line *l = sub->parent; 02596 struct skinny_device *d = l->parent; 02597 struct skinnysession *s = d->session; 02598 char exten[AST_MAX_EXTENSION] = ""; 02599 02600 ast_copy_string(exten, S_OR(ast->macroexten, ast->exten), sizeof(exten)); 02601 02602 sub->cxmode = SKINNY_CX_SENDRECV; 02603 if (!sub->rtp) { 02604 start_rtp(sub); 02605 } 02606 if (skinnydebug) 02607 ast_verbose("skinny_answer(%s) on %s@%s-%d\n", ast->name, l->name, d->name, sub->callid); 02608 if (ast->_state != AST_STATE_UP) { 02609 ast_setstate(ast, AST_STATE_UP); 02610 } 02611 02612 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 02613 /* order matters here... 02614 for some reason, transmit_callinfo must be before transmit_callstate, 02615 or you won't get keypad messages in some situations. */ 02616 transmit_callinfo(s, ast->cid.cid_name, ast->cid.cid_num, exten, exten, l->instance, sub->callid, 2); 02617 transmit_callstate(s, l->instance, SKINNY_CONNECTED, sub->callid); 02618 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_CONNECTED); 02619 transmit_dialednumber(s, exten, l->instance, sub->callid); 02620 transmit_displaypromptstatus(s, "Connected", 0, l->instance, sub->callid); 02621 return res; 02622 }
static int skinny_call | ( | struct ast_channel * | ast, | |
char * | dest, | |||
int | timeout | |||
) | [static] |
Definition at line 2495 of file chan_skinny.c.
References ast_channel::_state, AST_CONTROL_BUSY, AST_CONTROL_RINGING, ast_log(), ast_queue_control(), ast_setstate(), AST_STATE_DOWN, AST_STATE_RESERVED, AST_STATE_RINGING, ast_verbose(), skinny_subchannel::callid, ast_channel::cid, skinny_line::cid_name, ast_callerid::cid_name, skinny_line::cid_num, ast_callerid::cid_num, skinny_line::dnd, skinny_line::hookstate, skinny_line::instance, KEYDEF_RINGIN, LOG_ERROR, LOG_WARNING, ast_channel::name, skinny_subchannel::outgoing, skinny_line::parent, skinny_subchannel::parent, skinny_device::registered, s, skinny_device::session, SKINNY_ALERT, SKINNY_CALLWAITTONE, SKINNY_LAMP_BLINK, SKINNY_OFFHOOK, SKINNY_ONHOOK, SKINNY_RING_INSIDE, SKINNY_RINGIN, skinnydebug, STIMULUS_LINE, skinny_line::sub, ast_channel::tech_pvt, transmit_callinfo(), transmit_callstate(), transmit_displaypromptstatus(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_selectsoftkeys(), and VERBOSE_PREFIX_3.
02496 { 02497 int res = 0; 02498 int tone = 0; 02499 struct skinny_subchannel *sub = ast->tech_pvt; 02500 struct skinny_line *l = sub->parent; 02501 struct skinny_device *d = l->parent; 02502 struct skinnysession *s = d->session; 02503 02504 if (!d->registered) { 02505 ast_log(LOG_ERROR, "Device not registered, cannot call %s\n", dest); 02506 return -1; 02507 } 02508 02509 if ((ast->_state != AST_STATE_DOWN) && (ast->_state != AST_STATE_RESERVED)) { 02510 ast_log(LOG_WARNING, "skinny_call called on %s, neither down nor reserved\n", ast->name); 02511 return -1; 02512 } 02513 02514 if (skinnydebug) 02515 ast_verbose(VERBOSE_PREFIX_3 "skinny_call(%s)\n", ast->name); 02516 02517 if (l->dnd) { 02518 ast_queue_control(ast, AST_CONTROL_BUSY); 02519 return -1; 02520 } 02521 02522 switch (l->hookstate) { 02523 case SKINNY_OFFHOOK: 02524 tone = SKINNY_CALLWAITTONE; 02525 break; 02526 case SKINNY_ONHOOK: 02527 tone = SKINNY_ALERT; 02528 break; 02529 default: 02530 ast_log(LOG_ERROR, "Don't know how to deal with hookstate %d\n", l->hookstate); 02531 break; 02532 } 02533 02534 transmit_callstate(s, l->instance, SKINNY_RINGIN, sub->callid); 02535 transmit_selectsoftkeys(s, l->instance, sub->callid, KEYDEF_RINGIN); 02536 transmit_displaypromptstatus(s, "Ring-In", 0, l->instance, sub->callid); 02537 transmit_callinfo(s, ast->cid.cid_name, ast->cid.cid_num, l->cid_name, l->cid_num, l->instance, sub->callid, 1); 02538 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_BLINK); 02539 transmit_ringer_mode(s, SKINNY_RING_INSIDE); 02540 02541 ast_setstate(ast, AST_STATE_RINGING); 02542 ast_queue_control(ast, AST_CONTROL_RINGING); 02543 sub->outgoing = 1; 02544 return res; 02545 }
static int skinny_do_debug | ( | int | fd, | |
int | argc, | |||
char * | argv[] | |||
) | [static] |
Definition at line 1869 of file chan_skinny.c.
References ast_cli(), RESULT_SHOWUSAGE, RESULT_SUCCESS, and skinnydebug.
01870 { 01871 if (argc != 3) { 01872 return RESULT_SHOWUSAGE; 01873 } 01874 skinnydebug = 1; 01875 ast_cli(fd, "Skinny Debugging Enabled\n"); 01876 return RESULT_SUCCESS; 01877 }
static int skinny_fixup | ( | struct ast_channel * | oldchan, | |
struct ast_channel * | newchan | |||
) | [static] |
Definition at line 2710 of file chan_skinny.c.
References ast_log(), LOG_NOTICE, LOG_WARNING, ast_channel::name, skinny_subchannel::owner, and ast_channel::tech_pvt.
02711 { 02712 struct skinny_subchannel *sub = newchan->tech_pvt; 02713 ast_log(LOG_NOTICE, "skinny_fixup(%s, %s)\n", oldchan->name, newchan->name); 02714 if (sub->owner != oldchan) { 02715 ast_log(LOG_WARNING, "old channel wasn't %p but was %p\n", oldchan, sub->owner); 02716 return -1; 02717 } 02718 sub->owner = newchan; 02719 return 0; 02720 }
static enum ast_rtp_get_result skinny_get_rtp_peer | ( | struct ast_channel * | c, | |
struct ast_rtp ** | rtp | |||
) | [static] |
Definition at line 1839 of file chan_skinny.c.
References AST_RTP_GET_FAILED, AST_RTP_TRY_NATIVE, skinny_subchannel::rtp, and ast_channel::tech_pvt.
01840 { 01841 struct skinny_subchannel *sub = NULL; 01842 01843 if (!(sub = c->tech_pvt) || !(sub->rtp)) 01844 return AST_RTP_GET_FAILED; 01845 01846 *rtp = sub->rtp; 01847 01848 return AST_RTP_TRY_NATIVE; 01849 }
static enum ast_rtp_get_result skinny_get_vrtp_peer | ( | struct ast_channel * | c, | |
struct ast_rtp ** | rtp | |||
) | [static] |
Definition at line 1827 of file chan_skinny.c.
References AST_RTP_GET_FAILED, AST_RTP_TRY_NATIVE, skinny_subchannel::rtp, ast_channel::tech_pvt, and skinny_subchannel::vrtp.
01828 { 01829 struct skinny_subchannel *sub = NULL; 01830 01831 if (!(sub = c->tech_pvt) || !(sub->vrtp)) 01832 return AST_RTP_GET_FAILED; 01833 01834 *rtp = sub->vrtp; 01835 01836 return AST_RTP_TRY_NATIVE; 01837 }
static int skinny_hangup | ( | struct ast_channel * | ast | ) | [static] |
Definition at line 2547 of file chan_skinny.c.
References skinny_subchannel::alreadygone, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_rtp_destroy(), ast_verbose(), skinny_subchannel::callid, do_housekeeping(), skinny_line::hookstate, skinny_line::instance, skinny_subchannel::lock, LOG_DEBUG, skinny_device::name, skinny_line::name, ast_channel::name, skinny_subchannel::outgoing, skinny_subchannel::owner, skinny_line::parent, skinny_subchannel::parent, skinny_device::registered, skinny_subchannel::rtp, s, skinny_device::session, SKINNY_LAMP_OFF, SKINNY_OFFHOOK, SKINNY_ONHOOK, SKINNY_RING_OFF, SKINNY_SILENCE, SKINNY_SPEAKEROFF, skinnydebug, STIMULUS_LINE, ast_channel::tech_pvt, transmit_callstate(), transmit_lamp_indication(), transmit_ringer_mode(), transmit_speaker_mode(), transmit_tone(), skinny_line::type, and TYPE_LINE.
02548 { 02549 struct skinny_subchannel *sub = ast->tech_pvt; 02550 struct skinny_line *l; 02551 struct skinny_device *d; 02552 struct skinnysession *s; 02553 02554 if (!sub) { 02555 ast_log(LOG_DEBUG, "Asked to hangup channel not connected\n"); 02556 return 0; 02557 } 02558 l = sub->parent; 02559 d = l->parent; 02560 s = d->session; 02561 if (skinnydebug) 02562 ast_verbose("skinny_hangup(%s) on %s@%s\n", ast->name, l->name, d->name); 02563 02564 if (d->registered) { 02565 if ((l->type = TYPE_LINE) && (l->hookstate == SKINNY_OFFHOOK)) { 02566 l->hookstate = SKINNY_ONHOOK; 02567 transmit_callstate(s, l->instance, SKINNY_ONHOOK, sub->callid); 02568 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_OFF); 02569 transmit_speaker_mode(s, SKINNY_SPEAKEROFF); 02570 } else if ((l->type = TYPE_LINE) && (l->hookstate == SKINNY_ONHOOK)) { 02571 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 02572 transmit_callstate(s, l->instance, SKINNY_ONHOOK, sub->callid); 02573 transmit_ringer_mode(s, SKINNY_RING_OFF); 02574 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_OFF); 02575 do_housekeeping(s); 02576 } 02577 } 02578 ast_mutex_lock(&sub->lock); 02579 sub->owner = NULL; 02580 ast->tech_pvt = NULL; 02581 sub->alreadygone = 0; 02582 sub->outgoing = 0; 02583 if (sub->rtp) { 02584 ast_rtp_destroy(sub->rtp); 02585 sub->rtp = NULL; 02586 } 02587 ast_mutex_unlock(&sub->lock); 02588 return 0; 02589 }
static int skinny_hold | ( | struct skinny_subchannel * | sub | ) | [static] |
Definition at line 2973 of file chan_skinny.c.
References ACTIVATE_CALL_PLANE_MESSAGE, skinny_data::activatecallplane, AST_CONTROL_HOLD, ast_queue_control_data(), ast_strlen_zero(), ast_verbose(), skinny_subchannel::callid, CLOSE_RECEIVE_CHANNEL_MESSAGE, skinny_data::closereceivechannel, stop_media_transmission_message::conferenceId, close_receive_channel_message::conferenceId, skinny_req::data, htolel, skinny_line::instance, activate_call_plane_message::lineInstance, skinny_line::mohsuggest, skinny_subchannel::onhold, skinny_subchannel::owner, skinny_line::parent, skinny_subchannel::parent, close_receive_channel_message::partyId, stop_media_transmission_message::passThruPartyId, req_alloc(), s, S_OR, skinny_device::session, SKINNY_LAMP_BLINK, skinnydebug, STIMULUS_LINE, STOP_MEDIA_TRANSMISSION_MESSAGE, skinny_data::stopmedia, skinny_line::sub, transmit_lamp_indication(), and transmit_response().
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
02974 { 02975 struct skinny_line *l = sub->parent; 02976 struct skinny_device *d = l->parent; 02977 struct skinnysession *s = d->session; 02978 struct skinny_req *req; 02979 02980 /* Don't try to hold a channel that doesn't exist */ 02981 if (!sub || !sub->owner) 02982 return 0; 02983 02984 /* Channel needs to be put on hold */ 02985 if (skinnydebug) 02986 ast_verbose("Putting on Hold(%d)\n", l->instance); 02987 02988 ast_queue_control_data(sub->owner, AST_CONTROL_HOLD, 02989 S_OR(l->mohsuggest, NULL), 02990 !ast_strlen_zero(l->mohsuggest) ? strlen(l->mohsuggest) + 1 : 0); 02991 02992 if (!(req = req_alloc(sizeof(struct activate_call_plane_message), ACTIVATE_CALL_PLANE_MESSAGE))) 02993 return 0; 02994 02995 req->data.activatecallplane.lineInstance = htolel(l->instance); 02996 transmit_response(s, req); 02997 02998 if (!(req = req_alloc(sizeof(struct close_receive_channel_message), CLOSE_RECEIVE_CHANNEL_MESSAGE))) 02999 return 0; 03000 03001 req->data.closereceivechannel.conferenceId = htolel(sub->callid); 03002 req->data.closereceivechannel.partyId = htolel(sub->callid); 03003 transmit_response(s, req); 03004 03005 if (!(req = req_alloc(sizeof(struct stop_media_transmission_message), STOP_MEDIA_TRANSMISSION_MESSAGE))) 03006 return 0; 03007 03008 req->data.stopmedia.conferenceId = htolel(sub->callid); 03009 req->data.stopmedia.passThruPartyId = htolel(sub->callid); 03010 transmit_response(s, req); 03011 03012 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_BLINK); 03013 sub->onhold = 1; 03014 return 1; 03015 }
static int skinny_indicate | ( | struct ast_channel * | ast, | |
int | ind, | |||
const void * | data, | |||
size_t | datalen | |||
) | [static] |
Definition at line 2790 of file chan_skinny.c.
References ast_channel::_state, skinny_subchannel::alreadygone, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_HOLD, AST_CONTROL_PROCEEDING, AST_CONTROL_PROGRESS, AST_CONTROL_RINGING, AST_CONTROL_SRCCHANGE, AST_CONTROL_SRCUPDATE, AST_CONTROL_UNHOLD, ast_copy_string(), ast_log(), AST_MAX_EXTENSION, ast_moh_start(), ast_moh_stop(), ast_rtp_change_source(), ast_rtp_new_source(), AST_SOFTHANGUP_DEV, ast_softhangup_nolock(), AST_STATE_UP, ast_verbose(), skinny_subchannel::callid, ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, control2str(), skinny_device::earlyrtp, ast_channel::exten, exten, skinny_line::instance, LOG_NOTICE, LOG_WARNING, ast_channel::macroexten, skinny_line::mohinterpret, ast_channel::name, skinny_subchannel::outgoing, skinny_line::parent, skinny_subchannel::parent, skinny_subchannel::progress, skinny_subchannel::ringing, skinny_subchannel::rtp, s, S_OR, skinny_device::session, SKINNY_ALERT, SKINNY_BUSY, SKINNY_BUSYTONE, SKINNY_CONGESTION, SKINNY_PROGRESS, SKINNY_REORDER, SKINNY_RINGOUT, SKINNY_SILENCE, skinnydebug, skinny_line::sub, ast_channel::tech_pvt, transmit_callinfo(), transmit_callstate(), transmit_dialednumber(), transmit_displaypromptstatus(), transmit_tone(), and VERBOSE_PREFIX_3.
02791 { 02792 struct skinny_subchannel *sub = ast->tech_pvt; 02793 struct skinny_line *l = sub->parent; 02794 struct skinny_device *d = l->parent; 02795 struct skinnysession *s = d->session; 02796 char exten[AST_MAX_EXTENSION] = ""; 02797 02798 if (!s) { 02799 ast_log(LOG_NOTICE, "Asked to indicate '%s' condition on channel %s, but session does not exist.\n", control2str(ind), ast->name); 02800 return -1; 02801 } 02802 02803 ast_copy_string(exten, S_OR(ast->macroexten, ast->exten), sizeof(exten)); 02804 02805 if (skinnydebug) 02806 ast_verbose(VERBOSE_PREFIX_3 "Asked to indicate '%s' condition on channel %s\n", control2str(ind), ast->name); 02807 switch(ind) { 02808 case AST_CONTROL_RINGING: 02809 if (ast->_state != AST_STATE_UP) { 02810 if (!sub->progress) { 02811 if (!d->earlyrtp) { 02812 transmit_tone(s, SKINNY_ALERT, l->instance, sub->callid); 02813 } 02814 transmit_callstate(s, l->instance, SKINNY_RINGOUT, sub->callid); 02815 transmit_dialednumber(s, exten, l->instance, sub->callid); 02816 transmit_displaypromptstatus(s, "Ring Out", 0, l->instance, sub->callid); 02817 transmit_callinfo(s, ast->cid.cid_name, ast->cid.cid_num, exten, exten, l->instance, sub->callid, 2); /* 2 = outgoing from phone */ 02818 sub->ringing = 1; 02819 if (!d->earlyrtp) { 02820 break; 02821 } 02822 } 02823 } 02824 return -1; /* Tell asterisk to provide inband signalling */ 02825 case AST_CONTROL_BUSY: 02826 if (ast->_state != AST_STATE_UP) { 02827 if (!d->earlyrtp) { 02828 transmit_tone(s, SKINNY_BUSYTONE, l->instance, sub->callid); 02829 } 02830 transmit_callstate(s, l->instance, SKINNY_BUSY, sub->callid); 02831 sub->alreadygone = 1; 02832 ast_softhangup_nolock(ast, AST_SOFTHANGUP_DEV); 02833 if (!d->earlyrtp) { 02834 break; 02835 } 02836 } 02837 return -1; /* Tell asterisk to provide inband signalling */ 02838 case AST_CONTROL_CONGESTION: 02839 if (ast->_state != AST_STATE_UP) { 02840 if (!d->earlyrtp) { 02841 transmit_tone(s, SKINNY_REORDER, l->instance, sub->callid); 02842 } 02843 transmit_callstate(s, l->instance, SKINNY_CONGESTION, sub->callid); 02844 sub->alreadygone = 1; 02845 ast_softhangup_nolock(ast, AST_SOFTHANGUP_DEV); 02846 if (!d->earlyrtp) { 02847 break; 02848 } 02849 } 02850 return -1; /* Tell asterisk to provide inband signalling */ 02851 case AST_CONTROL_PROGRESS: 02852 if ((ast->_state != AST_STATE_UP) && !sub->progress && !sub->outgoing) { 02853 if (!d->earlyrtp) { 02854 transmit_tone(s, SKINNY_ALERT, l->instance, sub->callid); 02855 } 02856 transmit_callstate(s, l->instance, SKINNY_PROGRESS, sub->callid); 02857 transmit_displaypromptstatus(s, "Call Progress", 0, l->instance, sub->callid); 02858 transmit_callinfo(s, ast->cid.cid_name, ast->cid.cid_num, exten, exten, l->instance, sub->callid, 2); /* 2 = outgoing from phone */ 02859 sub->progress = 1; 02860 if (!d->earlyrtp) { 02861 break; 02862 } 02863 } 02864 return -1; /* Tell asterisk to provide inband signalling */ 02865 case -1: /* STOP_TONE */ 02866 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 02867 break; 02868 case AST_CONTROL_HOLD: 02869 ast_moh_start(ast, data, l->mohinterpret); 02870 break; 02871 case AST_CONTROL_UNHOLD: 02872 ast_moh_stop(ast); 02873 break; 02874 case AST_CONTROL_PROCEEDING: 02875 break; 02876 case AST_CONTROL_SRCUPDATE: 02877 ast_rtp_new_source(sub->rtp); 02878 break; 02879 case AST_CONTROL_SRCCHANGE: 02880 ast_rtp_change_source(sub->rtp); 02881 break; 02882 default: 02883 ast_log(LOG_WARNING, "Don't know how to indicate condition %d\n", ind); 02884 return -1; /* Tell asterisk to provide inband signalling */ 02885 } 02886 return 0; 02887 }
static struct ast_channel* skinny_new | ( | struct skinny_line * | l, | |
int | state | |||
) | [static] |
Definition at line 2889 of file chan_skinny.c.
References accountcode, skinny_line::accountcode, ast_channel::adsicpe, ast_channel::amaflags, skinny_line::amaflags, AST_ADSI_UNAVAILABLE, ast_best_codec(), ast_calloc, ast_channel_alloc(), ast_copy_string(), ast_hangup(), ast_jb_configure(), ast_log(), ast_module_ref(), ast_mutex_init(), ast_pbx_start(), ast_rtp_fd(), AST_STATE_DOWN, AST_STATE_RING, ast_strdup, ast_string_field_set, ast_strlen_zero(), ast_verbose(), skinny_line::call_forward, skinny_line::callgroup, ast_channel::callgroup, skinny_subchannel::callid, callnums, skinny_line::capability, ast_channel::cid, ast_callerid::cid_ani, skinny_line::cid_name, skinny_line::cid_num, ast_channel::context, skinny_line::context, skinny_subchannel::cxmode, default_capability, ast_channel::exten, skinny_line::exten, ast_channel::fds, global_jbconf, skinny_line::instance, language, skinny_line::language, skinny_device::lastcallreference, skinny_device::lastlineinstance, skinny_subchannel::lock, LOG_WARNING, skinny_device::name, skinny_line::name, skinny_line::nat, skinny_subchannel::nat, ast_channel::nativeformats, skinny_subchannel::next, skinny_subchannel::onhold, skinny_subchannel::owner, skinny_subchannel::parent, skinny_line::parent, skinny_line::pickupgroup, ast_channel::pickupgroup, ast_channel::priority, ast_channel::rawreadformat, ast_channel::rawwriteformat, ast_channel::readformat, ast_channel::rings, skinny_subchannel::rtp, SKINNY_CX_INACTIVE, skinny_tech, skinnydebug, skinny_line::sub, ast_channel::tech, ast_channel::tech_pvt, and ast_channel::writeformat.
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_request().
02890 { 02891 struct ast_channel *tmp; 02892 struct skinny_subchannel *sub; 02893 struct skinny_device *d = l->parent; 02894 int fmt; 02895 02896 tmp = ast_channel_alloc(1, state, l->cid_num, l->cid_name, l->accountcode, l->exten, l->context, l->amaflags, "Skinny/%s@%s-%d", l->name, d->name, callnums); 02897 if (!tmp) { 02898 ast_log(LOG_WARNING, "Unable to allocate channel structure\n"); 02899 return NULL; 02900 } else { 02901 sub = ast_calloc(1, sizeof(struct skinny_subchannel)); 02902 if (!sub) { 02903 ast_log(LOG_WARNING, "Unable to allocate Skinny subchannel\n"); 02904 return NULL; 02905 } else { 02906 ast_mutex_init(&sub->lock); 02907 02908 sub->owner = tmp; 02909 sub->callid = callnums++; 02910 d->lastlineinstance = l->instance; 02911 d->lastcallreference = sub->callid; 02912 sub->cxmode = SKINNY_CX_INACTIVE; 02913 sub->nat = l->nat; 02914 sub->parent = l; 02915 sub->onhold = 0; 02916 02917 sub->next = l->sub; 02918 l->sub = sub; 02919 } 02920 tmp->tech = &skinny_tech; 02921 tmp->tech_pvt = sub; 02922 tmp->nativeformats = l->capability; 02923 if (!tmp->nativeformats) 02924 tmp->nativeformats = default_capability; 02925 fmt = ast_best_codec(tmp->nativeformats); 02926 if (skinnydebug) 02927 ast_verbose("skinny_new: tmp->nativeformats=%d fmt=%d\n", tmp->nativeformats, fmt); 02928 if (sub->rtp) { 02929 tmp->fds[0] = ast_rtp_fd(sub->rtp); 02930 } 02931 if (state == AST_STATE_RING) { 02932 tmp->rings = 1; 02933 } 02934 tmp->writeformat = fmt; 02935 tmp->rawwriteformat = fmt; 02936 tmp->readformat = fmt; 02937 tmp->rawreadformat = fmt; 02938 if (!ast_strlen_zero(l->language)) 02939 ast_string_field_set(tmp, language, l->language); 02940 if (!ast_strlen_zero(l->accountcode)) 02941 ast_string_field_set(tmp, accountcode, l->accountcode); 02942 if (l->amaflags) 02943 tmp->amaflags = l->amaflags; 02944 02945 ast_module_ref(ast_module_info->self); 02946 tmp->callgroup = l->callgroup; 02947 tmp->pickupgroup = l->pickupgroup; 02948 ast_string_field_set(tmp, call_forward, l->call_forward); 02949 ast_copy_string(tmp->context, l->context, sizeof(tmp->context)); 02950 ast_copy_string(tmp->exten, l->exten, sizeof(tmp->exten)); 02951 02952 /* Don't use ast_set_callerid() here because it will 02953 * generate a needless NewCallerID event */ 02954 tmp->cid.cid_ani = ast_strdup(l->cid_num); 02955 02956 tmp->priority = 1; 02957 tmp->adsicpe = AST_ADSI_UNAVAILABLE; 02958 02959 if (sub->rtp) 02960 ast_jb_configure(tmp, &global_jbconf); 02961 02962 if (state != AST_STATE_DOWN) { 02963 if (ast_pbx_start(tmp)) { 02964 ast_log(LOG_WARNING, "Unable to start PBX on %s\n", tmp->name); 02965 ast_hangup(tmp); 02966 tmp = NULL; 02967 } 02968 } 02969 } 02970 return tmp; 02971 }
static void* skinny_newcall | ( | void * | data | ) | [static] |
Definition at line 2369 of file chan_skinny.c.
References ast_copy_string(), ast_log(), ast_pbx_run(), ast_set_callerid(), ast_setstate(), AST_STATE_RING, skinny_subchannel::callid, ast_channel::cid, ast_callerid::cid_ani, skinny_line::cid_name, skinny_line::cid_num, ast_channel::exten, skinny_line::hidecallerid, skinny_line::instance, skinny_line::lastnumberdialed, LOG_WARNING, skinny_line::parent, skinny_subchannel::parent, skinny_subchannel::rtp, s, skinny_device::session, SKINNY_REORDER, start_rtp(), skinny_line::sub, ast_channel::tech_pvt, and transmit_tone().
Referenced by handle_enbloc_call_message(), handle_soft_key_event_message(), handle_stimulus_message(), and skinny_ss().
02370 { 02371 struct ast_channel *c = data; 02372 struct skinny_subchannel *sub = c->tech_pvt; 02373 struct skinny_line *l = sub->parent; 02374 struct skinny_device *d = l->parent; 02375 struct skinnysession *s = d->session; 02376 int res = 0; 02377 02378 ast_copy_string(l->lastnumberdialed, c->exten, sizeof(l->lastnumberdialed)); 02379 ast_set_callerid(c, 02380 l->hidecallerid ? "" : l->cid_num, 02381 l->hidecallerid ? "" : l->cid_name, 02382 c->cid.cid_ani ? NULL : l->cid_num); 02383 ast_setstate(c, AST_STATE_RING); 02384 if (!sub->rtp) { 02385 start_rtp(sub); 02386 } 02387 res = ast_pbx_run(c); 02388 if (res) { 02389 ast_log(LOG_WARNING, "PBX exited non-zero\n"); 02390 transmit_tone(s, SKINNY_REORDER, l->instance, sub->callid); 02391 } 02392 return NULL; 02393 }
static int skinny_no_debug | ( | int | fd, | |
int | argc, | |||
char * | argv[] | |||
) | [static] |
Definition at line 1879 of file chan_skinny.c.
References ast_cli(), RESULT_SHOWUSAGE, RESULT_SUCCESS, and skinnydebug.
01880 { 01881 if (argc != 4) { 01882 return RESULT_SHOWUSAGE; 01883 } 01884 skinnydebug = 0; 01885 ast_cli(fd, "Skinny Debugging Disabled\n"); 01886 return RESULT_SUCCESS; 01887 }
static struct ast_frame * skinny_read | ( | struct ast_channel * | ast | ) | [static] |
Definition at line 2672 of file chan_skinny.c.
References ast_mutex_lock(), ast_mutex_unlock(), skinny_subchannel::lock, skinny_rtp_read(), and ast_channel::tech_pvt.
02673 { 02674 struct ast_frame *fr; 02675 struct skinny_subchannel *sub = ast->tech_pvt; 02676 ast_mutex_lock(&sub->lock); 02677 fr = skinny_rtp_read(sub); 02678 ast_mutex_unlock(&sub->lock); 02679 return fr; 02680 }
static int skinny_register | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 1421 of file chan_skinny.c.
References __ourip, ast_apply_ha(), ast_copy_string(), ast_log(), ast_mutex_lock(), ast_strlen_zero(), skinny_req::data, devicelock, devices, skinny_device::ha, skinny_device::id, letohl, LOG_WARNING, register_message::name, skinny_device::next, skinny_data::reg, skinny_device::registered, s, skinny_device::session, register_message::type, skinny_device::type, version_id, and skinny_device::version_id.
Referenced by handle_register_message().
01422 { 01423 struct skinny_device *d; 01424 struct sockaddr_in sin; 01425 socklen_t slen; 01426 01427 ast_mutex_lock(&devicelock); 01428 for (d = devices; d; d = d->next) { 01429 if (!strcasecmp(req->data.reg.name, d->id) 01430 && ast_apply_ha(d->ha, &(s->sin))) { 01431 s->device = d; 01432 d->type = letohl(req->data.reg.type); 01433 if (ast_strlen_zero(d->version_id)) { 01434 ast_copy_string(d->version_id, version_id, sizeof(d->version_id)); 01435 } 01436 d->registered = 1; 01437 d->session = s; 01438 01439 slen = sizeof(sin); 01440 if (getsockname(s->fd, (struct sockaddr *)&sin, &slen)) { 01441 ast_log(LOG_WARNING, "Cannot get socket name\n"); 01442 sin.sin_addr = __ourip; 01443 } 01444 d->ourip = sin.sin_addr; 01445 break; 01446 } 01447 } 01448 ast_mutex_unlock(&devicelock); 01449 if (!d) { 01450 return 0; 01451 } 01452 return 1; 01453 }
static struct skinny_req* skinny_req_parse | ( | struct skinnysession * | s | ) | [static] |
Definition at line 4547 of file chan_skinny.c.
References ast_calloc, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), skinny_req::data, skinny_req::e, free, letohl, LOG_ERROR, s, skinny_header_size, and SKINNY_MAX_PACKET.
Referenced by skinny_session().
04548 { 04549 struct skinny_req *req; 04550 int *bufaddr; 04551 04552 if (!(req = ast_calloc(1, SKINNY_MAX_PACKET))) 04553 return NULL; 04554 04555 ast_mutex_lock(&s->lock); 04556 memcpy(req, s->inbuf, skinny_header_size); 04557 bufaddr = (int *)(s->inbuf); 04558 memcpy(&req->data, s->inbuf+skinny_header_size, letohl(*bufaddr)-4); 04559 04560 ast_mutex_unlock(&s->lock); 04561 04562 if (letohl(req->e) < 0) { 04563 ast_log(LOG_ERROR, "Event Message is NULL from socket %d, This is bad\n", s->fd); 04564 free(req); 04565 return NULL; 04566 } 04567 04568 return req; 04569 }
static struct ast_channel * skinny_request | ( | const char * | type, | |
int | format, | |||
void * | data, | |||
int * | cause | |||
) | [static] |
Definition at line 4727 of file chan_skinny.c.
References ast_copy_string(), AST_FORMAT_MAX_AUDIO, ast_log(), AST_STATE_DOWN, ast_strlen_zero(), ast_verbose(), find_line_by_name(), LOG_NOTICE, LOG_WARNING, option_verbose, restart_monitor(), skinny_new(), and VERBOSE_PREFIX_3.
04728 { 04729 int oldformat; 04730 04731 struct skinny_line *l; 04732 struct ast_channel *tmpc = NULL; 04733 char tmp[256]; 04734 char *dest = data; 04735 04736 oldformat = format; 04737 04738 if (!(format &= ((AST_FORMAT_MAX_AUDIO << 1) - 1))) { 04739 ast_log(LOG_NOTICE, "Asked to get a channel of unsupported format '%d'\n", format); 04740 return NULL; 04741 } 04742 04743 ast_copy_string(tmp, dest, sizeof(tmp)); 04744 if (ast_strlen_zero(tmp)) { 04745 ast_log(LOG_NOTICE, "Skinny channels require a device\n"); 04746 return NULL; 04747 } 04748 l = find_line_by_name(tmp); 04749 if (!l) { 04750 ast_log(LOG_NOTICE, "No available lines on: %s\n", dest); 04751 return NULL; 04752 } 04753 if (option_verbose > 2) { 04754 ast_verbose(VERBOSE_PREFIX_3 "skinny_request(%s)\n", tmp); 04755 } 04756 tmpc = skinny_new(l, AST_STATE_DOWN); 04757 if (!tmpc) { 04758 ast_log(LOG_WARNING, "Unable to make channel for '%s'\n", tmp); 04759 } 04760 restart_monitor(); 04761 return tmpc; 04762 }
static int skinny_reset_device | ( | int | fd, | |
int | argc, | |||
char * | argv[] | |||
) | [static] |
Definition at line 1907 of file chan_skinny.c.
References ast_mutex_lock(), ast_mutex_unlock(), ast_verbose(), skinny_req::data, devicelock, devices, skinny_device::id, skinny_device::next, option_verbose, req_alloc(), skinny_data::reset, RESET_MESSAGE, reset_message::resetType, RESULT_SHOWUSAGE, RESULT_SUCCESS, skinny_device::session, transmit_response(), and VERBOSE_PREFIX_3.
01908 { 01909 struct skinny_device *d; 01910 struct skinny_req *req; 01911 01912 if (argc < 3 || argc > 4) { 01913 return RESULT_SHOWUSAGE; 01914 } 01915 ast_mutex_lock(&devicelock); 01916 01917 for (d = devices; d; d = d->next) { 01918 int fullrestart = 0; 01919 if (!strcasecmp(argv[2], d->id) || !strcasecmp(argv[2], "all")) { 01920 if (!(d->session)) 01921 continue; 01922 01923 if (!(req = req_alloc(sizeof(struct reset_message), RESET_MESSAGE))) 01924 continue; 01925 01926 if (argc == 4 && !strcasecmp(argv[3], "restart")) 01927 fullrestart = 1; 01928 01929 if (fullrestart) 01930 req->data.reset.resetType = 2; 01931 else 01932 req->data.reset.resetType = 1; 01933 01934 if (option_verbose > 2) 01935 ast_verbose(VERBOSE_PREFIX_3 "%s device %s.\n", (fullrestart) ? "Restarting" : "Resetting", d->id); 01936 transmit_response(d->session, req); 01937 } 01938 } 01939 ast_mutex_unlock(&devicelock); 01940 return RESULT_SUCCESS; 01941 }
static struct ast_frame* skinny_rtp_read | ( | struct skinny_subchannel * | sub | ) | [static] |
Definition at line 2625 of file chan_skinny.c.
References AST_FRAME_VOICE, ast_log(), ast_null_frame, ast_rtcp_read(), ast_rtp_read(), ast_set_read_format(), ast_set_write_format(), ast_udptl_read(), f, ast_channel::fdno, LOG_DEBUG, ast_channel::nativeformats, skinny_subchannel::owner, ast_channel::readformat, skinny_subchannel::rtp, skinny_subchannel::vrtp, and ast_channel::writeformat.
Referenced by skinny_read().
02626 { 02627 struct ast_channel *ast = sub->owner; 02628 struct ast_frame *f; 02629 02630 if (!sub->rtp) { 02631 /* We have no RTP allocated for this channel */ 02632 return &ast_null_frame; 02633 } 02634 02635 switch(ast->fdno) { 02636 case 0: 02637 f = ast_rtp_read(sub->rtp); /* RTP Audio */ 02638 break; 02639 case 1: 02640 f = ast_rtcp_read(sub->rtp); /* RTCP Control Channel */ 02641 break; 02642 case 2: 02643 f = ast_rtp_read(sub->vrtp); /* RTP Video */ 02644 break; 02645 case 3: 02646 f = ast_rtcp_read(sub->vrtp); /* RTCP Control Channel for video */ 02647 break; 02648 #if 0 02649 case 5: 02650 /* Not yet supported */ 02651 f = ast_udptl_read(sub->udptl); /* UDPTL for T.38 */ 02652 break; 02653 #endif 02654 default: 02655 f = &ast_null_frame; 02656 } 02657 02658 if (ast) { 02659 /* We already hold the channel lock */ 02660 if (f->frametype == AST_FRAME_VOICE) { 02661 if (f->subclass != ast->nativeformats) { 02662 ast_log(LOG_DEBUG, "Oooh, format changed to %d\n", f->subclass); 02663 ast->nativeformats = f->subclass; 02664 ast_set_read_format(ast, ast->readformat); 02665 ast_set_write_format(ast, ast->writeformat); 02666 } 02667 } 02668 } 02669 return f; 02670 }
static int skinny_senddigit_begin | ( | struct ast_channel * | ast, | |
char | digit | |||
) | [static] |
static int skinny_senddigit_end | ( | struct ast_channel * | ast, | |
char | digit, | |||
unsigned int | duration | |||
) | [static] |
Definition at line 2727 of file chan_skinny.c.
References skinny_subchannel::callid, skinny_line::instance, skinny_line::parent, skinny_subchannel::parent, skinny_device::session, skinny_line::sub, ast_channel::tech_pvt, and transmit_tone().
02728 { 02729 #if 0 02730 struct skinny_subchannel *sub = ast->tech_pvt; 02731 struct skinny_line *l = sub->parent; 02732 struct skinny_device *d = l->parent; 02733 int tmp; 02734 /* not right */ 02735 sprintf(tmp, "%d", digit); 02736 transmit_tone(d->session, digit, l->instance, sub->callid); 02737 #endif 02738 return -1; /* Stop inband indications */ 02739 }
static void* skinny_session | ( | void * | data | ) | [static] |
Definition at line 4571 of file chan_skinny.c.
References ast_inet_ntoa(), ast_log(), ast_verbose(), destroy_session(), errno, get_input(), handle_message(), LOG_NOTICE, option_verbose, skinny_req::res, s, skinny_req_parse(), and VERBOSE_PREFIX_3.
Referenced by accept_thread().
04572 { 04573 int res; 04574 struct skinny_req *req; 04575 struct skinnysession *s = data; 04576 04577 if (option_verbose > 2) 04578 ast_verbose(VERBOSE_PREFIX_3 "Starting Skinny session from %s\n", ast_inet_ntoa(s->sin.sin_addr)); 04579 04580 for (;;) { 04581 res = get_input(s); 04582 if (res < 0) { 04583 break; 04584 } 04585 04586 if (res > 0) 04587 { 04588 if (!(req = skinny_req_parse(s))) { 04589 destroy_session(s); 04590 return NULL; 04591 } 04592 04593 res = handle_message(req, s); 04594 if (res < 0) { 04595 destroy_session(s); 04596 return NULL; 04597 } 04598 } 04599 } 04600 ast_log(LOG_NOTICE, "Skinny Session returned: %s\n", strerror(errno)); 04601 04602 if (s) 04603 destroy_session(s); 04604 04605 return 0; 04606 }
static int skinny_set_rtp_peer | ( | struct ast_channel * | c, | |
struct ast_rtp * | rtp, | |||
struct ast_rtp * | vrtp, | |||
int | codecs, | |||
int | nat_active | |||
) | [static] |
Definition at line 1851 of file chan_skinny.c.
References ast_channel::tech_pvt.
01852 { 01853 struct skinny_subchannel *sub; 01854 sub = c->tech_pvt; 01855 if (sub) { 01856 /* transmit_modify_with_sdp(sub, rtp); @@FIXME@@ if needed */ 01857 return 0; 01858 } 01859 return -1; 01860 }
static int skinny_show_devices | ( | int | fd, | |
int | argc, | |||
char * | argv[] | |||
) | [static] |
Definition at line 2032 of file chan_skinny.c.
References ast_cli(), ast_inet_ntoa(), ast_mutex_lock(), device2str(), devicelock, devices, skinny_device::id, skinny_device::lines, skinny_device::name, skinny_line::next, skinny_device::next, skinny_device::registered, RESULT_SHOWUSAGE, skinny_device::session, skinnysession::sin, and skinny_device::type.
02033 { 02034 struct skinny_device *d; 02035 struct skinny_line *l; 02036 int numlines = 0; 02037 02038 if (argc != 3) { 02039 return RESULT_SHOWUSAGE; 02040 } 02041 ast_mutex_lock(&devicelock); 02042 02043 ast_cli(fd, "Name DeviceId IP Type R NL\n"); 02044 ast_cli(fd, "-------------------- ---------------- --------------- --------------- - --\n"); 02045 for (d = devices; d; d = d->next) { 02046 numlines = 0; 02047 for (l = d->lines; l; l = l->next) { 02048 numlines++; 02049 } 02050 02051 ast_cli(fd, "%-20s %-16s %-15s %-15s %c %2d\n", 02052 d->name, 02053 d->id, 02054 d->session?ast_inet_ntoa(d->session->sin.sin_addr):"", 02055 device2str(d->type), 02056 d->registered?'Y':'N', 02057 numlines); 02058 } 02059 ast_mutex_unlock(&devicelock); 02060 return RESULT_SUCCESS; 02061 }
static int skinny_show_lines | ( | int | fd, | |
int | argc, | |||
char * | argv[] | |||
) | [static] |
Definition at line 2063 of file chan_skinny.c.
References ast_cli(), ast_mutex_lock(), devicelock, devices, skinny_line::instance, skinny_line::label, skinny_device::lines, skinny_line::name, skinny_device::name, skinny_line::next, skinny_device::next, and RESULT_SHOWUSAGE.
02064 { 02065 struct skinny_device *d; 02066 struct skinny_line *l; 02067 02068 if (argc != 3) { 02069 return RESULT_SHOWUSAGE; 02070 } 02071 ast_mutex_lock(&devicelock); 02072 02073 ast_cli(fd, "Device Name Instance Name Label \n"); 02074 ast_cli(fd, "-------------------- -------- -------------------- --------------------\n"); 02075 for (d = devices; d; d = d->next) { 02076 for (l = d->lines; l; l = l->next) { 02077 ast_cli(fd, "%-20s %8d %-20s %-20s\n", 02078 d->name, 02079 l->instance, 02080 l->name, 02081 l->label); 02082 } 02083 } 02084 02085 ast_mutex_unlock(&devicelock); 02086 return RESULT_SUCCESS; 02087 }
static void* skinny_ss | ( | void * | data | ) | [static] |
Definition at line 2395 of file chan_skinny.c.
References ast_channel::_state, ast_canmatch_extension(), ast_copy_string(), ast_exists_extension(), ast_hangup(), ast_ignore_pattern(), ast_indicate(), ast_log(), ast_matchmore_extension(), AST_MAX_EXTENSION, ast_safe_sleep(), AST_STATE_UP, ast_strlen_zero(), ast_verbose(), skinny_line::call_forward, skinny_subchannel::callid, ast_channel::cid, ast_callerid::cid_num, skinny_line::cid_num, ast_channel::context, ast_channel::exten, skinny_device::exten, firstdigittimeout, gendigittimeout, skinny_line::instance, skinny_line::lastnumberdialed, len(), LOG_DEBUG, LOG_WARNING, matchdigittimeout, ast_channel::name, skinny_device::name, skinny_line::name, option_verbose, skinny_subchannel::owner, skinny_line::parent, skinny_subchannel::parent, s, skinny_device::session, SKINNY_DIALTONE, skinny_newcall(), SKINNY_REORDER, SKINNY_SILENCE, skinny_line::sub, ast_channel::tech_pvt, transmit_tone(), and VERBOSE_PREFIX_3.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), and handle_stimulus_message().
02396 { 02397 struct ast_channel *c = data; 02398 struct skinny_subchannel *sub = c->tech_pvt; 02399 struct skinny_line *l = sub->parent; 02400 struct skinny_device *d = l->parent; 02401 struct skinnysession *s = d->session; 02402 int len = 0; 02403 int timeout = firstdigittimeout; 02404 int res = 0; 02405 int getforward=0; 02406 int loop_pause = 100; 02407 02408 if (option_verbose > 2) 02409 ast_verbose( VERBOSE_PREFIX_3 "Starting simple switch on '%s@%s'\n", l->name, d->name); 02410 len = strlen(d->exten); 02411 02412 while (len < AST_MAX_EXTENSION-1) { 02413 02414 res = 1; /* Assume we will get a digit */ 02415 while (strlen(d->exten) == len) { 02416 ast_safe_sleep(c, loop_pause); 02417 timeout -= loop_pause; 02418 if (timeout <= 0){ 02419 res = 0; 02420 break; 02421 } 02422 } 02423 02424 len = strlen(d->exten); 02425 02426 if (!ast_ignore_pattern(c->context, d->exten)) { 02427 transmit_tone(s, SKINNY_SILENCE, l->instance, sub->callid); 02428 } 02429 02430 if (ast_exists_extension(c, c->context, d->exten, 1, l->cid_num)) { 02431 if (!res || !ast_matchmore_extension(c, c->context, d->exten, 1, l->cid_num)) { 02432 if (getforward) { 02433 /* Record this as the forwarding extension */ 02434 ast_copy_string(l->call_forward, d->exten, sizeof(l->call_forward)); 02435 if (option_verbose > 2) 02436 ast_verbose(VERBOSE_PREFIX_3 "Setting call forward to '%s' on channel %s\n", 02437 l->call_forward, c->name); 02438 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 02439 if (res) { 02440 break; 02441 } 02442 ast_safe_sleep(c, 500); 02443 ast_indicate(c, -1); 02444 ast_safe_sleep(c, 1000); 02445 memset(d->exten, 0, sizeof(d->exten)); 02446 transmit_tone(s, SKINNY_DIALTONE, l->instance, sub->callid); 02447 len = 0; 02448 getforward = 0; 02449 } else { 02450 ast_copy_string(c->exten, d->exten, sizeof(c->exten)); 02451 ast_copy_string(l->lastnumberdialed, d->exten, sizeof(l->lastnumberdialed)); 02452 memset (d->exten, 0, sizeof(d->exten)); 02453 skinny_newcall(c); 02454 return NULL; 02455 } 02456 } else { 02457 /* It's a match, but they just typed a digit, and there is an ambiguous match, 02458 so just set the timeout to matchdigittimeout and wait some more */ 02459 timeout = matchdigittimeout; 02460 } 02461 } else if (res == 0) { 02462 ast_log(LOG_DEBUG, "Not enough digits (and no ambiguous match)...\n"); 02463 memset(d->exten, 0, sizeof(d->exten)); 02464 transmit_tone(s, SKINNY_REORDER, l->instance, sub->callid); 02465 if (sub->owner && sub->owner->_state != AST_STATE_UP) { 02466 ast_indicate(c, -1); 02467 ast_hangup(c); 02468 } 02469 return NULL; 02470 } else if (!ast_canmatch_extension(c, c->context, d->exten, 1, c->cid.cid_num) && 02471 ((d->exten[0] != '*') || (!ast_strlen_zero(d->exten) > 2))) { 02472 ast_log(LOG_WARNING, "Can't match [%s] from '%s' in context %s\n", d->exten, c->cid.cid_num ? c->cid.cid_num : "<Unknown Caller>", c->context); 02473 memset(d->exten, 0, sizeof(d->exten)); 02474 transmit_tone(s, SKINNY_REORDER, l->instance, sub->callid); 02475 /* hang out for 3 seconds to let congestion play */ 02476 ast_safe_sleep(c, 3000); 02477 break; 02478 } 02479 if (!timeout) { 02480 timeout = gendigittimeout; 02481 } 02482 if (len && !ast_ignore_pattern(c->context, d->exten)) { 02483 ast_indicate(c, -1); 02484 } 02485 } 02486 if (c) 02487 ast_hangup(c); 02488 02489 memset(d->exten, 0, sizeof(d->exten)); 02490 return NULL; 02491 }
static int skinny_unhold | ( | struct skinny_subchannel * | sub | ) | [static] |
Definition at line 3017 of file chan_skinny.c.
References ACTIVATE_CALL_PLANE_MESSAGE, skinny_data::activatecallplane, AST_CONTROL_UNHOLD, ast_queue_control(), ast_verbose(), skinny_req::data, htolel, skinny_line::instance, activate_call_plane_message::lineInstance, skinny_subchannel::onhold, skinny_subchannel::owner, skinny_line::parent, skinny_subchannel::parent, req_alloc(), s, skinny_device::session, SKINNY_LAMP_ON, skinnydebug, STIMULUS_LINE, skinny_line::sub, transmit_connect(), transmit_lamp_indication(), and transmit_response().
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
03018 { 03019 struct skinny_line *l = sub->parent; 03020 struct skinny_device *d = l->parent; 03021 struct skinnysession *s = d->session; 03022 struct skinny_req *req; 03023 03024 /* Don't try to unhold a channel that doesn't exist */ 03025 if (!sub || !sub->owner) 03026 return 0; 03027 03028 /* Channel is on hold, so we will unhold */ 03029 if (skinnydebug) 03030 ast_verbose("Taking off Hold(%d)\n", l->instance); 03031 03032 ast_queue_control(sub->owner, AST_CONTROL_UNHOLD); 03033 03034 if (!(req = req_alloc(sizeof(struct activate_call_plane_message), ACTIVATE_CALL_PLANE_MESSAGE))) 03035 return 0; 03036 03037 req->data.activatecallplane.lineInstance = htolel(l->instance); 03038 transmit_response(s, req); 03039 03040 transmit_connect(s, sub); 03041 transmit_lamp_indication(s, STIMULUS_LINE, l->instance, SKINNY_LAMP_ON); 03042 sub->onhold = 0; 03043 return 1; 03044 }
static int skinny_unregister | ( | struct skinny_req * | req, | |
struct skinnysession * | s | |||
) | [static] |
Definition at line 1455 of file chan_skinny.c.
References skinny_device::registered, s, and skinny_device::session.
Referenced by get_input(), handle_unregister_message(), and transmit_response().
01456 { 01457 struct skinny_device *d; 01458 01459 d = s->device; 01460 01461 if (d) { 01462 d->session = NULL; 01463 d->registered = 0; 01464 } 01465 01466 return -1; /* main loop will destroy the session */ 01467 }
static int skinny_write | ( | struct ast_channel * | ast, | |
struct ast_frame * | frame | |||
) | [static] |
Definition at line 2682 of file chan_skinny.c.
References AST_FRAME_IMAGE, AST_FRAME_VOICE, ast_log(), ast_mutex_lock(), ast_mutex_unlock(), ast_rtp_write(), ast_frame::frametype, skinny_subchannel::lock, LOG_WARNING, ast_channel::nativeformats, ast_channel::readformat, skinny_subchannel::rtp, ast_frame::subclass, ast_channel::tech_pvt, and ast_channel::writeformat.
02683 { 02684 struct skinny_subchannel *sub = ast->tech_pvt; 02685 int res = 0; 02686 if (frame->frametype != AST_FRAME_VOICE) { 02687 if (frame->frametype == AST_FRAME_IMAGE) { 02688 return 0; 02689 } else { 02690 ast_log(LOG_WARNING, "Can't send %d type frames with skinny_write\n", frame->frametype); 02691 return 0; 02692 } 02693 } else { 02694 if (!(frame->subclass & ast->nativeformats)) { 02695 ast_log(LOG_WARNING, "Asked to transmit frame type %d, while native formats is %d (read/write = %d/%d)\n", 02696 frame->subclass, ast->nativeformats, ast->readformat, ast->writeformat); 02697 return -1; 02698 } 02699 } 02700 if (sub) { 02701 ast_mutex_lock(&sub->lock); 02702 if (sub->rtp) { 02703 res = ast_rtp_write(sub->rtp, frame); 02704 } 02705 ast_mutex_unlock(&sub->lock); 02706 } 02707 return res; 02708 }
static void start_rtp | ( | struct skinny_subchannel * | sub | ) | [static] |
Definition at line 2334 of file chan_skinny.c.
References ast_mutex_lock(), ast_mutex_unlock(), ast_rtcp_fd(), ast_rtp_codec_setpref(), ast_rtp_fd(), ast_rtp_new_with_bindaddr(), ast_rtp_setnat(), bindaddr, ast_channel::fds, io, skinny_subchannel::lock, skinny_line::nat, skinny_subchannel::owner, skinny_line::parent, skinny_subchannel::parent, skinny_line::prefs, skinny_subchannel::rtp, skinny_device::session, skinny_line::sub, transmit_connect(), and skinny_subchannel::vrtp.
02335 { 02336 struct skinny_line *l = sub->parent; 02337 struct skinny_device *d = l->parent; 02338 int hasvideo = 0; 02339 02340 ast_mutex_lock(&sub->lock); 02341 /* Allocate the RTP */ 02342 sub->rtp = ast_rtp_new_with_bindaddr(sched, io, 1, 0, bindaddr.sin_addr); 02343 if (hasvideo) 02344 sub->vrtp = ast_rtp_new_with_bindaddr(sched, io, 1, 0, bindaddr.sin_addr); 02345 02346 if (sub->rtp && sub->owner) { 02347 sub->owner->fds[0] = ast_rtp_fd(sub->rtp); 02348 sub->owner->fds[1] = ast_rtcp_fd(sub->rtp); 02349 } 02350 if (hasvideo && sub->vrtp && sub->owner) { 02351 sub->owner->fds[2] = ast_rtp_fd(sub->vrtp); 02352 sub->owner->fds[3] = ast_rtcp_fd(sub->vrtp); 02353 } 02354 if (sub->rtp) { 02355 ast_rtp_setnat(sub->rtp, l->nat); 02356 } 02357 if (sub->vrtp) { 02358 ast_rtp_setnat(sub->vrtp, l->nat); 02359 } 02360 /* Set Frame packetization */ 02361 if (sub->rtp) 02362 ast_rtp_codec_setpref(sub->rtp, &l->prefs); 02363 02364 /* Create the RTP connection */ 02365 transmit_connect(d->session, sub); 02366 ast_mutex_unlock(&sub->lock); 02367 }
static void transmit_callinfo | ( | struct skinnysession * | s, | |
const char * | fromname, | |||
const char * | fromnum, | |||
const char * | toname, | |||
const char * | tonum, | |||
int | instance, | |||
int | callid, | |||
int | calltype | |||
) | [static] |
Definition at line 1532 of file chan_skinny.c.
References ast_copy_string(), ast_verbose(), CALL_INFO_MESSAGE, call_info_message::calledParty, call_info_message::calledPartyName, skinny_data::callinfo, call_info_message::callingParty, call_info_message::callingPartyName, skinny_req::data, htolel, call_info_message::instance, call_info_message::reference, req_alloc(), s, skinnydebug, transmit_response(), and call_info_message::type.
Referenced by skinny_answer(), skinny_call(), and skinny_indicate().
01533 { 01534 struct skinny_req *req; 01535 01536 if (!(req = req_alloc(sizeof(struct call_info_message), CALL_INFO_MESSAGE))) 01537 return; 01538 01539 if (skinnydebug) 01540 ast_verbose("Setting Callinfo to %s(%s) from %s(%s) on %s(%d)\n", fromname, fromnum, toname, tonum, s->device->name, instance); 01541 01542 if (fromname) { 01543 ast_copy_string(req->data.callinfo.callingPartyName, fromname, sizeof(req->data.callinfo.callingPartyName)); 01544 } 01545 if (fromnum) { 01546 ast_copy_string(req->data.callinfo.callingParty, fromnum, sizeof(req->data.callinfo.callingParty)); 01547 } 01548 if (toname) { 01549 ast_copy_string(req->data.callinfo.calledPartyName, toname, sizeof(req->data.callinfo.calledPartyName)); 01550 } 01551 if (tonum) { 01552 ast_copy_string(req->data.callinfo.calledParty, tonum, sizeof(req->data.callinfo.calledParty)); 01553 } 01554 req->data.callinfo.instance = htolel(instance); 01555 req->data.callinfo.reference = htolel(callid); 01556 req->data.callinfo.type = htolel(calltype); 01557 transmit_response(s, req); 01558 }
static void transmit_callstate | ( | struct skinnysession * | s, | |
int | instance, | |||
int | state, | |||
unsigned | callid | |||
) | [static] |
Definition at line 1744 of file chan_skinny.c.
References ACTIVATE_CALL_PLANE_MESSAGE, skinny_data::activatecallplane, CALL_STATE_MESSAGE, call_state_message::callReference, call_state_message::callState, skinny_data::callstate, CLOSE_RECEIVE_CHANNEL_MESSAGE, skinny_data::closereceivechannel, stop_media_transmission_message::conferenceId, close_receive_channel_message::conferenceId, skinny_req::data, htolel, KEYDEF_ONHOOK, activate_call_plane_message::lineInstance, call_state_message::lineInstance, close_receive_channel_message::partyId, stop_media_transmission_message::passThruPartyId, req_alloc(), s, SKINNY_OFFHOOK, SKINNY_ONHOOK, SKINNY_SPEAKEROFF, STOP_MEDIA_TRANSMISSION_MESSAGE, skinny_data::stopmedia, transmit_displaypromptstatus(), transmit_response(), transmit_selectsoftkeys(), and transmit_speaker_mode().
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_onhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_answer(), skinny_call(), skinny_hangup(), and skinny_indicate().
01745 { 01746 struct skinny_req *req; 01747 01748 if (state == SKINNY_ONHOOK) { 01749 if (!(req = req_alloc(sizeof(struct close_receive_channel_message), CLOSE_RECEIVE_CHANNEL_MESSAGE))) 01750 return; 01751 01752 req->data.closereceivechannel.conferenceId = htolel(callid); 01753 req->data.closereceivechannel.partyId = htolel(callid); 01754 transmit_response(s, req); 01755 01756 if (!(req = req_alloc(sizeof(struct stop_media_transmission_message), STOP_MEDIA_TRANSMISSION_MESSAGE))) 01757 return; 01758 01759 req->data.stopmedia.conferenceId = htolel(callid); 01760 req->data.stopmedia.passThruPartyId = htolel(callid); 01761 transmit_response(s, req); 01762 01763 transmit_speaker_mode(s, SKINNY_SPEAKEROFF); 01764 01765 transmit_displaypromptstatus(s, NULL, 0, instance, callid); 01766 } 01767 01768 if (!(req = req_alloc(sizeof(struct call_state_message), CALL_STATE_MESSAGE))) 01769 return; 01770 01771 req->data.callstate.callState = htolel(state); 01772 req->data.callstate.lineInstance = htolel(instance); 01773 req->data.callstate.callReference = htolel(callid); 01774 transmit_response(s, req); 01775 01776 if (state == SKINNY_ONHOOK) { 01777 transmit_selectsoftkeys(s, 0, 0, KEYDEF_ONHOOK); 01778 } 01779 01780 if (state == SKINNY_OFFHOOK || state == SKINNY_ONHOOK) { 01781 if (!(req = req_alloc(sizeof(struct activate_call_plane_message), ACTIVATE_CALL_PLANE_MESSAGE))) 01782 return; 01783 01784 req->data.activatecallplane.lineInstance = htolel(instance); 01785 transmit_response(s, req); 01786 } 01787 }
static void transmit_connect | ( | struct skinnysession * | s, | |
struct skinny_subchannel * | sub | |||
) | [static] |
Definition at line 1560 of file chan_skinny.c.
References ast_best_codec(), ast_codec_pref_getsize(), open_receive_channel_message::bitrate, ast_format_list::bits, skinny_subchannel::callid, open_receive_channel_message::capability, skinny_line::capability, codec_ast2skinny(), open_receive_channel_message::conferenceId, ast_format_list::cur_ms, skinny_req::data, open_receive_channel_message::echo, htolel, OPEN_RECEIVE_CHANNEL_MESSAGE, skinny_data::openreceivechannel, open_receive_channel_message::packets, skinny_subchannel::parent, open_receive_channel_message::partyId, skinny_line::prefs, req_alloc(), s, skinny_line::sub, and transmit_response().
Referenced by skinny_unhold(), and start_rtp().
01561 { 01562 struct skinny_req *req; 01563 struct skinny_line *l = sub->parent; 01564 struct ast_format_list fmt; 01565 01566 if (!(req = req_alloc(sizeof(struct open_receive_channel_message), OPEN_RECEIVE_CHANNEL_MESSAGE))) 01567 return; 01568 01569 fmt = ast_codec_pref_getsize(&l->prefs, ast_best_codec(l->capability)); 01570 01571 req->data.openreceivechannel.conferenceId = htolel(sub->callid); 01572 req->data.openreceivechannel.partyId = htolel(sub->callid); 01573 req->data.openreceivechannel.packets = htolel(fmt.cur_ms); 01574 req->data.openreceivechannel.capability = htolel(codec_ast2skinny(fmt.bits)); 01575 req->data.openreceivechannel.echo = htolel(0); 01576 req->data.openreceivechannel.bitrate = htolel(0); 01577 transmit_response(s, req); 01578 }
static void transmit_dialednumber | ( | struct skinnysession * | s, | |
const char * | text, | |||
int | instance, | |||
int | callid | |||
) | [static] |
Definition at line 1730 of file chan_skinny.c.
References ast_copy_string(), dialed_number_message::callReference, skinny_req::data, DIALED_NUMBER_MESSAGE, dialed_number_message::dialedNumber, skinny_data::dialednumber, htolel, dialed_number_message::lineInstance, req_alloc(), s, and transmit_response().
Referenced by skinny_answer(), and skinny_indicate().
01731 { 01732 struct skinny_req *req; 01733 01734 if (!(req = req_alloc(sizeof(struct dialed_number_message), DIALED_NUMBER_MESSAGE))) 01735 return; 01736 01737 ast_copy_string(req->data.dialednumber.dialedNumber, text, sizeof(req->data.dialednumber.dialedNumber)); 01738 req->data.dialednumber.lineInstance = htolel(instance); 01739 req->data.dialednumber.callReference = htolel(callid); 01740 01741 transmit_response(s, req); 01742 }
static void transmit_displaymessage | ( | struct skinnysession * | s, | |
const char * | text, | |||
int | instance, | |||
int | reference | |||
) | [static] |
Definition at line 1660 of file chan_skinny.c.
References ast_copy_string(), ast_verbose(), clear_prompt_message::callReference, CLEAR_DISPLAY_MESSAGE, skinny_data::clearpromptstatus, skinny_req::data, skinny_data::displaytext, DISPLAYTEXT_MESSAGE, clear_prompt_message::lineInstance, req_alloc(), s, skinnydebug, displaytext_message::text, and transmit_response().
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), and handle_stimulus_message().
01661 { 01662 struct skinny_req *req; 01663 01664 if (text == 0) { 01665 if (!(req = req_alloc(0, CLEAR_DISPLAY_MESSAGE))) 01666 return; 01667 01668 req->data.clearpromptstatus.lineInstance = instance; 01669 req->data.clearpromptstatus.callReference = reference; 01670 01671 if (skinnydebug) 01672 ast_verbose("Clearing Display\n"); 01673 } else { 01674 if (!(req = req_alloc(sizeof(struct displaytext_message), DISPLAYTEXT_MESSAGE))) 01675 return; 01676 01677 ast_copy_string(req->data.displaytext.text, text, sizeof(req->data.displaytext.text)); 01678 if (skinnydebug) 01679 ast_verbose("Displaying message '%s'\n", req->data.displaytext.text); 01680 } 01681 01682 transmit_response(s, req); 01683 }
static void transmit_displaynotify | ( | struct skinnysession * | s, | |
const char * | text, | |||
int | t | |||
) | [static] |
Definition at line 1685 of file chan_skinny.c.
References ast_copy_string(), ast_verbose(), skinny_req::data, DISPLAY_NOTIFY_MESSAGE, display_notify_message::displayMessage, skinny_data::displaynotify, display_notify_message::displayTimeout, htolel, req_alloc(), s, skinnydebug, and transmit_response().
Referenced by handle_soft_key_event_message(), and handle_stimulus_message().
01686 { 01687 struct skinny_req *req; 01688 01689 if (!(req = req_alloc(sizeof(struct display_notify_message), DISPLAY_NOTIFY_MESSAGE))) 01690 return; 01691 01692 ast_copy_string(req->data.displaynotify.displayMessage, text, sizeof(req->data.displaynotify.displayMessage)); 01693 req->data.displaynotify.displayTimeout = htolel(t); 01694 01695 if (skinnydebug) 01696 ast_verbose("Displaying notify '%s'\n", text); 01697 01698 transmit_response(s, req); 01699 }
static void transmit_displaypromptstatus | ( | struct skinnysession * | s, | |
const char * | text, | |||
int | t, | |||
int | instance, | |||
int | callid | |||
) | [static] |
Definition at line 1701 of file chan_skinny.c.
References ast_copy_string(), ast_verbose(), display_prompt_status_message::callReference, clear_prompt_message::callReference, CLEAR_PROMPT_MESSAGE, skinny_data::clearpromptstatus, skinny_req::data, DISPLAY_PROMPT_STATUS_MESSAGE, skinny_data::displaypromptstatus, htolel, display_prompt_status_message::lineInstance, clear_prompt_message::lineInstance, display_prompt_status_message::messageTimeout, display_prompt_status_message::promptMessage, req_alloc(), s, skinnydebug, and transmit_response().
Referenced by handle_stimulus_message(), skinny_answer(), skinny_call(), skinny_indicate(), and transmit_callstate().
01702 { 01703 struct skinny_req *req; 01704 01705 if (text == 0) { 01706 if (!(req = req_alloc(sizeof(struct clear_prompt_message), CLEAR_PROMPT_MESSAGE))) 01707 return; 01708 01709 req->data.clearpromptstatus.lineInstance = htolel(instance); 01710 req->data.clearpromptstatus.callReference = htolel(callid); 01711 01712 if (skinnydebug) 01713 ast_verbose("Clearing Prompt\n"); 01714 } else { 01715 if (!(req = req_alloc(sizeof(struct display_prompt_status_message), DISPLAY_PROMPT_STATUS_MESSAGE))) 01716 return; 01717 01718 ast_copy_string(req->data.displaypromptstatus.promptMessage, text, sizeof(req->data.displaypromptstatus.promptMessage)); 01719 req->data.displaypromptstatus.messageTimeout = htolel(t); 01720 req->data.displaypromptstatus.lineInstance = htolel(instance); 01721 req->data.displaypromptstatus.callReference = htolel(callid); 01722 01723 if (skinnydebug) 01724 ast_verbose("Displaying Prompt Status '%s'\n", text); 01725 } 01726 01727 transmit_response(s, req); 01728 }
static void transmit_lamp_indication | ( | struct skinnysession * | s, | |
int | stimulus, | |||
int | instance, | |||
int | indication | |||
) | [static] |
Definition at line 1622 of file chan_skinny.c.
References skinny_req::data, set_lamp_message::deviceStimulus, htolel, req_alloc(), s, SET_LAMP_MESSAGE, skinny_data::setlamp, set_lamp_message::stimulus, set_lamp_message::stimulusInstance, and transmit_response().
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_call(), skinny_hangup(), skinny_hold(), and skinny_unhold().
01623 { 01624 struct skinny_req *req; 01625 01626 if (!(req = req_alloc(sizeof(struct set_lamp_message), SET_LAMP_MESSAGE))) 01627 return; 01628 01629 req->data.setlamp.stimulus = htolel(stimulus); 01630 req->data.setlamp.stimulusInstance = htolel(instance); 01631 req->data.setlamp.deviceStimulus = htolel(indication); 01632 transmit_response(s, req); 01633 }
static int transmit_response | ( | struct skinnysession * | s, | |
struct skinny_req * | req | |||
) | [static] |
Definition at line 1469 of file chan_skinny.c.
References ast_log(), ast_mutex_lock(), ast_mutex_unlock(), skinny_req::data, skinny_req::e, errno, skinny_req::len, letohl, LOG_VERBOSE, LOG_WARNING, s, skinny_header_size, SKINNY_MAX_PACKET, skinny_unregister(), and skinnydebug.
01470 { 01471 int res = 0; 01472 01473 if (!s) { 01474 ast_log(LOG_WARNING, "Asked to transmit to a non-existant session!\n"); 01475 return -1; 01476 } 01477 01478 ast_mutex_lock(&s->lock); 01479 01480 if (skinnydebug) 01481 ast_log(LOG_VERBOSE, "writing packet type %04X (%d bytes) to socket %d\n", letohl(req->e), letohl(req->len)+8, s->fd); 01482 01483 if (letohl(req->len > SKINNY_MAX_PACKET) || letohl(req->len < 0)) { 01484 ast_log(LOG_WARNING, "transmit_response: the length of the request is out of bounds\n"); 01485 ast_mutex_unlock(&s->lock); 01486 return -1; 01487 } 01488 01489 memset(s->outbuf,0,sizeof(s->outbuf)); 01490 memcpy(s->outbuf, req, skinny_header_size); 01491 memcpy(s->outbuf+skinny_header_size, &req->data, letohl(req->len)); 01492 01493 res = write(s->fd, s->outbuf, letohl(req->len)+8); 01494 01495 if (res != letohl(req->len)+8) { 01496 ast_log(LOG_WARNING, "Transmit: write only sent %d out of %d bytes: %s\n", res, letohl(req->len)+8, strerror(errno)); 01497 if (res == -1) { 01498 if (skinnydebug) 01499 ast_log(LOG_WARNING, "Transmit: Skinny Client was lost, unregistering\n"); 01500 skinny_unregister(NULL, s); 01501 } 01502 01503 } 01504 01505 ast_mutex_unlock(&s->lock); 01506 return 1; 01507 }
static void transmit_ringer_mode | ( | struct skinnysession * | s, | |
int | mode | |||
) | [static] |
Definition at line 1635 of file chan_skinny.c.
References ast_verbose(), skinny_req::data, htolel, req_alloc(), set_ringer_message::ringerMode, s, SET_RINGER_MESSAGE, skinny_data::setringer, skinnydebug, transmit_response(), set_ringer_message::unknown1, and set_ringer_message::unknown2.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_call(), and skinny_hangup().
01636 { 01637 struct skinny_req *req; 01638 01639 if (skinnydebug) 01640 ast_verbose("Setting ringer mode to '%d'.\n", mode); 01641 01642 if (!(req = req_alloc(sizeof(struct set_ringer_message), SET_RINGER_MESSAGE))) 01643 return; 01644 01645 req->data.setringer.ringerMode = htolel(mode); 01646 /* XXX okay, I don't quite know what this is, but here's what happens (on a 7960). 01647 Note: The phone will always show as ringing on the display. 01648 01649 1: phone will audibly ring over and over 01650 2: phone will audibly ring only once 01651 any other value, will NOT cause the phone to audibly ring 01652 */ 01653 req->data.setringer.unknown1 = htolel(1); 01654 /* XXX the value here doesn't seem to change anything. Must be higher than 0. 01655 Perhaps a packet capture can shed some light on this. */ 01656 req->data.setringer.unknown2 = htolel(1); 01657 transmit_response(s, req); 01658 }
static void transmit_selectsoftkeys | ( | struct skinnysession * | s, | |
int | instance, | |||
int | callid, | |||
int | softkey | |||
) | [static] |
Definition at line 1608 of file chan_skinny.c.
References skinny_req::data, htolel, select_soft_keys_message::instance, select_soft_keys_message::reference, req_alloc(), s, SELECT_SOFT_KEYS_MESSAGE, skinny_data::selectsoftkey, select_soft_keys_message::softKeySetIndex, transmit_response(), and select_soft_keys_message::validKeyMask.
Referenced by handle_offhook_message(), handle_soft_key_event_message(), handle_soft_key_set_req_message(), handle_stimulus_message(), skinny_answer(), skinny_call(), and transmit_callstate().
01609 { 01610 struct skinny_req *req; 01611 01612 if (!(req = req_alloc(sizeof(struct select_soft_keys_message), SELECT_SOFT_KEYS_MESSAGE))) 01613 return; 01614 01615 req->data.selectsoftkey.instance = htolel(instance); 01616 req->data.selectsoftkey.reference = htolel(callid); 01617 req->data.selectsoftkey.softKeySetIndex = htolel(softkey); 01618 req->data.selectsoftkey.validKeyMask = htolel(0xFFFFFFFF); 01619 transmit_response(s, req); 01620 }
static void transmit_speaker_mode | ( | struct skinnysession * | s, | |
int | mode | |||
) | [static] |
Definition at line 1509 of file chan_skinny.c.
References skinny_req::data, htolel, set_speaker_message::mode, req_alloc(), s, SET_SPEAKER_MESSAGE, skinny_data::setspeaker, and transmit_response().
Referenced by handle_soft_key_event_message(), handle_stimulus_message(), skinny_hangup(), and transmit_callstate().
01510 { 01511 struct skinny_req *req; 01512 01513 if (!(req = req_alloc(sizeof(struct set_speaker_message), SET_SPEAKER_MESSAGE))) 01514 return; 01515 01516 req->data.setspeaker.mode = htolel(mode); 01517 transmit_response(s, req); 01518 }
static void transmit_tone | ( | struct skinnysession * | s, | |
int | tone, | |||
int | instance, | |||
int | reference | |||
) | [static] |
Definition at line 1580 of file chan_skinny.c.
References skinny_req::data, htolel, stop_tone_message::instance, start_tone_message::instance, stop_tone_message::reference, start_tone_message::reference, req_alloc(), s, SKINNY_NOTONE, START_TONE_MESSAGE, skinny_data::starttone, STOP_TONE_MESSAGE, skinny_data::stoptone, start_tone_message::tone, and transmit_response().
Referenced by handle_enbloc_call_message(), handle_offhook_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_answer(), skinny_hangup(), skinny_indicate(), skinny_newcall(), skinny_senddigit_end(), and skinny_ss().
01581 { 01582 struct skinny_req *req; 01583 01584 if (tone == SKINNY_NOTONE) { 01585 /* This is bad, mmm'kay? */ 01586 return; 01587 } 01588 01589 if (tone > 0) { 01590 if (!(req = req_alloc(sizeof(struct start_tone_message), START_TONE_MESSAGE))) 01591 return; 01592 req->data.starttone.tone = htolel(tone); 01593 req->data.starttone.instance = htolel(instance); 01594 req->data.starttone.reference = htolel(reference); 01595 } else { 01596 if (!(req = req_alloc(sizeof(struct stop_tone_message), STOP_TONE_MESSAGE))) 01597 return; 01598 req->data.stoptone.instance = htolel(instance); 01599 req->data.stoptone.reference = htolel(reference); 01600 } 01601 01602 if (tone > 0) { 01603 req->data.starttone.tone = htolel(tone); 01604 } 01605 transmit_response(s, req); 01606 }
static int unload_module | ( | void | ) | [static] |
Definition at line 5021 of file chan_skinny.c.
References accept_t, skinny_subchannel::alreadygone, ast_channel_unregister(), ast_cli_unregister_multiple(), ast_mutex_destroy(), ast_mutex_lock(), ast_mutex_unlock(), AST_PTHREADT_NULL, AST_PTHREADT_STOP, ast_rtp_proto_unregister(), ast_softhangup(), AST_SOFTHANGUP_APPUNLOAD, cli_skinny, delete_devices(), skinnysession::device, skinnysession::fd, free, skinny_device::lines, skinnysession::lock, skinny_subchannel::lock, skinny_line::lock, monitor_thread, monlock, netlock, skinny_subchannel::next, skinny_line::next, skinny_device::next, skinny_subchannel::owner, s, sched_context_destroy(), sessionlock, skinny_rtp, skinny_tech, skinnysock, and skinny_line::sub.
05022 { 05023 struct skinnysession *s, *slast; 05024 struct skinny_device *d; 05025 struct skinny_line *l; 05026 struct skinny_subchannel *sub; 05027 05028 ast_mutex_lock(&sessionlock); 05029 /* Destroy all the interfaces and free their memory */ 05030 s = sessions; 05031 while(s) { 05032 slast = s; 05033 s = s->next; 05034 for (d = slast->device; d; d = d->next) { 05035 for (l = d->lines; l; l = l->next) { 05036 ast_mutex_lock(&l->lock); 05037 for (sub = l->sub; sub; sub = sub->next) { 05038 ast_mutex_lock(&sub->lock); 05039 if (sub->owner) { 05040 sub->alreadygone = 1; 05041 ast_softhangup(sub->owner, AST_SOFTHANGUP_APPUNLOAD); 05042 } 05043 ast_mutex_unlock(&sub->lock); 05044 } 05045 ast_mutex_unlock(&l->lock); 05046 } 05047 } 05048 if (slast->fd > -1) 05049 close(slast->fd); 05050 ast_mutex_destroy(&slast->lock); 05051 free(slast); 05052 } 05053 sessions = NULL; 05054 ast_mutex_unlock(&sessionlock); 05055 05056 delete_devices(); 05057 05058 ast_mutex_lock(&monlock); 05059 if ((monitor_thread != AST_PTHREADT_NULL) && (monitor_thread != AST_PTHREADT_STOP)) { 05060 pthread_cancel(monitor_thread); 05061 pthread_kill(monitor_thread, SIGURG); 05062 pthread_join(monitor_thread, NULL); 05063 } 05064 monitor_thread = AST_PTHREADT_STOP; 05065 ast_mutex_unlock(&monlock); 05066 05067 ast_mutex_lock(&netlock); 05068 if (accept_t && (accept_t != AST_PTHREADT_STOP)) { 05069 pthread_cancel(accept_t); 05070 pthread_kill(accept_t, SIGURG); 05071 pthread_join(accept_t, NULL); 05072 } 05073 accept_t = AST_PTHREADT_STOP; 05074 ast_mutex_unlock(&netlock); 05075 05076 ast_rtp_proto_unregister(&skinny_rtp); 05077 ast_channel_unregister(&skinny_tech); 05078 ast_cli_unregister_multiple(cli_skinny, sizeof(cli_skinny) / sizeof(struct ast_cli_entry)); 05079 05080 close(skinnysock); 05081 if (sched) 05082 sched_context_destroy(sched); 05083 05084 return 0; 05085 }
struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT | AST_MODFLAG_BUILDSUM, .description = "Skinny Client Control Protocol (Skinny)" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "361d7bb937402d51e4658efb5b4d76e4" , .load = load_module, .unload = unload_module, } [static] |
Definition at line 5090 of file chan_skinny.c.
struct in_addr __ourip [static] |
Definition at line 790 of file chan_skinny.c.
pthread_t accept_t [static] |
char accountcode[AST_MAX_ACCOUNT_CODE] = "" [static] |
Definition at line 814 of file chan_skinny.c.
struct ast_hostent ahp |
Definition at line 791 of file chan_skinny.c.
Referenced by __ast_http_load(), __set_address_from_contact(), ast_dnsmgr_lookup(), ast_find_ourip(), ast_get_ip_or_srv(), ast_sip_ouraddrfor(), check_via(), create_addr(), dnsmgr_refresh(), festival_exec(), gtalk_load_config(), gtalk_update_stun(), launch_netscript(), parse_register_contact(), process_sdp(), process_via(), realtime_peer(), realtime_user(), reload_config(), rtcp_do_debug_ip(), rtcp_do_debug_ip_deprecated(), rtp_do_debug_ip(), set_destination(), sip_devicestate(), sip_do_debug_ip(), and udptl_do_debug_ip().
int amaflags = 0 [static] |
Definition at line 816 of file chan_skinny.c.
const struct ast_module_info* ast_module_info = &__mod_info [static] |
Definition at line 5090 of file chan_skinny.c.
int auth_limit = DEFAULT_AUTH_LIMIT [static] |
int auth_timeout = DEFAULT_AUTH_TIMEOUT [static] |
struct sockaddr_in bindaddr [static] |
Definition at line 787 of file chan_skinny.c.
int callnums = 1 [static] |
int callreturn = 0 [static] |
Definition at line 807 of file chan_skinny.c.
int callwaiting = 0 [static] |
Definition at line 806 of file chan_skinny.c.
int cancallforward = 0 [static] |
Definition at line 812 of file chan_skinny.c.
char cid_name[AST_MAX_EXTENSION] = "" [static] |
Definition at line 800 of file chan_skinny.c.
char cid_num[AST_MAX_EXTENSION] = "" [static] |
Definition at line 799 of file chan_skinny.c.
struct ast_cli_entry cli_skinny[] [static] |
const char config[] = "skinny.conf" [static] |
Definition at line 81 of file chan_skinny.c.
char context[AST_MAX_CONTEXT] = "default" [static] |
Definition at line 795 of file chan_skinny.c.
struct ast_threadstorage control2str_threadbuf = { .once = PTHREAD_ONCE_INIT , .key_init = control2str_threadbuf_init , } [static] |
ast_group_t cur_callergroup = 0 [static] |
Definition at line 803 of file chan_skinny.c.
ast_group_t cur_pickupgroup = 0 [static] |
Definition at line 804 of file chan_skinny.c.
char date_format[6] = "D-M-Y" [static] |
Definition at line 106 of file chan_skinny.c.
Referenced by handle_register_message(), and reload_config().
char debug_usage[] [static] |
Initial value:
"Usage: skinny set debug\n" " Enables dumping of Skinny packets for debugging purposes\n"
Definition at line 2097 of file chan_skinny.c.
int default_capability = AST_FORMAT_ULAW | AST_FORMAT_ALAW [static] |
Definition at line 83 of file chan_skinny.c.
Referenced by build_device(), reload_config(), and skinny_new().
struct ast_jb_conf default_jbconf [static] |
Global jitterbuffer configuration - by default, jb is disabled
Definition at line 134 of file chan_skinny.c.
struct ast_codec_pref default_prefs [static] |
Definition at line 84 of file chan_skinny.c.
struct ast_threadstorage device2str_threadbuf = { .once = PTHREAD_ONCE_INIT , .key_init = device2str_threadbuf_init , } [static] |
ast_mutex_t devicelock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) [static] |
Definition at line 931 of file chan_skinny.c.
Referenced by delete_devices(), find_line_by_name(), handle_line_state_req_message(), reload_config(), skinny_register(), skinny_reset_device(), skinny_show_devices(), and skinny_show_lines().
struct skinny_device * devices [static] |
int firstdigittimeout = 16000 [static] |
Definition at line 942 of file chan_skinny.c.
int gendigittimeout = 8000 [static] |
Definition at line 945 of file chan_skinny.c.
struct ast_jb_conf global_jbconf [static] |
Definition at line 141 of file chan_skinny.c.
struct hostent* hp |
Definition at line 792 of file chan_skinny.c.
Referenced by __ast_http_load(), __set_address_from_contact(), ast_dnsmgr_lookup(), ast_find_ourip(), ast_get_ip_or_srv(), ast_gethostbyname(), ast_sip_ouraddrfor(), build_peer(), check_via(), connect_sphinx(), create_addr(), dnsmgr_refresh(), get_ip_and_port_from_sdp(), gtalk_load_config(), gtalk_update_stun(), iax_template_parse(), launch_netscript(), parse_register_contact(), process_sdp(), process_sdp_c(), process_via(), realtime_peer(), realtime_user(), reload_config(), rtcp_do_debug_ip(), rtcp_do_debug_ip_deprecated(), rtp_do_debug_ip(), set_config(), set_destination(), sip_devicestate(), sip_do_debug_ip(), and udptl_do_debug_ip().
int immediate = 0 [static] |
Definition at line 805 of file chan_skinny.c.
struct io_context* io [static] |
Definition at line 921 of file chan_skinny.c.
int keep_alive = 120 [static] |
Definition at line 102 of file chan_skinny.c.
Referenced by get_input(), handle_register_message(), and reload_config().
char language[MAX_LANGUAGE] = "" [static] |
Definition at line 796 of file chan_skinny.c.
char linelabel[AST_MAX_EXTENSION] = "" [static] |
char mailbox[AST_MAX_EXTENSION] [static] |
Definition at line 815 of file chan_skinny.c.
int matchdigittimeout = 3000 [static] |
Definition at line 948 of file chan_skinny.c.
char mohinterpret[MAX_MUSICCLASS] = "default" [static] |
Definition at line 797 of file chan_skinny.c.
char mohsuggest[MAX_MUSICCLASS] = "" [static] |
Definition at line 798 of file chan_skinny.c.
pthread_t monitor_thread = AST_PTHREADT_NULL [static] |
Definition at line 939 of file chan_skinny.c.
ast_mutex_t monlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) [static] |
Definition at line 925 of file chan_skinny.c.
int mwiblink = 0 [static] |
int nat = 0 [static] |
Definition at line 802 of file chan_skinny.c.
ast_mutex_t netlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) [static] |
Definition at line 927 of file chan_skinny.c.
char no_debug_usage[] [static] |
Initial value:
"Usage: skinny set debug off\n" " Disables dumping of Skinny packets for debugging purposes\n"
Definition at line 2101 of file chan_skinny.c.
char ourhost[256] [static] |
Definition at line 788 of file chan_skinny.c.
int ourport [static] |
Definition at line 789 of file chan_skinny.c.
char reset_usage[] [static] |
Initial value:
"Usage: skinny reset <DeviceId|all> [restart]\n" " Causes a Skinny device to reset itself, optionally with a full restart\n"
Definition at line 2105 of file chan_skinny.c.
struct sched_context* sched = NULL [static] |
Definition at line 920 of file chan_skinny.c.
ast_mutex_t sessionlock = ((ast_mutex_t) PTHREAD_MUTEX_INITIALIZER ) [static] |
Definition at line 929 of file chan_skinny.c.
Referenced by accept_thread(), destroy_session(), and unload_module().
struct skinnysession * sessions [static] |
char show_devices_usage[] [static] |
Initial value:
"Usage: skinny show devices\n" " Lists all devices known to the Skinny subsystem.\n"
Definition at line 2089 of file chan_skinny.c.
char show_lines_usage[] [static] |
Initial value:
"Usage: skinny show lines\n" " Lists all lines known to the Skinny subsystem.\n"
Definition at line 2093 of file chan_skinny.c.
int skinny_header_size = 12 |
Definition at line 778 of file chan_skinny.c.
Referenced by skinny_req_parse(), and transmit_response().
struct ast_rtp_protocol skinny_rtp [static] |
struct ast_channel_tech skinny_tech [static] |
Definition at line 1089 of file chan_skinny.c.
Referenced by load_module(), skinny_new(), and unload_module().
int skinnydebug = 0 [static] |
Definition at line 784 of file chan_skinny.c.
Referenced by accept_thread(), get_input(), handle_alarm_message(), handle_capabilities_res_message(), handle_enbloc_call_message(), handle_keypad_button_message(), handle_message(), handle_offhook_message(), handle_onhook_message(), handle_open_receive_channel_ack_message(), handle_register_message(), handle_soft_key_event_message(), handle_stimulus_message(), skinny_answer(), skinny_call(), skinny_do_debug(), skinny_hangup(), skinny_hold(), skinny_indicate(), skinny_new(), skinny_no_debug(), skinny_unhold(), transmit_callinfo(), transmit_displaymessage(), transmit_displaynotify(), transmit_displaypromptstatus(), transmit_response(), and transmit_ringer_mode().
int skinnysock = -1 [static] |
Definition at line 793 of file chan_skinny.c.
Referenced by accept_thread(), reload_config(), and unload_module().
const uint8_t soft_key_default_connected[] [static] |
Definition at line 576 of file chan_skinny.c.
const uint8_t soft_key_default_connwithconf[] [static] |
const uint8_t soft_key_default_connwithtrans[] [static] |
Definition at line 606 of file chan_skinny.c.
const uint8_t soft_key_default_dadfd[] [static] |
struct soft_key_definitions soft_key_default_definitions[] [static] |
const uint8_t soft_key_default_offhook[] [static] |
Definition at line 598 of file chan_skinny.c.
const uint8_t soft_key_default_offhookwithfeat[] [static] |
const uint8_t soft_key_default_onhold[] [static] |
Definition at line 585 of file chan_skinny.c.
const uint8_t soft_key_default_onhook[] [static] |
Definition at line 567 of file chan_skinny.c.
const uint8_t soft_key_default_ringin[] [static] |
Initial value:
Definition at line 592 of file chan_skinny.c.
const uint8_t soft_key_default_ringout[] [static] |
const uint8_t soft_key_default_unknown[] [static] |
Definition at line 540 of file chan_skinny.c.
Referenced by handle_soft_key_set_req_message(), handle_soft_key_template_req_message(), and load_module().
const char tdesc[] = "Skinny Client Control Protocol (Skinny)" [static] |
Definition at line 80 of file chan_skinny.c.
int threewaycalling = 0 [static] |
Definition at line 808 of file chan_skinny.c.
int transfer = 0 [static] |
Definition at line 811 of file chan_skinny.c.
int unauth_sessions = 0 [static] |
Definition at line 105 of file chan_skinny.c.
char version_id[16] = "P002F202" [static] |