Wed Jan 8 2020 09:50:13

Asterisk developer's documentation


func_sprintf.c File Reference

String manipulation dialplan functions. More...

#include "asterisk.h"
#include <ctype.h>
#include "asterisk/module.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/utils.h"
#include "asterisk/app.h"

Go to the source code of this file.

Macros

#define SPRINTF_CONVERSION   4
 
#define SPRINTF_FLAG   0
 
#define SPRINTF_LENGTH   3
 
#define SPRINTF_PRECISION   2
 
#define SPRINTF_WIDTH   1
 

Functions

static void __init_result_buf (void)
 
static void __reg_module (void)
 
static void __unreg_module (void)
 
static int acf_sprintf (struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
 
static int load_module (void)
 
static int unload_module (void)
 

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "SPRINTF dialplan function" , .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 = "ac1f6a56484a8820659555499174e588" , .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, }
 
static struct ast_module_infoast_module_info = &__mod_info
 
static struct ast_threadstorage result_buf = { .once = PTHREAD_ONCE_INIT , .key_init = __init_result_buf , .custom_init = NULL , }
 
static struct ast_custom_function sprintf_function
 

Detailed Description

String manipulation dialplan functions.

Author
Tilghman Lesher
Anothony Minessale II

Definition in file func_sprintf.c.

Macro Definition Documentation

#define SPRINTF_CONVERSION   4

Referenced by acf_sprintf().

#define SPRINTF_FLAG   0

Referenced by acf_sprintf().

#define SPRINTF_LENGTH   3

Referenced by acf_sprintf().

#define SPRINTF_PRECISION   2

Referenced by acf_sprintf().

#define SPRINTF_WIDTH   1

Referenced by acf_sprintf().

Function Documentation

static void __init_result_buf ( void  )
static

Definition at line 44 of file func_sprintf.c.

68 {
static void __reg_module ( void  )
static

Definition at line 234 of file func_sprintf.c.

static void __unreg_module ( void  )
static

Definition at line 234 of file func_sprintf.c.

static int acf_sprintf ( struct ast_channel chan,
const char *  cmd,
char *  data,
char *  buf,
size_t  len 
)
static

Definition at line 67 of file func_sprintf.c.

References AST_APP_ARG, ast_copy_string(), AST_DECLARE_APP_ARGS, ast_log(), AST_STANDARD_APP_ARGS, format, LOG_ERROR, SPRINTF_CONVERSION, SPRINTF_FLAG, SPRINTF_LENGTH, SPRINTF_PRECISION, SPRINTF_WIDTH, and var.

68 {
69 #define SPRINTF_FLAG 0
70 #define SPRINTF_WIDTH 1
71 #define SPRINTF_PRECISION 2
72 #define SPRINTF_LENGTH 3
73 #define SPRINTF_CONVERSION 4
74  int i, state = -1, argcount = 0;
75  char *formatstart = NULL, *bufptr = buf;
76  char formatbuf[256] = "";
77  int tmpi;
78  double tmpd;
81  AST_APP_ARG(var)[100];
82  );
83 
84  AST_STANDARD_APP_ARGS(arg, data);
85 
86  /* Scan the format, converting each argument into the requisite format type. */
87  for (i = 0; arg.format[i]; i++) {
88  switch (state) {
89  case SPRINTF_FLAG:
90  if (strchr("#0- +'I", arg.format[i]))
91  break;
92  state = SPRINTF_WIDTH;
93  case SPRINTF_WIDTH:
94  if (arg.format[i] >= '0' && arg.format[i] <= '9')
95  break;
96 
97  /* Next character must be a period to go into a precision */
98  if (arg.format[i] == '.') {
99  state = SPRINTF_PRECISION;
100  } else {
101  state = SPRINTF_LENGTH;
102  i--;
103  }
104  break;
105  case SPRINTF_PRECISION:
106  if (arg.format[i] >= '0' && arg.format[i] <= '9')
107  break;
108  state = SPRINTF_LENGTH;
109  case SPRINTF_LENGTH:
110  if (strchr("hl", arg.format[i])) {
111  if (arg.format[i + 1] == arg.format[i])
112  i++;
113  state = SPRINTF_CONVERSION;
114  break;
115  } else if (strchr("Lqjzt", arg.format[i])) {
116  state = SPRINTF_CONVERSION;
117  break;
118  }
119  state = SPRINTF_CONVERSION;
120  case SPRINTF_CONVERSION:
121  if (strchr("diouxXc", arg.format[i])) {
122  /* Integer */
123 
124  /* Isolate this format alone */
125  ast_copy_string(formatbuf, formatstart, sizeof(formatbuf));
126  formatbuf[&arg.format[i] - formatstart + 1] = '\0';
127 
128  /* Convert the argument into the required type */
129  if (arg.var[argcount]) {
130  if (sscanf(arg.var[argcount++], "%30d", &tmpi) != 1) {
131  ast_log(LOG_ERROR, "Argument '%s' is not an integer number for format '%s'\n", arg.var[argcount - 1], formatbuf);
132  goto sprintf_fail;
133  }
134  } else {
135  ast_log(LOG_ERROR, "SPRINTF() has more format specifiers than arguments!\n");
136  goto sprintf_fail;
137  }
138 
139  /* Format the argument */
140  snprintf(bufptr, buf + len - bufptr, formatbuf, tmpi);
141 
142  /* Update the position of the next parameter to print */
143  bufptr = strchr(buf, '\0');
144  } else if (strchr("eEfFgGaA", arg.format[i])) {
145  /* Double */
146 
147  /* Isolate this format alone */
148  ast_copy_string(formatbuf, formatstart, sizeof(formatbuf));
149  formatbuf[&arg.format[i] - formatstart + 1] = '\0';
150 
151  /* Convert the argument into the required type */
152  if (arg.var[argcount]) {
153  if (sscanf(arg.var[argcount++], "%30lf", &tmpd) != 1) {
154  ast_log(LOG_ERROR, "Argument '%s' is not a floating point number for format '%s'\n", arg.var[argcount - 1], formatbuf);
155  goto sprintf_fail;
156  }
157  } else {
158  ast_log(LOG_ERROR, "SPRINTF() has more format specifiers than arguments!\n");
159  goto sprintf_fail;
160  }
161 
162  /* Format the argument */
163  snprintf(bufptr, buf + len - bufptr, formatbuf, tmpd);
164 
165  /* Update the position of the next parameter to print */
166  bufptr = strchr(buf, '\0');
167  } else if (arg.format[i] == 's') {
168  /* String */
169 
170  /* Isolate this format alone */
171  ast_copy_string(formatbuf, formatstart, sizeof(formatbuf));
172  formatbuf[&arg.format[i] - formatstart + 1] = '\0';
173 
174  /* Format the argument */
175  snprintf(bufptr, buf + len - bufptr, formatbuf, arg.var[argcount++]);
176 
177  /* Update the position of the next parameter to print */
178  bufptr = strchr(buf, '\0');
179  } else if (arg.format[i] == '%') {
180  /* Literal data to copy */
181  *bufptr++ = arg.format[i];
182  } else {
183  /* Not supported */
184 
185  /* Isolate this format alone */
186  ast_copy_string(formatbuf, formatstart, sizeof(formatbuf));
187  formatbuf[&arg.format[i] - formatstart + 1] = '\0';
188 
189  ast_log(LOG_ERROR, "Format type not supported: '%s' with argument '%s'\n", formatbuf, arg.var[argcount++]);
190  goto sprintf_fail;
191  }
192  state = -1;
193  break;
194  default:
195  if (arg.format[i] == '%') {
196  state = SPRINTF_FLAG;
197  formatstart = &arg.format[i];
198  break;
199  } else {
200  /* Literal data to copy */
201  *bufptr++ = arg.format[i];
202  }
203  }
204  }
205  *bufptr = '\0';
206  return 0;
207 sprintf_fail:
208  return -1;
209 }
#define SPRINTF_WIDTH
#define SPRINTF_PRECISION
#define SPRINTF_CONVERSION
#define AST_DECLARE_APP_ARGS(name, arglist)
Declare a structure to hold an application&#39;s arguments.
Definition: app.h:572
#define var
Definition: ast_expr2f.c:606
#define SPRINTF_LENGTH
#define SPRINTF_FLAG
#define LOG_ERROR
Definition: logger.h:155
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
void ast_log(int level, const char *file, int line, const char *function, const char *fmt,...)
Used for sending a log message This is the standard logger function. Probably the only way you will i...
Definition: logger.c:1207
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
Definition: strings.h:223
#define AST_APP_ARG(name)
Define an application argument.
Definition: app.h:555
#define AST_STANDARD_APP_ARGS(args, parse)
Performs the &#39;standard&#39; argument separation process for an application.
Definition: app.h:604
static snd_pcm_format_t format
Definition: chan_alsa.c:93
static int load_module ( void  )
static

Definition at line 225 of file func_sprintf.c.

References ast_custom_function_register.

226 {
227  int res = 0;
228 
230 
231  return res;
232 }
static struct ast_custom_function sprintf_function
Definition: func_sprintf.c:211
#define ast_custom_function_register(acf)
Register a custom function.
Definition: pbx.h:1164
static int unload_module ( void  )
static

Definition at line 216 of file func_sprintf.c.

References ast_custom_function_unregister().

217 {
218  int res = 0;
219 
221 
222  return res;
223 }
int ast_custom_function_unregister(struct ast_custom_function *acf)
Unregister a custom function.
Definition: pbx.c:3814
static struct ast_custom_function sprintf_function
Definition: func_sprintf.c:211

Variable Documentation

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "SPRINTF dialplan function" , .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 = "ac1f6a56484a8820659555499174e588" , .load = load_module, .unload = unload_module, .load_pri = AST_MODPRI_DEFAULT, }
static

Definition at line 234 of file func_sprintf.c.

Definition at line 234 of file func_sprintf.c.

struct ast_threadstorage result_buf = { .once = PTHREAD_ONCE_INIT , .key_init = __init_result_buf , .custom_init = NULL , }
static

Definition at line 44 of file func_sprintf.c.

struct ast_custom_function sprintf_function
static
Initial value:
= {
.name = "SPRINTF",
.read = acf_sprintf,
}
static int acf_sprintf(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
Definition: func_sprintf.c:67

Definition at line 211 of file func_sprintf.c.