2 * Asterisk -- An open source telephony toolkit.
4 * Copyright (C) 2006, Digium, Inc.
6 * See http://www.asterisk.org for more information about
7 * the Asterisk project. Please do not directly contact
8 * any of the maintainers of this project for assistance;
9 * the project provides a web site, mailing lists and IRC
10 * channels for your use.
12 * This program is free software, distributed under the terms of
13 * the GNU General Public License Version 2. See the LICENSE file
14 * at the top of the source tree.
19 * \brief Channel info dialplan function
21 * \author Kevin P. Fleming <kpfleming@digium.com>
27 ASTERISK_FILE_VERSION(__FILE__
, "$Revision$")
32 #include <sys/types.h>
34 #include "asterisk/module.h"
35 #include "asterisk/channel.h"
36 #include "asterisk/pbx.h"
37 #include "asterisk/logger.h"
38 #include "asterisk/utils.h"
39 #include "asterisk/app.h"
40 #include "asterisk/indications.h"
41 #include "asterisk/stringfields.h"
43 #define locked_copy_string(chan, dest, source, len) \
45 ast_channel_lock(chan); \
46 ast_copy_string(dest, source, len); \
47 ast_channel_unlock(chan); \
49 #define locked_string_field_set(chan, field, source) \
51 ast_channel_lock(chan); \
52 ast_string_field_set(chan, field, source); \
53 ast_channel_unlock(chan); \
56 char *transfercapability_table
[0x20] = {
57 "SPEECH", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK",
58 "DIGITAL", "RESTRICTED_DIGITAL", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK",
59 "3K1AUDIO", "DIGITAL_W_TONES", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK",
60 "VIDEO", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK", "UNK", };
62 static int func_channel_read(struct ast_channel
*chan
, char *function
,
63 char *data
, char *buf
, size_t len
)
67 if (!strcasecmp(data
, "audionativeformat"))
68 /* use the _multiple version when chan->nativeformats holds multiple formats */
69 /* ast_getformatname_multiple(buf, len, chan->nativeformats & AST_FORMAT_AUDIO_MASK); */
70 ast_copy_string(buf
, ast_getformatname(chan
->nativeformats
& AST_FORMAT_AUDIO_MASK
), len
);
71 else if (!strcasecmp(data
, "videonativeformat"))
72 /* use the _multiple version when chan->nativeformats holds multiple formats */
73 /* ast_getformatname_multiple(buf, len, chan->nativeformats & AST_FORMAT_VIDEO_MASK); */
74 ast_copy_string(buf
, ast_getformatname(chan
->nativeformats
& AST_FORMAT_VIDEO_MASK
), len
);
75 else if (!strcasecmp(data
, "audioreadformat"))
76 ast_copy_string(buf
, ast_getformatname(chan
->readformat
), len
);
77 else if (!strcasecmp(data
, "audiowriteformat"))
78 ast_copy_string(buf
, ast_getformatname(chan
->writeformat
), len
);
79 else if (!strcasecmp(data
, "tonezone") && chan
->zone
)
80 locked_copy_string(chan
, buf
, chan
->zone
->country
, len
);
81 else if (!strcasecmp(data
, "language"))
82 locked_copy_string(chan
, buf
, chan
->language
, len
);
83 else if (!strcasecmp(data
, "musicclass"))
84 locked_copy_string(chan
, buf
, chan
->musicclass
, len
);
85 else if (!strcasecmp(data
, "state"))
86 locked_copy_string(chan
, buf
, ast_state2str(chan
->_state
), len
);
87 else if (!strcasecmp(data
, "channeltype"))
88 locked_copy_string(chan
, buf
, chan
->tech
->type
, len
);
89 else if (!strcasecmp(data
, "transfercapability"))
90 locked_copy_string(chan
, buf
, transfercapability_table
[chan
->transfercapability
& 0x1f], len
);
91 else if (!strcasecmp(data
, "callgroup")) {
93 locked_copy_string(chan
, buf
, ast_print_group(groupbuf
, sizeof(groupbuf
), chan
->callgroup
), len
);
94 } else if (!chan
->tech
->func_channel_read
95 || chan
->tech
->func_channel_read(chan
, function
, data
, buf
, len
)) {
96 ast_log(LOG_WARNING
, "Unknown or unavailable item requested: '%s'\n", data
);
103 static int func_channel_write(struct ast_channel
*chan
, char *function
,
104 char *data
, const char *value
)
109 if (!strcasecmp(data
, "language"))
110 locked_string_field_set(chan
, language
, value
);
111 else if (!strcasecmp(data
, "musicclass"))
112 locked_string_field_set(chan
, musicclass
, value
);
113 else if (!strcasecmp(data
, "tonezone")) {
114 struct tone_zone
*new_zone
;
115 if (!(new_zone
= ast_get_indication_zone(value
))) {
116 ast_log(LOG_ERROR
, "Unknown country code '%s' for tonezone. Check indications.conf for available country codes.\n", value
);
119 chan
->zone
= new_zone
;
120 } else if (!strcasecmp(data
, "callgroup"))
121 chan
->callgroup
= ast_get_group(value
);
122 else if (!strcasecmp(data
, "txgain")) {
123 sscanf(value
, "%hhd", &gainset
);
124 ast_channel_setoption(chan
, AST_OPTION_TXGAIN
, &gainset
, sizeof(gainset
), 0);
125 } else if (!strcasecmp(data
, "rxgain")) {
126 sscanf(value
, "%hhd", &gainset
);
127 ast_channel_setoption(chan
, AST_OPTION_RXGAIN
, &gainset
, sizeof(gainset
), 0);
128 } else if (!strcasecmp(data
, "transfercapability")) {
130 for (i
= 0; i
< 0x20; i
++) {
131 if (!strcasecmp(transfercapability_table
[i
], value
) && strcmp(value
, "UNK")) {
132 chan
->transfercapability
= i
;
136 } else if (!chan
->tech
->func_channel_write
137 || chan
->tech
->func_channel_write(chan
, function
, data
, value
)) {
138 ast_log(LOG_WARNING
, "Unknown or unavailable item requested: '%s'\n",
146 static struct ast_custom_function channel_function
= {
148 .synopsis
= "Gets/sets various pieces of information about the channel.",
149 .syntax
= "CHANNEL(item)",
150 .desc
= "Gets/set various pieces of information about the channel.\n"
151 "Standard items (provided by all channel technologies) are:\n"
152 "R/O audioreadformat format currently being read\n"
153 "R/O audionativeformat format used natively for audio\n"
154 "R/O audiowriteformat format currently being written\n"
155 "R/W callgroup call groups for call pickup\n"
156 "R/O channeltype technology used for channel\n"
157 "R/W language language for sounds played\n"
158 "R/W musicclass class (from musiconhold.conf) for hold music\n"
159 "R/W rxgain set rxgain level on channel drivers that support it\n"
160 "R/O state state for channel\n"
161 "R/W tonezone zone for indications played\n"
162 "R/W txgain set txgain level on channel drivers that support it\n"
163 "R/O videonativeformat format used natively for video\n"
165 "chan_sip provides the following additional options:\n"
166 "R/O rtpqos Get QOS information about the RTP stream\n"
167 " This option takes two additional arguments:\n"
169 " audio Get data about the audio stream\n"
170 " video Get data about the video stream\n"
172 " local_ssrc Local SSRC (stream ID)\n"
173 " local_lostpackets Local lost packets\n"
174 " local_jitter Local calculated jitter\n"
175 " local_count Number of received packets\n"
176 " remote_ssrc Remote SSRC (stream ID)\n"
177 " remote_lostpackets Remote lost packets\n"
178 " remote_jitter Remote reported jitter\n"
179 " remote_count Number of transmitted packets\n"
180 " rtt Round trip time\n"
181 " all All statistics (in a form suited to logging, but not for parsing)\n"
183 "Additional items may be available from the channel driver providing\n"
184 "the channel; see its documentation for details.\n"
186 "Any item requested that is not available on the current channel will\n"
187 "return an empty string.\n",
188 .read
= func_channel_read
,
189 .write
= func_channel_write
,
192 static int unload_module(void)
194 return ast_custom_function_unregister(&channel_function
);
197 static int load_module(void)
199 return ast_custom_function_register(&channel_function
);
202 AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY
, "Channel information dialplan function");