65 #include <portaudio.h>
75 #include "asterisk/stasis_channels.h"
84 #define SAMPLE_RATE 16000
96 #define NUM_SAMPLES 320
99 #define INPUT_CHANNELS 1
102 #define OUTPUT_CHANNELS 1
109 #define TEXT_SIZE 256
112 #define V_BEGIN " --- <(\"<) --- "
113 #define V_END " --- (>\")> ---\n"
172 AST_MUTEX_DEFINE_STATIC(globals_lock);
175 #define NUM_PVT_BUCKETS 7
178 AST_RWLOCK_DEFINE_STATIC(active_lock);
189 .resync_threshold = 1000,
198 static int console_digit_begin(
struct ast_channel *c,
char digit);
199 static int console_digit_end(
struct ast_channel *c,
char digit,
unsigned int duration);
200 static int console_text(
struct ast_channel *c,
const char *text);
204 static int console_call(
struct ast_channel *c,
const char *dest,
int timeout);
206 static int console_indicate(
struct ast_channel *chan,
int cond,
213 .description =
"Console Channel Driver",
215 .send_digit_begin = console_digit_begin,
216 .send_digit_end = console_digit_end,
217 .send_text = console_text,
218 .hangup = console_hangup,
219 .answer = console_answer,
221 .call = console_call,
222 .write = console_write,
223 .indicate = console_indicate,
224 .fixup = console_fixup,
228 #define console_pvt_lock(pvt) ao2_lock(pvt)
231 #define console_pvt_unlock(pvt) ao2_unlock(pvt)
273 .src =
"console_stream_monitor",
275 .datalen =
sizeof(buf),
276 .
samples =
sizeof(buf) /
sizeof(int16_t),
281 res = Pa_ReadStream(pvt->
stream, buf,
sizeof(buf) /
sizeof(int16_t));
288 if (res == paNoError) {
291 ast_log(LOG_WARNING,
"Console ReadStream failed: %s\n", Pa_GetErrorText(res));
300 int res = paInternalError;
302 if (!strcasecmp(pvt->input_device,
"default") &&
303 !strcasecmp(pvt->output_device,
"default")) {
307 PaStreamParameters input_params = {
309 .sampleFormat = paInt16,
310 .suggestedLatency = (1.0 / 50.0),
311 .device = paNoDevice,
313 PaStreamParameters output_params = {
315 .sampleFormat = paInt16,
316 .suggestedLatency = (1.0 / 50.0),
317 .device = paNoDevice,
319 PaDeviceIndex idx, num_devices, def_input, def_output;
321 if (!(num_devices = Pa_GetDeviceCount()))
324 def_input = Pa_GetDefaultInputDevice();
325 def_output = Pa_GetDefaultOutputDevice();
328 idx < num_devices && (input_params.device == paNoDevice
329 || output_params.device == paNoDevice);
332 const PaDeviceInfo *dev = Pa_GetDeviceInfo(idx);
334 if (dev->maxInputChannels) {
335 if ( (idx == def_input && !strcasecmp(pvt->input_device,
"default")) ||
336 !strcasecmp(pvt->input_device, dev->name) )
337 input_params.device = idx;
340 if (dev->maxOutputChannels) {
341 if ( (idx == def_output && !strcasecmp(pvt->output_device,
"default")) ||
342 !strcasecmp(pvt->output_device, dev->name) )
343 output_params.device = idx;
347 if (input_params.device == paNoDevice)
348 ast_log(LOG_ERROR,
"No input device found for console device '%s'\n", pvt->
name);
349 if (output_params.device == paNoDevice)
350 ast_log(LOG_ERROR,
"No output device found for console device '%s'\n", pvt->
name);
352 res = Pa_OpenStream(&pvt->
stream, &input_params, &output_params,
375 res = open_stream(pvt);
376 if (res != paNoError) {
377 ast_log(LOG_WARNING,
"Failed to open stream - (%d) %s\n",
378 res, Pa_GetErrorText(res));
383 res = Pa_StartStream(pvt->
stream);
384 if (res != paNoError) {
385 ast_log(LOG_WARNING,
"Failed to start stream - (%d) %s\n",
386 res, Pa_GetErrorText(res));
392 ast_log(LOG_ERROR,
"Failed to start stream monitor thread\n");
409 pthread_kill(pvt->
thread, SIGURG);
410 pthread_join(pvt->
thread, NULL);
413 Pa_AbortStream(pvt->
stream);
414 Pa_CloseStream(pvt->
stream);
436 ext, ctx, assignedids, requestor, 0,
"Console/%s", pvt->
name))) {
443 ast_channel_tech_set(chan, &console_tech);
447 ast_channel_nativeformats_set(chan, caps);
449 ast_channel_tech_pvt_set(chan, ref_pvt(pvt));
453 if (!ast_strlen_zero(pvt->
language))
454 ast_channel_language_set(chan, pvt->
language);
459 ast_channel_unlock(chan);
463 ast_channel_hangupcause_set(chan, AST_CAUSE_SWITCH_CONGESTION);
478 if (!(pvt = find_pvt(data))) {
479 ast_log(LOG_ERROR,
"Console device '%s' not found\n", data);
485 ast_log(LOG_NOTICE,
"Channel requested with unsupported format(s): '%s'\n",
491 ast_log(LOG_NOTICE,
"Console channel already active!\n");
492 *cause = AST_CAUSE_BUSY;
501 ast_log(LOG_WARNING,
"Unable to create new Console channel!\n");
509 static int console_digit_begin(
struct ast_channel *c,
char digit)
511 ast_verb(1,
V_BEGIN "Console Received Beginning of Digit %c" V_END, digit);
516 static int console_digit_end(
struct ast_channel *c,
char digit,
unsigned int duration)
518 ast_verb(1,
V_BEGIN "Console Received End of Digit %c (duration %u)" V_END,
524 static int console_text(
struct ast_channel *c,
const char *text)
526 ast_verb(1,
V_BEGIN "Console Received Text '%s'" V_END, text);
535 ast_verb(1,
V_BEGIN "Hangup on Console" V_END);
541 ast_channel_tech_pvt_set(c, unref_pvt(pvt));
550 ast_verb(1,
V_BEGIN "Call from Console has been Answered" V_END);
554 return start_stream(pvt);
579 ast_debug(1,
"I should not be called ...\n");
584 static int console_call(
struct ast_channel *c,
const char *dest,
int timeout)
589 ast_verb(1,
V_BEGIN "Call to device '%s' on console from '%s' <%s>" V_END,
591 S_COR(ast_channel_caller(c)->
id.
name.valid, ast_channel_caller(c)->
id.
name.str,
""),
592 S_COR(ast_channel_caller(c)->
id.
number.valid, ast_channel_caller(c)->
id.
number.str,
""));
599 ast_verb(1,
V_BEGIN "Auto-answered" V_END);
603 ast_verb(1,
V_BEGIN "Type 'console answer' to answer, or use the 'autoanswer' option "
604 "for future calls" V_END);
611 return start_stream(pvt);
616 struct console_pvt *pvt = ast_channel_tech_pvt(chan);
625 static int console_indicate(
struct ast_channel *chan,
int cond,
const void *data,
size_t datalen)
627 struct console_pvt *pvt = ast_channel_tech_pvt(chan);
645 ast_verb(1,
V_BEGIN "Console Has Been Placed on Hold" V_END);
649 ast_verb(1,
V_BEGIN "Console Has Been Retrieved from Hold" V_END);
653 ast_log(LOG_WARNING,
"Don't know how to display condition %d on %s\n",
654 cond, ast_channel_name(chan));
664 struct console_pvt *pvt = ast_channel_tech_pvt(newchan);
666 pvt->
owner = newchan;
684 if (ext == NULL || ctx == NULL)
689 if (src && *src !=
'\0')
697 *ctx = strrchr(*ext,
'@');
709 ast_rwlock_rdlock(&active_lock);
710 pvt = ref_pvt(active_pvt);
711 ast_rwlock_unlock(&active_lock);
716 static char *cli_console_autoanswer(
struct ast_cli_entry *e,
int cmd,
720 char *res = CLI_SUCCESS;
724 e->
command =
"console {set|show} autoanswer [on|off]";
726 "Usage: console {set|show} autoanswer [on|off]\n"
727 " Enables or disables autoanswer feature. If used without\n"
728 " argument, displays the current on/off status of autoanswer.\n"
729 " The default value of autoanswer is in 'oss.conf'.\n";
736 pvt = get_active_pvt();
738 ast_cli(a->fd,
"No console device is set as active.\n");
742 if (a->argc == e->
args - 1) {
743 ast_cli(a->fd,
"Auto answer is %s.\n", pvt->
autoanswer ?
"on" :
"off");
748 if (a->argc != e->
args) {
750 return CLI_SHOWUSAGE;
753 if (!strcasecmp(a->argv[e->
args-1],
"on"))
755 else if (!strcasecmp(a->argv[e->
args - 1],
"off"))
769 if (cmd == CLI_INIT) {
772 "Usage: console flash\n"
773 " Flashes the call currently placed on the console.\n";
775 }
else if (cmd == CLI_GENERATE) {
779 if (a->argc != e->
args) {
780 return CLI_SHOWUSAGE;
783 pvt = get_active_pvt();
785 ast_cli(a->fd,
"No console device is set as active\n");
790 ast_cli(a->fd,
"No call to flash\n");
807 const char *mye = NULL, *myc = NULL;
810 if (cmd == CLI_INIT) {
813 "Usage: console dial [extension[@context]]\n"
814 " Dials a given extension (and context if specified)\n";
816 }
else if (cmd == CLI_GENERATE) {
820 if (a->argc > e->
args + 1) {
821 return CLI_SHOWUSAGE;
824 pvt = get_active_pvt();
826 ast_cli(a->fd,
"No console device is currently set as active\n");
835 if (a->argc == e->
args) {
836 ast_cli(a->fd,
"Already in a call. You can only dial digits until you hangup.\n");
840 s = a->argv[e->
args];
842 for (i = 0; i < strlen(s); i++) {
851 if (a->argc == e->
args + 1) {
852 char *ext = NULL, *con = NULL;
856 ast_debug(1,
"provided '%s', exten '%s' context '%s'\n",
857 a->argv[e->
args], mye, myc);
861 if (ast_strlen_zero(mye))
863 if (ast_strlen_zero(myc))
872 ast_cli(a->fd,
"No such extension '%s' in context '%s'\n", mye, myc);
885 if (cmd == CLI_INIT) {
888 "Usage: console hangup\n"
889 " Hangs up any call currently placed on the console.\n";
891 }
else if (cmd == CLI_GENERATE) {
895 if (a->argc != e->
args) {
896 return CLI_SHOWUSAGE;
899 pvt = get_active_pvt();
901 ast_cli(a->fd,
"No console device is set as active\n");
906 ast_cli(a->fd,
"No call to hang up\n");
924 char *res = CLI_SUCCESS;
926 if (cmd == CLI_INIT) {
927 e->
command =
"console {mute|unmute}";
929 "Usage: console {mute|unmute}\n"
930 " Mute/unmute the microphone.\n";
932 }
else if (cmd == CLI_GENERATE) {
936 if (a->argc != e->
args) {
937 return CLI_SHOWUSAGE;
940 pvt = get_active_pvt();
942 ast_cli(a->fd,
"No console device is set as active\n");
946 s = a->argv[e->
args-1];
947 if (!strcasecmp(s,
"mute"))
949 else if (!strcasecmp(s,
"unmute"))
954 ast_verb(1,
V_BEGIN "The Console is now %s" V_END,
955 pvt->
muted ?
"Muted" :
"Unmuted");
964 PaDeviceIndex idx, num, def_input, def_output;
966 if (cmd == CLI_INIT) {
967 e->
command =
"console list available";
969 "Usage: console list available\n"
970 " List all available devices.\n";
972 }
else if (cmd == CLI_GENERATE)
975 if (a->argc != e->
args)
976 return CLI_SHOWUSAGE;
979 "=============================================================\n"
980 "=== Available Devices =======================================\n"
981 "=============================================================\n"
984 num = Pa_GetDeviceCount();
986 ast_cli(a->fd,
"(None)\n");
990 def_input = Pa_GetDefaultInputDevice();
991 def_output = Pa_GetDefaultOutputDevice();
992 for (idx = 0; idx < num; idx++) {
993 const PaDeviceInfo *dev = Pa_GetDeviceInfo(idx);
996 ast_cli(a->fd,
"=== ---------------------------------------------------------\n"
997 "=== Device Name: %s\n", dev->name);
998 if (dev->maxInputChannels)
999 ast_cli(a->fd,
"=== ---> %sInput Device\n", (idx == def_input) ?
"Default " :
"");
1000 if (dev->maxOutputChannels)
1001 ast_cli(a->fd,
"=== ---> %sOutput Device\n", (idx == def_output) ?
"Default " :
"");
1002 ast_cli(a->fd,
"=== ---------------------------------------------------------\n===\n");
1005 ast_cli(a->fd,
"=============================================================\n\n");
1015 if (cmd == CLI_INIT) {
1016 e->
command =
"console list devices";
1018 "Usage: console list devices\n"
1019 " List all configured devices.\n";
1021 }
else if (cmd == CLI_GENERATE)
1024 if (a->argc != e->
args)
1025 return CLI_SHOWUSAGE;
1028 "=============================================================\n"
1029 "=== Configured Devices ======================================\n"
1030 "=============================================================\n"
1034 while ((pvt = ao2_iterator_next(&i))) {
1037 ast_cli(a->fd,
"=== ---------------------------------------------------------\n"
1038 "=== Device Name: %s\n"
1039 "=== ---> Active: %s\n"
1040 "=== ---> Input Device: %s\n"
1041 "=== ---> Output Device: %s\n"
1042 "=== ---> Context: %s\n"
1043 "=== ---> Extension: %s\n"
1044 "=== ---> CallerID Num: %s\n"
1045 "=== ---> CallerID Name: %s\n"
1046 "=== ---> MOH Interpret: %s\n"
1047 "=== ---> Language: %s\n"
1048 "=== ---> Parkinglot: %s\n"
1049 "=== ---> Muted: %s\n"
1050 "=== ---> Auto-Answer: %s\n"
1051 "=== ---> Override Context: %s\n"
1052 "=== ---------------------------------------------------------\n===\n",
1053 pvt->
name, (pvt == active_pvt) ?
"Yes" :
"No",
1054 pvt->input_device, pvt->output_device, pvt->
context,
1064 ast_cli(a->fd,
"=============================================================\n\n");
1077 e->
command =
"console answer";
1079 "Usage: console answer\n"
1080 " Answers an incoming call on the console channel.\n";
1087 pvt = get_active_pvt();
1089 ast_cli(a->fd,
"No console device is set as active\n");
1093 if (a->argc != e->
args) {
1095 return CLI_SHOWUSAGE;
1099 ast_cli(a->fd,
"No one is calling us\n");
1128 .src =
"console_send_text",
1132 if (cmd == CLI_INIT) {
1133 e->
command =
"console send text";
1135 "Usage: console send text <message>\n"
1136 " Sends a text message for display on the remote terminal.\n";
1138 }
else if (cmd == CLI_GENERATE) {
1142 pvt = get_active_pvt();
1144 ast_cli(a->fd,
"No console device is set as active\n");
1148 if (a->argc < e->
args + 1) {
1150 return CLI_SHOWUSAGE;
1154 ast_cli(a->fd,
"Not in a call\n");
1160 if (ast_strlen_zero(buf)) {
1162 return CLI_SHOWUSAGE;
1176 static void set_active(
struct console_pvt *pvt,
const char *value)
1178 if (pvt == &globals) {
1179 ast_log(LOG_ERROR,
"active is only valid as a per-device setting\n");
1186 ast_rwlock_wrlock(&active_lock);
1188 unref_pvt(active_pvt);
1189 active_pvt = ref_pvt(pvt);
1190 ast_rwlock_unlock(&active_lock);
1199 e->
command =
"console {set|show} active";
1201 "Usage: console {set|show} active [<device>]\n"
1202 " Set or show the active console device for the Asterisk CLI.\n";
1205 if (a->pos == e->
args) {
1210 while ((pvt = ao2_iterator_next(&i))) {
1211 if (++x > a->n && !strncasecmp(pvt->
name, a->word, strlen(a->word)))
1224 if (a->argc < e->
args)
1225 return CLI_SHOWUSAGE;
1228 pvt = get_active_pvt();
1231 ast_cli(a->fd,
"No device is currently set as the active console device.\n");
1234 ast_cli(a->fd,
"The active console device is '%s'.\n", pvt->
name);
1236 pvt = unref_pvt(pvt);
1242 if (!(pvt = find_pvt(a->argv[e->
args]))) {
1243 ast_cli(a->fd,
"Could not find a device called '%s'.\n", a->argv[e->
args]);
1247 set_active(pvt,
"yes");
1250 ast_cli(a->fd,
"The active console device has been set to '%s'\n", pvt->
name);
1259 AST_CLI_DEFINE(cli_console_dial,
"Dial an extension from the console"),
1260 AST_CLI_DEFINE(cli_console_hangup,
"Hangup a call on the console"),
1261 AST_CLI_DEFINE(cli_console_mute,
"Disable/Enable mic input"),
1264 AST_CLI_DEFINE(cli_console_flash,
"Send a flash to the connected party"),
1265 AST_CLI_DEFINE(cli_console_autoanswer,
"Turn autoanswer on or off"),
1266 AST_CLI_DEFINE(cli_list_available,
"List available devices"),
1267 AST_CLI_DEFINE(cli_list_devices,
"List configured devices"),
1268 AST_CLI_DEFINE(cli_console_active,
"View or Set the active console device"),
1278 if (pvt == &globals) {
1290 ast_mutex_lock(&globals_lock);
1303 ast_mutex_unlock(&globals_lock);
1307 static void store_callerid(
struct console_pvt *pvt,
const char *value)
1312 ast_callerid_split(value, cid_name,
sizeof(cid_name),
1313 cid_num,
sizeof(cid_num));
1331 CV_STRFIELD(
"context", pvt, context);
1332 CV_STRFIELD(
"extension", pvt, exten);
1333 CV_STRFIELD(
"mohinterpret", pvt, mohinterpret);
1334 CV_STRFIELD(
"language", pvt, language);
1335 CV_F(
"callerid", store_callerid(pvt, value));
1338 CV_STRFIELD(
"parkinglot", pvt, parkinglot);
1340 if (pvt != &globals) {
1341 CV_F(
"active", set_active(pvt, value))
1342 CV_STRFIELD(
"input_device", pvt, input_device);
1343 CV_STRFIELD(
"output_device", pvt, output_device);
1346 ast_log(LOG_WARNING,
"Unknown option '%s'\n", var);
1351 static void pvt_destructor(
void *obj)
1360 pvt->
thread = AST_PTHREADT_NULL;
1370 static void build_device(
struct ast_config *cfg,
const char *name)
1376 if ((pvt = find_pvt(name))) {
1381 if (!(pvt = ao2_alloc(
sizeof(*pvt), pvt_destructor)))
1383 init_pvt(pvt, name);
1388 for (v = ast_variable_browse(cfg, name); v; v = v->
next)
1399 static int pvt_mark_destroy_cb(
void *obj,
void *arg,
int flags)
1406 static void destroy_pvts(
void)
1412 while ((pvt = ao2_iterator_next(&i))) {
1415 ast_rwlock_wrlock(&active_lock);
1416 if (active_pvt == pvt)
1417 active_pvt = unref_pvt(pvt);
1418 ast_rwlock_unlock(&active_lock);
1436 char *context = NULL;
1439 memcpy(&global_jbconf, &default_jbconf,
sizeof(global_jbconf));
1440 ast_mutex_lock(&globals_lock);
1442 ast_mutex_unlock(&globals_lock);
1445 ast_log(LOG_NOTICE,
"Unable to open configuration file %s!\n",
config_file);
1447 }
else if (cfg == CONFIG_STATUS_FILEINVALID) {
1448 ast_log(LOG_NOTICE,
"Config file %s has an invalid format\n",
config_file);
1454 ast_mutex_lock(&globals_lock);
1455 for (v = ast_variable_browse(cfg,
"general"); v; v = v->
next)
1457 ast_mutex_unlock(&globals_lock);
1460 if (strcasecmp(context,
"general"))
1461 build_device(cfg, context);
1471 static int pvt_hash_cb(
const void *obj,
const int flags)
1478 static int pvt_cmp_cb(
void *obj,
void *arg,
int flags)
1485 static void stop_streams(
void)
1491 while ((pvt = ao2_iterator_next(&i))) {
1499 static int unload_module(
void)
1513 pvt_destructor(&globals);
1537 init_pvt(&globals, NULL);
1540 pvt_hash_cb, NULL, pvt_cmp_cb);
1547 res = Pa_Initialize();
1548 if (res != paNoError) {
1549 ast_log(LOG_WARNING,
"Failed to initialize audio system - (%d) %s\n",
1550 res, Pa_GetErrorText(res));
1551 goto return_error_pa_init;
1555 ast_log(LOG_ERROR,
"Unable to register channel type 'Console'\n");
1556 goto return_error_chan_reg;
1560 goto return_error_cli_reg;
1564 return_error_cli_reg:
1566 return_error_chan_reg:
1568 return_error_pa_init:
1576 pvt_destructor(&globals);
1581 static int reload(
void)
1586 AST_MODULE_INFO(
ASTERISK_GPL_KEY, AST_MODFLAG_LOAD_ORDER,
"Console Channel Driver",
1587 .support_level = AST_MODULE_SUPPORT_EXTENDED,
1589 .unload = unload_module,
struct ast_variable * next
int ast_queue_hangup(struct ast_channel *chan)
Queue a hangup frame.
static char * cli_console_sendtext(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
Console send text CLI command.
Main Channel structure associated with a channel.
Asterisk main include file. File version handling, generic pbx functions.
int ast_queue_control(struct ast_channel *chan, enum ast_control_frame_type control)
Queue a control frame without payload.
const ast_string_field cid_num
CallerID (and other GR30) management and generation Includes code and algorithms from the Zapata libr...
#define ast_join(s, len, w)
Join an array of strings into a single string.
int ast_cli_unregister_multiple(struct ast_cli_entry *e, int len)
Unregister multiple commands.
int ast_indicate(struct ast_channel *chan, int condition)
Indicates condition of channel.
const ast_string_field context
void ast_channel_unregister(const struct ast_channel_tech *tech)
Unregister a channel technology.
static void set_pvt_defaults(struct console_pvt *pvt)
Set default values for a pvt struct.
descriptor for a cli entry.
enum ast_pbx_result ast_pbx_start(struct ast_channel *c)
Create a new thread and start the PBX.
#define ao2_callback(c, flags, cb_fn, arg)
ao2_callback() is a generic function that applies cb_fn() to all objects in a container, as described below.
int ast_jb_read_conf(struct ast_jb_conf *conf, const char *varname, const char *value)
Sets jitterbuffer configuration property.
Structure for variables, used for configurations and for channel variables.
unsigned int overridecontext
Structure to pass both assignedid values to channel drivers.
#define ast_cli_register_multiple(e, len)
Register multiple commands.
void ao2_iterator_destroy(struct ao2_iterator *iter)
Destroy a container iterator.
static int load_config(int reload)
Load the configuration.
ast_control_frame_type
Internal control frame subtype field values.
#define AST_DECLARE_STRING_FIELDS(field_list)
Declare the fields needed in a structure.
struct ast_channel * owner
int ast_channel_register(const struct ast_channel_tech *tech)
Register a channel technology (a new channel driver) Called by a channel module to register the kind ...
#define ast_strdup(str)
A wrapper for strdup()
const ast_string_field parkinglot
char * ast_category_browse(struct ast_config *config, const char *prev_name)
Browse categories.
#define CV_END
close a variable parsing block
#define SAMPLE_RATE
The sample rate to request from PortAudio.
#define CV_START(__in_var, __in_val)
the macro to open a block for variable parsing
void ast_moh_stop(struct ast_channel *chan)
Turn off music on hold on a given channel.
struct ast_frame_subclass subclass
int args
This gets set in ast_cli_register()
static struct ast_frame * console_read(struct ast_channel *chan)
Implementation of the ast_channel_tech read() callback.
static char * ast_ext_ctx(struct console_pvt *pvt, const char *src, char **ext, char **ctx)
static struct ast_jb_conf default_jbconf
Global jitterbuffer configuration.
#define CV_F(__pattern, __body)
call a generic function if the name matches.
static const char config_file[]
#define ast_config_load(filename, flags)
Load a config file.
General Asterisk PBX channel definitions.
#define TEXT_SIZE
Maximum text message length.
#define ast_string_field_init(x, size)
Initialize a field pool and fields.
void ast_channel_stage_snapshot_done(struct ast_channel *chan)
Clear flag to indicate channel snapshot is being staged, and publish snapshot.
#define ao2_ref(o, delta)
Reference/unreference an object and return the old refcount.
#define AST_STRING_FIELD(name)
Declare a string field.
#define S_COR(a, b, c)
returns the equivalent of logic or for strings, with an additional boolean check: second one if not e...
#define NUM_SAMPLES
The number of samples to configure the portaudio stream for.
#define console_pvt_unlock(pvt)
unlock a console_pvt struct
static struct ast_channel * console_new(struct console_pvt *pvt, const char *ext, const char *ctx, int state, const struct ast_assigned_ids *assignedids, const struct ast_channel *requestor)
#define ast_debug(level,...)
Log a DEBUG message.
int ast_exists_extension(struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid)
Determine whether an extension exists.
static void store_config_core(struct console_pvt *pvt, const char *var, const char *value)
Store a configuration parameter in a pvt struct.
Structure to describe a channel "technology", ie a channel driver See for examples: ...
Core PBX routines and definitions.
int ast_queue_frame(struct ast_channel *chan, struct ast_frame *f)
Queue one or more frames to a channel's frame queue.
#define OUTPUT_CHANNELS
Mono Output.
void ast_channel_stage_snapshot(struct ast_channel *chan)
Set flag to indicate channel snapshot is being staged.
const ast_string_field language
static void * stream_monitor(void *data)
Stream monitor thread.
#define ao2_container_alloc_hash(ao2_options, container_options, n_buckets, hash_fn, sort_fn, cmp_fn)
Allocate and initialize a hash container with the desired number of buckets.
int attribute_pure ast_true(const char *val)
Make sure something is true. Determine if a string containing a boolean value is "true". This function checks to see whether a string passed to it is an indication of an "true" value. It checks to see if the string is "yes", "true", "y", "t", "on" or "1".
Support for dynamic strings.
#define ao2_unlink(container, obj)
Remove an object from a container.
static char * cli_console_answer(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
answer command from the console
#define CV_BOOL(__x, __dst)
helper macros to assign the value to a BOOL, UINT, static string and dynamic string ...
int ast_moh_start(struct ast_channel *chan, const char *mclass, const char *interpclass)
Turn on music on hold on a given channel.
struct ast_format_cap * capabilities
static int load_module(void)
Load the module.
union ast_frame::@224 data
void ast_hangup(struct ast_channel *chan)
Hang up a channel.
#define INPUT_CHANNELS
Mono Input.
Module has failed to load, may be in an inconsistent state.
#define V_BEGIN
Dance, Kirby, Dance!
unsigned int flags
Combination of the AST_JB_ENABLED, AST_JB_FORCED and AST_JB_LOG flags.
Structure used to handle boolean flags.
void ast_jb_configure(struct ast_channel *chan, const struct ast_jb_conf *conf)
Configures a jitterbuffer on a channel.
static struct ast_channel * console_request(const char *type, struct ast_format_cap *cap, const struct ast_assigned_ids *assignedids, const struct ast_channel *requestor, const char *data, int *cause)
struct ast_frame ast_null_frame
When we need to walk through a container, we use an ao2_iterator to keep track of the current positio...
Standard Command Line Interface.
#define S_OR(a, b)
returns the equivalent of logic or for strings: first one if not empty, otherwise second one...
int ast_setstate(struct ast_channel *chan, enum ast_channel_state)
Change the state of a channel.
Data structure associated with a single frame of data.
Internal Asterisk hangup causes.
const ast_string_field mohinterpret
enum ast_frame_type frametype
#define console_pvt_lock(pvt)
lock a console_pvt struct
void ast_config_destroy(struct ast_config *cfg)
Destroys a config.
#define ASTERISK_GPL_KEY
The text the key() function should return.
#define ast_channel_alloc(needqueue, state, cid_num, cid_name, acctcode, exten, context, assignedids, requestor, amaflag,...)
Create a channel structure.
Asterisk module definitions.
const ast_string_field name
#define ast_string_field_free_memory(x)
free all memory - to be called before destroying the object
General jitterbuffer configuration.
struct ao2_iterator ao2_iterator_init(struct ao2_container *c, int flags) attribute_warn_unused_result
Create an iterator for a container.
const ast_string_field cid_name
static force_inline int attribute_pure ast_str_case_hash(const char *str)
Compute a hash value on a case-insensitive string.
const ast_string_field exten
#define ast_string_field_set(x, field, data)
Set a field to a simple string value.
#define ao2_link(container, obj)
Add an object to a container.