Asterisk - The Open Source Telephony Project GIT-master-27fb039
Loading...
Searching...
No Matches
Enumerations | Functions | Variables
app_read.c File Reference

Trivial application to read a variable. More...

#include "asterisk.h"
#include "asterisk/file.h"
#include "asterisk/pbx.h"
#include "asterisk/channel.h"
#include "asterisk/app.h"
#include "asterisk/module.h"
#include "asterisk/indications.h"
Include dependency graph for app_read.c:

Go to the source code of this file.

Enumerations

enum  { OPT_ARG_TERMINATOR , OPT_ARG_ARRAY_SIZE }
 
enum  read_option_flags {
  OPT_SKIP = (1 << 0) , OPT_INDICATION = (1 << 1) , OPT_NOANSWER = (1 << 2) , OPT_TERMINATOR = (1 << 3) ,
  OPT_KEEP_TERMINATOR = (1 << 4)
}
 

Functions

static void __reg_module (void)
 
static void __unreg_module (void)
 
struct ast_moduleAST_MODULE_SELF_SYM (void)
 
static int load_module (void)
 
static int read_exec (struct ast_channel *chan, const char *data)
 
static int unload_module (void)
 

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Read Variable Application" , .key = ASTERISK_GPL_KEY , .buildopt_sum = AST_BUILDOPT_SUM, .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, .support_level = AST_MODULE_SUPPORT_CORE, }
 
static char * app = "Read"
 
static const struct ast_module_infoast_module_info = &__mod_info
 
static const struct ast_app_option read_app_options [128] = { [ 's' ] = { .flag = OPT_SKIP }, [ 'i' ] = { .flag = OPT_INDICATION }, [ 'n' ] = { .flag = OPT_NOANSWER }, [ 't' ] = { .flag = OPT_TERMINATOR , .arg_index = OPT_ARG_TERMINATOR + 1 }, [ 'e' ] = { .flag = OPT_KEEP_TERMINATOR }, }
 

Detailed Description

Trivial application to read a variable.

Author
Mark Spencer marks.nosp@m.ter@.nosp@m.digiu.nosp@m.m.co.nosp@m.m

Definition in file app_read.c.

Enumeration Type Documentation

◆ anonymous enum

anonymous enum
Enumerator
OPT_ARG_TERMINATOR 
OPT_ARG_ARRAY_SIZE 

Definition at line 147 of file app_read.c.

147 {
149 /* note: this entry _MUST_ be the last one in the enum */
151};
@ OPT_ARG_TERMINATOR
Definition app_read.c:148
@ OPT_ARG_ARRAY_SIZE
Definition app_read.c:150

◆ read_option_flags

Enumerator
OPT_SKIP 
OPT_INDICATION 
OPT_NOANSWER 
OPT_TERMINATOR 
OPT_KEEP_TERMINATOR 

Definition at line 139 of file app_read.c.

139 {
140 OPT_SKIP = (1 << 0),
141 OPT_INDICATION = (1 << 1),
142 OPT_NOANSWER = (1 << 2),
143 OPT_TERMINATOR = (1 << 3),
144 OPT_KEEP_TERMINATOR = (1 << 4),
145};
@ OPT_TERMINATOR
Definition app_read.c:143
@ OPT_NOANSWER
Definition app_read.c:142
@ OPT_INDICATION
Definition app_read.c:141
@ OPT_SKIP
Definition app_read.c:140
@ OPT_KEEP_TERMINATOR
Definition app_read.c:144

Function Documentation

◆ __reg_module()

static void __reg_module ( void  )
static

Definition at line 337 of file app_read.c.

◆ __unreg_module()

static void __unreg_module ( void  )
static

Definition at line 337 of file app_read.c.

◆ AST_MODULE_SELF_SYM()

struct ast_module * AST_MODULE_SELF_SYM ( void  )

Definition at line 337 of file app_read.c.

◆ load_module()

static int load_module ( void  )
static

Definition at line 332 of file app_read.c.

333{
335}
static int read_exec(struct ast_channel *chan, const char *data)
Definition app_read.c:163
static char * app
Definition app_read.c:161
#define ast_register_application_xml(app, execute)
Register an application using XML documentation.
Definition module.h:640

References app, ast_register_application_xml, and read_exec().

◆ read_exec()

static int read_exec ( struct ast_channel chan,
const char *  data 
)
static

Definition at line 163 of file app_read.c.

164{
165 int res = 0;
166 char tmp[256] = "";
167 int maxdigits = 255;
168 int tries = 1, to = 0, x = 0;
169 double tosec;
170 char *argcopy = NULL;
171 char *opt_args[OPT_ARG_ARRAY_SIZE];
172 struct ast_tone_zone_sound *ts = NULL;
173 struct ast_flags flags = {0};
174 const char *status = "ERROR";
175 char *terminator = "#"; /* use default terminator # by default */
176
177 AST_DECLARE_APP_ARGS(arglist,
178 AST_APP_ARG(variable);
179 AST_APP_ARG(filename);
180 AST_APP_ARG(maxdigits);
182 AST_APP_ARG(attempts);
183 AST_APP_ARG(timeout);
184 );
185
186 pbx_builtin_setvar_helper(chan, "READSTATUS", status);
187 if (ast_strlen_zero(data)) {
188 ast_log(LOG_WARNING, "Read requires an argument (variable)\n");
189 return 0;
190 }
191
192 argcopy = ast_strdupa(data);
193
194 AST_STANDARD_APP_ARGS(arglist, argcopy);
195
196 if (!ast_strlen_zero(arglist.options)) {
197 ast_app_parse_options(read_app_options, &flags, opt_args, arglist.options);
198 }
199
200 if (!ast_strlen_zero(arglist.attempts)) {
201 tries = atoi(arglist.attempts);
202 if (tries <= 0)
203 tries = 1;
204 }
205
206 if (!ast_strlen_zero(arglist.timeout)) {
207 tosec = atof(arglist.timeout);
208 if (tosec <= 0)
209 to = 0;
210 else
211 to = tosec * 1000.0;
212 }
213
214 if (ast_strlen_zero(arglist.filename)) {
215 arglist.filename = NULL;
216 }
217 if (!ast_strlen_zero(arglist.maxdigits)) {
218 maxdigits = atoi(arglist.maxdigits);
219 if ((maxdigits < 1) || (maxdigits > 255)) {
220 maxdigits = 255;
221 } else
222 ast_verb(3, "Accepting a maximum of %d digits.\n", maxdigits);
223 }
224 if (ast_strlen_zero(arglist.variable)) {
225 ast_log(LOG_WARNING, "Invalid! Usage: Read(variable[,filename][,maxdigits][,option][,attempts][,timeout])\n\n");
226 return 0;
227 }
229 if (!ast_strlen_zero(arglist.filename)) {
230 ts = ast_get_indication_tone(ast_channel_zone(chan), arglist.filename);
231 }
232 }
234 if (!ast_strlen_zero(opt_args[OPT_ARG_TERMINATOR])) {
235 terminator = opt_args[OPT_ARG_TERMINATOR];
236 } else {
237 terminator = ""; /* no digit inherently will terminate input */
238 }
239 }
240 if (ast_channel_state(chan) != AST_STATE_UP) {
242 /* At the user's option, skip if the line is not up */
243 if (ts) {
245 }
246 pbx_builtin_setvar_helper(chan, arglist.variable, "");
247 pbx_builtin_setvar_helper(chan, "READSTATUS", "SKIPPED");
248 return 0;
249 } else if (!ast_test_flag(&flags, OPT_NOANSWER)) {
250 /* Otherwise answer unless we're supposed to read while on-hook */
251 res = ast_answer(chan);
252 }
253 }
254 if (!res) {
255 while (tries && !res) {
256 ast_stopstream(chan);
257 if (ts && ts->data[0]) {
258 if (!to)
259 to = ast_channel_pbx(chan) ? ast_channel_pbx(chan)->rtimeoutms : 6000;
260 res = ast_playtones_start(chan, 0, ts->data, 0);
261 for (x = 0; x < maxdigits; ) {
262 res = ast_waitfordigit(chan, to);
263 ast_playtones_stop(chan);
264 if (res < 1) {
265 if (res == 0)
266 status = "TIMEOUT";
267 tmp[x]='\0';
268 break;
269 }
270 tmp[x++] = res;
271 if (terminator && strchr(terminator, tmp[x-1])) {
272 tmp[x-1] = '\0';
273 status = "OK";
274 break;
275 }
276 if (x >= maxdigits) {
277 status = "OK";
278 }
279 }
280 } else {
281 res = ast_app_getdata_terminator(chan, arglist.filename, tmp, maxdigits, to, terminator);
282 if (res == AST_GETDATA_COMPLETE) {
283 status = "OK";
284 } else if (res == AST_GETDATA_EMPTY_END_TERMINATED) {
286 /* if the option is set to do so, read the
287 returned string as the terminator string */
288 ast_copy_string(tmp, terminator, sizeof(tmp));
289 }
290 status = "OK";
291 } else if (res == AST_GETDATA_TIMEOUT) {
292 status = "TIMEOUT";
293 } else if (res == AST_GETDATA_INTERRUPTED) {
294 status = "INTERRUPTED";
295 }
296 }
297 if (res > -1) {
298 pbx_builtin_setvar_helper(chan, arglist.variable, tmp);
299 if (!ast_strlen_zero(tmp)) {
300 ast_verb(3, "User entered '%s'\n", tmp);
301 tries = 0;
302 } else {
303 tries--;
304 if (tries)
305 ast_verb(3, "User entered nothing, %d chance%s left\n", tries, (tries != 1) ? "s" : "");
306 else
307 ast_verb(3, "User entered nothing.\n");
308 }
309 res = 0;
310 } else {
311 pbx_builtin_setvar_helper(chan, arglist.variable, tmp);
312 ast_verb(3, "User disconnected\n");
313 }
314 }
315 }
316
317 if (ts) {
319 }
320
321 if (ast_check_hangup(chan))
322 status = "HANGUP";
323 pbx_builtin_setvar_helper(chan, "READSTATUS", status);
324 return 0;
325}
jack_status_t status
Definition app_jack.c:149
static const struct ast_app_option read_app_options[128]
Definition app_read.c:159
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition astmm.h:298
#define ast_log
Definition astobj2.c:42
int ast_waitfordigit(struct ast_channel *c, int ms)
Waits for a digit.
Definition channel.c:3172
int ast_check_hangup(struct ast_channel *chan)
Check to see if a channel is needing hang up.
Definition channel.c:445
struct ast_tone_zone * ast_channel_zone(const struct ast_channel *chan)
struct ast_pbx * ast_channel_pbx(const struct ast_channel *chan)
int ast_answer(struct ast_channel *chan)
Answer a channel.
Definition channel.c:2803
ast_channel_state
ast_channel states
@ AST_STATE_UP
int ast_stopstream(struct ast_channel *c)
Stops a stream.
Definition file.c:223
#define AST_APP_ARG(name)
Define an application argument.
@ AST_GETDATA_INTERRUPTED
@ AST_GETDATA_COMPLETE
@ AST_GETDATA_TIMEOUT
@ AST_GETDATA_EMPTY_END_TERMINATED
#define AST_DECLARE_APP_ARGS(name, arglist)
Declare a structure to hold an application's arguments.
enum ast_getdata_result ast_app_getdata_terminator(struct ast_channel *c, const char *prompt, char *s, int maxlen, int timeout, char *terminator)
Plays a stream and gets DTMF data from a channel.
Definition main/app.c:193
#define AST_STANDARD_APP_ARGS(args, parse)
Performs the 'standard' argument separation process for an application.
int ast_app_parse_options(const struct ast_app_option *options, struct ast_flags *flags, char **args, char *optstr)
Parses a string containing application options and sets flags/arguments.
Definition main/app.c:3066
#define ast_verb(level,...)
#define LOG_WARNING
static struct ast_tone_zone_sound * ast_tone_zone_sound_unref(struct ast_tone_zone_sound *ts)
Release a reference to an ast_tone_zone_sound.
int ast_playtones_start(struct ast_channel *chan, int vol, const char *tonelist, int interruptible)
Start playing a list of tones on a channel.
void ast_playtones_stop(struct ast_channel *chan)
Stop playing tones on a channel.
struct ast_tone_zone_sound * ast_get_indication_tone(const struct ast_tone_zone *zone, const char *indication)
Locate a tone zone sound.
int pbx_builtin_setvar_helper(struct ast_channel *chan, const char *name, const char *value)
Add a variable to the channel variable stack, removing the most recently set value for the same name.
#define NULL
Definition resample.c:96
static force_inline int attribute_pure ast_strlen_zero(const char *s)
Definition strings.h:65
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
Definition strings.h:425
Structure used to handle boolean flags.
Definition utils.h:220
unsigned int flags
Definition utils.h:221
int rtimeoutms
Definition pbx.h:217
Description of a tone.
Definition indications.h:35
const char * data
Description of a tone.
Definition indications.h:52
static struct test_options options
#define ast_test_flag(p, flag)
Definition utils.h:64

References ast_answer(), AST_APP_ARG, ast_app_getdata_terminator(), ast_app_parse_options(), ast_channel_pbx(), ast_channel_zone(), ast_check_hangup(), ast_copy_string(), AST_DECLARE_APP_ARGS, ast_get_indication_tone(), AST_GETDATA_COMPLETE, AST_GETDATA_EMPTY_END_TERMINATED, AST_GETDATA_INTERRUPTED, AST_GETDATA_TIMEOUT, ast_log, ast_playtones_start(), ast_playtones_stop(), AST_STANDARD_APP_ARGS, AST_STATE_UP, ast_stopstream(), ast_strdupa, ast_strlen_zero(), ast_test_flag, ast_tone_zone_sound_unref(), ast_verb, ast_waitfordigit(), ast_tone_zone_sound::data, ast_flags::flags, LOG_WARNING, NULL, OPT_ARG_ARRAY_SIZE, OPT_ARG_TERMINATOR, OPT_INDICATION, OPT_KEEP_TERMINATOR, OPT_NOANSWER, OPT_SKIP, OPT_TERMINATOR, options, pbx_builtin_setvar_helper(), read_app_options, ast_pbx::rtimeoutms, and status.

Referenced by load_module().

◆ unload_module()

static int unload_module ( void  )
static

Definition at line 327 of file app_read.c.

328{
330}
int ast_unregister_application(const char *app)
Unregister an application.
Definition pbx_app.c:392

References app, and ast_unregister_application().

Variable Documentation

◆ __mod_info

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Read Variable Application" , .key = ASTERISK_GPL_KEY , .buildopt_sum = AST_BUILDOPT_SUM, .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, .support_level = AST_MODULE_SUPPORT_CORE, }
static

Definition at line 337 of file app_read.c.

◆ app

char* app = "Read"
static

Definition at line 161 of file app_read.c.

Referenced by load_module(), and unload_module().

◆ ast_module_info

const struct ast_module_info* ast_module_info = &__mod_info
static

Definition at line 337 of file app_read.c.

◆ read_app_options

const struct ast_app_option read_app_options[128] = { [ 's' ] = { .flag = OPT_SKIP }, [ 'i' ] = { .flag = OPT_INDICATION }, [ 'n' ] = { .flag = OPT_NOANSWER }, [ 't' ] = { .flag = OPT_TERMINATOR , .arg_index = OPT_ARG_TERMINATOR + 1 }, [ 'e' ] = { .flag = OPT_KEEP_TERMINATOR }, }
static

Definition at line 159 of file app_read.c.

Referenced by read_exec().