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

Party ID related dialplan functions (Caller-ID, Connected-line, Redirecting) More...

#include "asterisk.h"
#include "asterisk/module.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/utils.h"
#include "asterisk/app.h"
#include "asterisk/callerid.h"
Include dependency graph for func_callerid.c:

Go to the source code of this file.

Data Structures

struct  __subtype_ast_party_func_args
 
struct  __subtype_ast_party_members
 
struct  ast_party_func_args
 
struct  ast_party_members
 

Enumerations

enum  CONNECTED_LINE_OPT_ARGS { CONNECTED_LINE_OPT_DUMMY , CONNECTED_LINE_OPT_ARG_ARRAY_SIZE }
 
enum  CONNECTED_LINE_OPT_FLAGS { CONNECTED_LINE_OPT_INHIBIT = (1 << 0) }
 
enum  ID_FIELD_STATUS { ID_FIELD_VALID , ID_FIELD_INVALID , ID_FIELD_UNKNOWN }
 
enum  REDIRECTING_OPT_ARGS { REDIRECTING_OPT_DUMMY , REDIRECTING_OPT_ARG_ARRAY_SIZE }
 
enum  REDIRECTING_OPT_FLAGS { REDIRECTING_OPT_INHIBIT = (1 << 0) }
 

Functions

static void __reg_module (void)
 
static void __unreg_module (void)
 
struct ast_moduleAST_MODULE_SELF_SYM (void)
 
static int callerid_read (struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
 
static int callerid_write (struct ast_channel *chan, const char *cmd, char *data, const char *value)
 
static int connectedline_read (struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
 
static int connectedline_write (struct ast_channel *chan, const char *cmd, char *data, const char *value)
 
static int load_module (void)
 
static enum ID_FIELD_STATUS party_id_read (char *buf, size_t len, int argc, char *argv[], const struct ast_party_id *id)
 
static enum ID_FIELD_STATUS party_id_write (struct ast_party_id *id, int argc, char *argv[], const char *value)
 
static enum ID_FIELD_STATUS party_name_read (char *buf, size_t len, int argc, char *argv[], const struct ast_party_name *name)
 
static enum ID_FIELD_STATUS party_name_write (struct ast_party_name *name, int argc, char *argv[], const char *value)
 
static enum ID_FIELD_STATUS party_number_read (char *buf, size_t len, int argc, char *argv[], const struct ast_party_number *number)
 
static enum ID_FIELD_STATUS party_number_write (struct ast_party_number *number, int argc, char *argv[], const char *value)
 
static enum ID_FIELD_STATUS party_subaddress_read (char *buf, size_t len, int argc, char *argv[], const struct ast_party_subaddress *subaddress)
 
static enum ID_FIELD_STATUS party_subaddress_write (struct ast_party_subaddress *subaddress, int argc, char *argv[], const char *value)
 
static int redirecting_read (struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
 
static int redirecting_write (struct ast_channel *chan, const char *cmd, char *data, const char *value)
 
static int unload_module (void)
 

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Party ID related dialplan functions (Caller-ID, Connected-line, Redirecting)" , .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 const struct ast_module_infoast_module_info = &__mod_info
 
static struct ast_custom_function callerid_function
 
static struct ast_custom_function connectedline_function
 
static const struct ast_app_option connectedline_opts [128] = { [ 'i' ] = { .flag = CONNECTED_LINE_OPT_INHIBIT }, }
 
static struct ast_custom_function redirecting_function
 
static const struct ast_app_option redirecting_opts [128] = { [ 'i' ] = { .flag = REDIRECTING_OPT_INHIBIT }, }
 

Detailed Description

Party ID related dialplan functions (Caller-ID, Connected-line, Redirecting)

See Also:

Definition in file func_callerid.c.

Enumeration Type Documentation

◆ CONNECTED_LINE_OPT_ARGS

Enumerator
CONNECTED_LINE_OPT_DUMMY 

Delete this if CONNECTED_LINE ever gets an option with parameters.

CONNECTED_LINE_OPT_ARG_ARRAY_SIZE 
Note
This entry MUST be the last one in the enum

Definition at line 483 of file func_callerid.c.

483 {
484 CONNECTED_LINE_OPT_DUMMY, /*!< Delete this if CONNECTED_LINE ever gets an option with parameters. */
485
486 /*! \note This entry _MUST_ be the last one in the enum */
488};
@ CONNECTED_LINE_OPT_ARG_ARRAY_SIZE
@ CONNECTED_LINE_OPT_DUMMY

◆ CONNECTED_LINE_OPT_FLAGS

Enumerator
CONNECTED_LINE_OPT_INHIBIT 

Definition at line 480 of file func_callerid.c.

480 {
482};
@ CONNECTED_LINE_OPT_INHIBIT

◆ ID_FIELD_STATUS

Enumerator
ID_FIELD_VALID 
ID_FIELD_INVALID 
ID_FIELD_UNKNOWN 

Definition at line 464 of file func_callerid.c.

464 {
468};
@ ID_FIELD_INVALID
@ ID_FIELD_VALID
@ ID_FIELD_UNKNOWN

◆ REDIRECTING_OPT_ARGS

Enumerator
REDIRECTING_OPT_DUMMY 

Delete this if REDIRECTING ever gets an option with parameters.

REDIRECTING_OPT_ARG_ARRAY_SIZE 
Note
This entry MUST be the last one in the enum

Definition at line 497 of file func_callerid.c.

497 {
498 REDIRECTING_OPT_DUMMY, /*!< Delete this if REDIRECTING ever gets an option with parameters. */
499
500 /*! \note This entry _MUST_ be the last one in the enum */
502};
@ REDIRECTING_OPT_ARG_ARRAY_SIZE
@ REDIRECTING_OPT_DUMMY

◆ REDIRECTING_OPT_FLAGS

Enumerator
REDIRECTING_OPT_INHIBIT 

Definition at line 494 of file func_callerid.c.

494 {
495 REDIRECTING_OPT_INHIBIT = (1 << 0),
496};
@ REDIRECTING_OPT_INHIBIT

Function Documentation

◆ __reg_module()

static void __reg_module ( void  )
static

Definition at line 1864 of file func_callerid.c.

◆ __unreg_module()

static void __unreg_module ( void  )
static

Definition at line 1864 of file func_callerid.c.

◆ AST_MODULE_SELF_SYM()

struct ast_module * AST_MODULE_SELF_SYM ( void  )

Definition at line 1864 of file func_callerid.c.

◆ callerid_read()

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

< Member name

< Optional caller id to parse instead of from the channel.

Definition at line 959 of file func_callerid.c.

960{
961 char *parms;
962 struct ast_party_members member = { 0, };
964 AST_APP_ARG(member); /*!< Member name */
965 AST_APP_ARG(cid); /*!< Optional caller id to parse instead of from the channel. */
966 );
967
968 /* Ensure that the buffer is empty */
969 *buf = 0;
970
971 if (!chan) {
972 return -1;
973 }
974
975 parms = ast_strdupa(data);
977 if (args.argc == 0) {
978 /* Must have at least one argument. */
979 return -1;
980 }
981
983 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
984 /* Too few or too many subnames */
985 return -1;
986 }
987
988 if (args.argc == 2) {
989 char name[80];
990 char num[80];
991
992 ast_callerid_split(args.cid, name, sizeof(name), num, sizeof(num));
993
994 if (member.argc == 1 && !strcasecmp("all", member.subnames[0])) {
995 snprintf(buf, len, "\"%s\" <%s>", name, num);
996 } else if (member.argc == 1 && !strcasecmp("name", member.subnames[0])) {
998 } else if (member.argc == 1 && !strncasecmp("num", member.subnames[0], 3)) {
999 /* Accept num[ber] */
1000 ast_copy_string(buf, num, len);
1001 } else {
1002 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1003 }
1004 } else {
1006 ast_channel_lock(chan);
1007
1008 if (member.argc == 1 && !strcasecmp("rdnis", member.subnames[0])) {
1009 if (ast_channel_redirecting(chan)->from.number.valid
1010 && ast_channel_redirecting(chan)->from.number.str) {
1011 ast_copy_string(buf, ast_channel_redirecting(chan)->from.number.str, len);
1012 }
1013 } else if (!strcasecmp("dnid", member.subnames[0])) {
1014 if (member.argc == 1) {
1015 /* Setup as if user had given dnid-num instead. */
1016 member.argc = 2;
1017 member.subnames[1] = "num";
1018 }
1019 if (!strncasecmp("num", member.subnames[1], 3)) {
1020 /*
1021 * Accept num[ber]
1022 * dnid-num...
1023 */
1024 if (member.argc == 2) {
1025 /* dnid-num */
1026 if (ast_channel_dialed(chan)->number.str) {
1028 }
1029 } else if (member.argc == 3 && !strcasecmp("plan", member.subnames[2])) {
1030 /* dnid-num-plan */
1031 snprintf(buf, len, "%d", ast_channel_dialed(chan)->number.plan);
1032 } else {
1033 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1034 }
1035 } else if (!strncasecmp("subaddr", member.subnames[1], 7)) {
1036 /*
1037 * Accept subaddr[ess]
1038 * dnid-subaddr...
1039 */
1040 status = party_subaddress_read(buf, len, member.argc - 2, member.subnames + 2,
1041 &ast_channel_dialed(chan)->subaddress);
1042 switch (status) {
1043 case ID_FIELD_VALID:
1044 case ID_FIELD_INVALID:
1045 break;
1046 default:
1047 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1048 break;
1049 }
1050 } else {
1051 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1052 }
1053 } else if (member.argc == 1 && !strcasecmp("ani2", member.subnames[0])) {
1054 /* ANI2 is always formatted as two digits:
1055 * https://nanpa.com/numbering/ani-ii-digits */
1056 snprintf(buf, len, "%02d", ast_channel_caller(chan)->ani2);
1057 } else if (!strcasecmp("ani", member.subnames[0])) {
1058 if (member.argc == 1) {
1059 /* Setup as if user had given ani-num instead. */
1060 member.argc = 2;
1061 member.subnames[1] = "num";
1062 }
1063 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1064 &ast_channel_caller(chan)->ani);
1065 switch (status) {
1066 case ID_FIELD_VALID:
1067 case ID_FIELD_INVALID:
1068 break;
1069 default:
1070 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1071 break;
1072 }
1073 } else if (!strcasecmp("priv", member.subnames[0])) {
1074 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1075 &ast_channel_caller(chan)->priv);
1076 switch (status) {
1077 case ID_FIELD_VALID:
1078 case ID_FIELD_INVALID:
1079 break;
1080 default:
1081 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1082 break;
1083 }
1084 } else {
1085 status = party_id_read(buf, len, member.argc, member.subnames, &ast_channel_caller(chan)->id);
1086 switch (status) {
1087 case ID_FIELD_VALID:
1088 case ID_FIELD_INVALID:
1089 break;
1090 default:
1091 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1092 break;
1093 }
1094 }
1095
1096 ast_channel_unlock(chan);
1097 }
1098
1099 return 0;
1100}
jack_status_t status
Definition app_jack.c:149
#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_callerid_split(const char *src, char *name, int namelen, char *num, int numlen)
Definition callerid.c:1292
#define ast_channel_lock(chan)
Definition channel.h:2982
struct ast_party_redirecting * ast_channel_redirecting(struct ast_channel *chan)
struct ast_party_dialed * ast_channel_dialed(struct ast_channel *chan)
struct ast_party_caller * ast_channel_caller(struct ast_channel *chan)
#define ast_channel_unlock(chan)
Definition channel.h:2983
char buf[BUFSIZE]
Definition eagi_proxy.c:66
static const char name[]
Definition format_mp3.c:68
ID_FIELD_STATUS
static enum ID_FIELD_STATUS party_id_read(char *buf, size_t len, int argc, char *argv[], const struct ast_party_id *id)
static enum ID_FIELD_STATUS party_subaddress_read(char *buf, size_t len, int argc, char *argv[], const struct ast_party_subaddress *subaddress)
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
#define AST_APP_ARG(name)
Define an application argument.
#define AST_DECLARE_APP_ARGS(name, arglist)
Declare a structure to hold an application's arguments.
#define AST_STANDARD_APP_ARGS(args, parse)
Performs the 'standard' argument separation process for an application.
#define AST_NONSTANDARD_APP_ARGS(args, parse, sep)
Performs the 'nonstandard' argument separation process for an application.
#define LOG_ERROR
static struct @519 args
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
Definition strings.h:425
Number structure.
#define ARRAY_LEN(a)
Definition utils.h:706

References args, ARRAY_LEN, AST_APP_ARG, ast_callerid_split(), ast_channel_caller(), ast_channel_dialed(), ast_channel_lock, ast_channel_redirecting(), ast_channel_unlock, ast_copy_string(), AST_DECLARE_APP_ARGS, ast_log, AST_NONSTANDARD_APP_ARGS, AST_STANDARD_APP_ARGS, ast_strdupa, buf, ID_FIELD_INVALID, ID_FIELD_VALID, len(), LOG_ERROR, name, party_id_read(), party_subaddress_read(), and status.

◆ callerid_write()

static int callerid_write ( struct ast_channel chan,
const char *  cmd,
char *  data,
const char *  value 
)
static

Definition at line 1114 of file func_callerid.c.

1115{
1116 struct ast_party_caller caller;
1117 struct ast_party_dialed dialed;
1119 char *val;
1120 char *parms;
1121 struct ast_party_func_args args = { 0, };
1122 struct ast_party_members member = { 0, };
1123
1124 if (!value || !chan) {
1125 return -1;
1126 }
1127
1128 parms = ast_strdupa(data);
1130 if (args.argc == 0) {
1131 /* Must have at least one argument. */
1132 return -1;
1133 }
1134
1135 AST_NONSTANDARD_APP_ARGS(member, args.member, '-');
1136 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
1137 /* Too few or too many subnames */
1138 return -1;
1139 }
1140
1142
1143 ast_channel_lock(chan);
1144 if (member.argc == 1 && !strcasecmp("rdnis", member.subnames[0])) {
1146 ast_free(ast_channel_redirecting(chan)->from.number.str);
1148 } else if (!strcasecmp("dnid", member.subnames[0])) {
1150 if (member.argc == 1) {
1151 /* Setup as if user had given dnid-num instead. */
1152 member.argc = 2;
1153 member.subnames[1] = "num";
1154 }
1155 if (!strncasecmp("num", member.subnames[1], 3)) {
1156 /*
1157 * Accept num[ber]
1158 * dnid-num...
1159 */
1160 if (member.argc == 2) {
1161 /* dnid-num */
1162 dialed.number.str = ast_strdup(value);
1163 ast_trim_blanks(dialed.number.str);
1165 } else if (member.argc == 3 && !strcasecmp("plan", member.subnames[2])) {
1166 /* dnid-num-plan */
1169
1170 if (('0' <= val[0]) && (val[0] <= '9')) {
1171 ast_channel_dialed(chan)->number.plan = atoi(val);
1172 } else {
1174 "Unknown type-of-number/numbering-plan '%s', value unchanged\n", val);
1175 }
1176 } else {
1177 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1178 }
1179 } else if (!strncasecmp("subaddr", member.subnames[1], 7)) {
1180 /*
1181 * Accept subaddr[ess]
1182 * dnid-subaddr...
1183 */
1184 status = party_subaddress_write(&dialed.subaddress, member.argc - 2,
1185 member.subnames + 2, value);
1186 switch (status) {
1187 case ID_FIELD_VALID:
1189 break;
1190 case ID_FIELD_INVALID:
1191 break;
1192 default:
1193 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1194 break;
1195 }
1196 } else {
1197 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1198 }
1199 ast_party_dialed_free(&dialed);
1200 } else if (member.argc == 1 && !strcasecmp("ani2", member.subnames[0])) {
1203
1204 if (('0' <= val[0]) && (val[0] <= '9')) {
1205 ast_channel_caller(chan)->ani2 = atoi(val);
1206 } else {
1207 ast_log(LOG_ERROR, "Unknown callerid ani2 '%s', value unchanged\n", val);
1208 }
1209 } else if (!strcasecmp("ani", member.subnames[0])) {
1211 if (member.argc == 1) {
1212 /* Setup as if user had given ani-num instead. */
1213 member.argc = 2;
1214 member.subnames[1] = "num";
1215 }
1216 status = party_id_write(&caller.ani, member.argc - 1, member.subnames + 1, value);
1217 switch (status) {
1218 case ID_FIELD_VALID:
1220 break;
1221 case ID_FIELD_INVALID:
1222 break;
1223 default:
1224 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1225 break;
1226 }
1227 ast_party_caller_free(&caller);
1228 } else if (!strcasecmp("priv", member.subnames[0])) {
1230 status = party_id_write(&caller.priv, member.argc - 1, member.subnames + 1, value);
1231 switch (status) {
1232 case ID_FIELD_VALID:
1234 break;
1235 case ID_FIELD_INVALID:
1236 break;
1237 default:
1238 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1239 break;
1240 }
1241 ast_party_caller_free(&caller);
1242 } else {
1244 status = party_id_write(&caller.id, member.argc, member.subnames, value);
1245 switch (status) {
1246 case ID_FIELD_VALID:
1247 ast_channel_set_caller_event(chan, &caller, NULL);
1248 break;
1249 case ID_FIELD_INVALID:
1250 break;
1251 default:
1252 ast_log(LOG_ERROR, "Unknown callerid data type '%s'.\n", data);
1253 break;
1254 }
1255 ast_party_caller_free(&caller);
1256 }
1257 ast_channel_unlock(chan);
1258
1259 return 0;
1260}
#define ast_free(a)
Definition astmm.h:180
#define ast_strdup(str)
A wrapper for strdup()
Definition astmm.h:241
void ast_party_dialed_set_init(struct ast_party_dialed *init, const struct ast_party_dialed *guide)
Initialize the given dialed structure using the given guide for a set update operation.
Definition channel.c:1936
void ast_channel_set_caller_event(struct ast_channel *chan, const struct ast_party_caller *caller, const struct ast_set_party_caller *update)
Set the caller id information in the Asterisk channel and generate an AMI event if the caller id name...
Definition channel.c:7384
void ast_party_caller_set(struct ast_party_caller *dest, const struct ast_party_caller *src, const struct ast_set_party_caller *update)
Set the caller information based on another caller source.
Definition channel.c:1993
void ast_party_caller_set_init(struct ast_party_caller *init, const struct ast_party_caller *guide)
Initialize the given caller structure using the given guide for a set update operation.
Definition channel.c:1985
void ast_party_dialed_free(struct ast_party_dialed *doomed)
Destroy the dialed party contents.
Definition channel.c:1957
void ast_party_caller_free(struct ast_party_caller *doomed)
Destroy the caller party contents.
Definition channel.c:2001
void ast_party_dialed_set(struct ast_party_dialed *dest, const struct ast_party_dialed *src)
Set the dialed information based on another dialed source.
Definition channel.c:1944
static enum ID_FIELD_STATUS party_id_write(struct ast_party_id *id, int argc, char *argv[], const char *value)
static enum ID_FIELD_STATUS party_subaddress_write(struct ast_party_subaddress *subaddress, int argc, char *argv[], const char *value)
#define NULL
Definition resample.c:96
char * ast_trim_blanks(char *str)
Trims trailing whitespace characters from a string.
Definition strings.h:186
char *attribute_pure ast_skip_blanks(const char *str)
Gets a pointer to the first non-whitespace character in a string.
Definition strings.h:161
Caller Party information.
Definition channel.h:420
int ani2
Automatic Number Identification 2 (Info Digits)
Definition channel.h:435
Dialed/Called Party information.
Definition channel.h:380
int plan
Q.931 Type-Of-Number and Numbering-Plan encoded fields.
Definition channel.h:390
struct ast_party_dialed::@221 number
Dialed/Called number.
struct ast_party_number number
Subscriber phone number.
Definition channel.h:344
unsigned char valid
TRUE if the number information is valid/present.
Definition channel.h:299
char * str
Subscriber phone number (Malloced)
Definition channel.h:293
struct ast_party_id from
Who is redirecting the call (Sent to the party the call is redirected toward)
Definition channel.h:529
int value
Definition syslog.c:37

References ast_party_caller::ani, ast_party_caller::ani2, args, ARRAY_LEN, ast_channel_caller(), ast_channel_dialed(), ast_channel_lock, ast_channel_redirecting(), ast_channel_set_caller_event(), ast_channel_unlock, ast_free, ast_log, AST_NONSTANDARD_APP_ARGS, ast_party_caller_free(), ast_party_caller_set(), ast_party_caller_set_init(), ast_party_dialed_free(), ast_party_dialed_set(), ast_party_dialed_set_init(), ast_skip_blanks(), AST_STANDARD_APP_ARGS, ast_strdup, ast_strdupa, ast_trim_blanks(), ast_party_redirecting::from, ast_party_caller::id, ID_FIELD_INVALID, ID_FIELD_VALID, LOG_ERROR, NULL, ast_party_id::number, ast_party_dialed::number, party_id_write(), party_subaddress_write(), ast_party_dialed::plan, ast_party_caller::priv, status, ast_party_number::str, ast_party_dialed::str, ast_party_dialed::subaddress, ast_party_number::valid, and value.

◆ connectedline_read()

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

Definition at line 1275 of file func_callerid.c.

1276{
1277 struct ast_party_members member = { 0, };
1278 char *read_what;
1280
1281 /* Ensure that the buffer is empty */
1282 *buf = 0;
1283
1284 if (!chan) {
1285 return -1;
1286 }
1287
1288 read_what = ast_strdupa(data);
1289 AST_NONSTANDARD_APP_ARGS(member, read_what, '-');
1290 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
1291 /* Too few or too many subnames */
1292 return -1;
1293 }
1294
1295 ast_channel_lock(chan);
1296
1297 if (member.argc == 1 && !strcasecmp("source", member.subnames[0])) {
1299 } else if (!strcasecmp("priv", member.subnames[0])) {
1300 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1301 &ast_channel_connected(chan)->priv);
1302 switch (status) {
1303 case ID_FIELD_VALID:
1304 case ID_FIELD_INVALID:
1305 break;
1306 default:
1307 ast_log(LOG_ERROR, "Unknown connectedline data type '%s'.\n", data);
1308 break;
1309 }
1310 } else {
1311 status = party_id_read(buf, len, member.argc, member.subnames, &ast_channel_connected(chan)->id);
1312 switch (status) {
1313 case ID_FIELD_VALID:
1314 case ID_FIELD_INVALID:
1315 break;
1316 default:
1317 ast_log(LOG_ERROR, "Unknown connectedline data type '%s'.\n", data);
1318 break;
1319 }
1320 }
1321
1322 ast_channel_unlock(chan);
1323
1324 return 0;
1325}
const char * ast_connected_line_source_name(int data)
Convert connected line update source value to text code.
Definition callerid.c:1505
struct ast_party_connected_line * ast_channel_connected(struct ast_channel *chan)

References ARRAY_LEN, ast_channel_connected(), ast_channel_lock, ast_channel_unlock, ast_connected_line_source_name(), ast_copy_string(), ast_log, AST_NONSTANDARD_APP_ARGS, ast_strdupa, buf, ID_FIELD_INVALID, ID_FIELD_VALID, len(), LOG_ERROR, party_id_read(), and status.

◆ connectedline_write()

static int connectedline_write ( struct ast_channel chan,
const char *  cmd,
char *  data,
const char *  value 
)
static

Definition at line 1339 of file func_callerid.c.

1340{
1342 char *val;
1343 char *parms;
1344 void (*set_it)(struct ast_channel *chan, const struct ast_party_connected_line *connected, const struct ast_set_party_connected_line *update);
1345 struct ast_party_func_args args = { 0, };
1346 struct ast_party_members member = { 0, };
1347 struct ast_flags opts;
1348 char *opt_args[CONNECTED_LINE_OPT_ARG_ARRAY_SIZE];
1350
1351 if (!value || !chan) {
1352 return -1;
1353 }
1354
1355 parms = ast_strdupa(data);
1357 if (args.argc == 0) {
1358 /* Must have at least one argument. */
1359 return -1;
1360 }
1361
1362 AST_NONSTANDARD_APP_ARGS(member, args.member, '-');
1363 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
1364 /* Too few or too many subnames */
1365 return -1;
1366 }
1367
1368 if (ast_app_parse_options(connectedline_opts, &opts, opt_args, args.opts)) {
1369 /* General invalid option syntax. */
1370 return -1;
1371 }
1372
1373 /* Determine if the update indication inhibit option is present */
1376 } else {
1378 }
1379
1380 ast_channel_lock(chan);
1382 ast_channel_unlock(chan);
1383
1385
1386 if (member.argc == 1 && !strcasecmp("source", member.subnames[0])) {
1387 int source;
1388
1391
1392 if (('0' <= val[0]) && (val[0] <= '9')) {
1393 source = atoi(val);
1394 } else {
1396 }
1397
1398 if (source < 0) {
1399 ast_log(LOG_ERROR, "Unknown connectedline source '%s', value unchanged\n", val);
1400 } else {
1401 connected.source = source;
1402 set_it(chan, &connected, NULL);
1403 }
1404 } else if (!strcasecmp("priv", member.subnames[0])) {
1405 status = party_id_write(&connected.priv, member.argc - 1, member.subnames + 1, value);
1406 switch (status) {
1407 case ID_FIELD_VALID:
1408 set_it(chan, &connected, NULL);
1409 break;
1410 case ID_FIELD_INVALID:
1411 break;
1412 default:
1413 ast_log(LOG_ERROR, "Unknown connectedline data type '%s'.\n", data);
1414 break;
1415 }
1417 } else {
1418 status = party_id_write(&connected.id, member.argc, member.subnames, value);
1419 switch (status) {
1420 case ID_FIELD_VALID:
1421 set_it(chan, &connected, NULL);
1422 break;
1423 case ID_FIELD_INVALID:
1424 break;
1425 default:
1426 ast_log(LOG_ERROR, "Unknown connectedline data type '%s'.\n", data);
1427 break;
1428 }
1430 }
1431
1432 return 0;
1433}
int ast_connected_line_source_parse(const char *data)
Convert connected line update source text code to value (used in config file parsing)
Definition callerid.c:1479
static int connected
Definition cdr_pgsql.c:73
void ast_channel_set_connected_line(struct ast_channel *chan, const struct ast_party_connected_line *connected, const struct ast_set_party_connected_line *update)
Set the connected line information in the Asterisk channel.
Definition channel.c:8352
void ast_party_connected_line_free(struct ast_party_connected_line *doomed)
Destroy the connected line information contents.
Definition channel.c:2058
void ast_channel_update_connected_line(struct ast_channel *chan, const struct ast_party_connected_line *connected, const struct ast_set_party_connected_line *update)
Indicate that the connected line information has changed.
Definition channel.c:9137
void ast_party_connected_line_set_init(struct ast_party_connected_line *init, const struct ast_party_connected_line *guide)
Initialize the given connected line structure using the given guide for a set update operation.
Definition channel.c:2031
static void update(int code_size, int y, int wi, int fi, int dq, int sr, int dqsez, struct g726_state *state_ptr)
Definition codec_g726.c:367
static const struct ast_app_option connectedline_opts[128]
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
Main Channel structure associated with a channel.
Structure used to handle boolean flags.
Definition utils.h:220
Connected Line/Party information.
Definition channel.h:458
Indicate what information in ast_party_connected_line should be set.
Definition channel.h:491
#define ast_test_flag(p, flag)
Definition utils.h:64

References args, ARRAY_LEN, ast_app_parse_options(), ast_channel_connected(), ast_channel_lock, ast_channel_set_connected_line(), ast_channel_unlock, ast_channel_update_connected_line(), ast_connected_line_source_parse(), ast_log, AST_NONSTANDARD_APP_ARGS, ast_party_connected_line_free(), ast_party_connected_line_set_init(), ast_skip_blanks(), AST_STANDARD_APP_ARGS, ast_strdupa, ast_test_flag, ast_trim_blanks(), connected, CONNECTED_LINE_OPT_ARG_ARRAY_SIZE, CONNECTED_LINE_OPT_INHIBIT, connectedline_opts, ID_FIELD_INVALID, ID_FIELD_VALID, LOG_ERROR, NULL, party_id_write(), status, update(), and value.

◆ load_module()

static int load_module ( void  )
static

Definition at line 1847 of file func_callerid.c.

1848{
1849 int res;
1850
1854
1855 if (res) {
1856 unload_module();
1858 }
1859
1861}
static struct ast_custom_function callerid_function
static struct ast_custom_function connectedline_function
static int unload_module(void)
static struct ast_custom_function redirecting_function
@ AST_MODULE_LOAD_SUCCESS
Definition module.h:70
@ AST_MODULE_LOAD_DECLINE
Module has failed to load, may be in an inconsistent state.
Definition module.h:78
#define ast_custom_function_register(acf)
Register a custom function.
Definition pbx.h:1562

References ast_custom_function_register, AST_MODULE_LOAD_DECLINE, AST_MODULE_LOAD_SUCCESS, callerid_function, connectedline_function, redirecting_function, and unload_module().

◆ party_id_read()

static enum ID_FIELD_STATUS party_id_read ( char *  buf,
size_t  len,
int  argc,
char *  argv[],
const struct ast_party_id id 
)
static

Definition at line 638 of file func_callerid.c.

639{
641
642 if (argc == 0) {
643 /* Must have at least one subname. */
644 return ID_FIELD_UNKNOWN;
645 }
646
648
649 if (argc == 1 && !strcasecmp("all", argv[0])) {
650 snprintf(buf, len, "\"%s\" <%s>",
651 S_COR(id->name.valid, id->name.str, ""),
652 S_COR(id->number.valid, id->number.str, ""));
653 } else if (!strcasecmp("name", argv[0])) {
654 status = party_name_read(buf, len, argc - 1, argv + 1, &id->name);
655 } else if (!strncasecmp("num", argv[0], 3)) {
656 /* Accept num[ber] */
657 status = party_number_read(buf, len, argc - 1, argv + 1, &id->number);
658 } else if (!strncasecmp("subaddr", argv[0], 7)) {
659 /* Accept subaddr[ess] */
660 status = party_subaddress_read(buf, len, argc - 1, argv + 1, &id->subaddress);
661 } else if (argc == 1 && !strcasecmp("tag", argv[0])) {
662 if (id->tag) {
663 ast_copy_string(buf, id->tag, len);
664 }
665 } else if (argc == 1 && !strcasecmp("ton", argv[0])) {
666 /* ton is an alias for num-plan */
667 snprintf(buf, len, "%d", id->number.plan);
668 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
669 /*
670 * Accept pres[entation]
671 * This is the combined name/number presentation.
672 */
675 } else {
677 }
678
679 return status;
680}
enum queue_result id
Definition app_queue.c:1771
const char * ast_named_caller_presentation(int data)
Convert caller ID pres value to text code.
Definition callerid.c:1382
int ast_party_id_presentation(const struct ast_party_id *id)
Determine the overall presentation value for the given party.
Definition channel.c:1807
static enum ID_FIELD_STATUS party_name_read(char *buf, size_t len, int argc, char *argv[], const struct ast_party_name *name)
static enum ID_FIELD_STATUS party_number_read(char *buf, size_t len, int argc, char *argv[], const struct ast_party_number *number)
#define S_COR(a, b, c)
returns the equivalent of logic or for strings, with an additional boolean check: second one if not e...
Definition strings.h:87

References ast_copy_string(), ast_named_caller_presentation(), ast_party_id_presentation(), buf, id, ID_FIELD_UNKNOWN, ID_FIELD_VALID, len(), party_name_read(), party_number_read(), party_subaddress_read(), S_COR, and status.

Referenced by callerid_read(), connectedline_read(), and redirecting_read().

◆ party_id_write()

static enum ID_FIELD_STATUS party_id_write ( struct ast_party_id id,
int  argc,
char *  argv[],
const char *  value 
)
static

Definition at line 873 of file func_callerid.c.

874{
875 char *val;
877
878 if (argc == 0) {
879 /* Must have at least one subname. */
880 return ID_FIELD_UNKNOWN;
881 }
882
884
885 if (argc == 1 && !strcasecmp("all", argv[0])) {
886 char name[256];
887 char num[256];
888
889 ast_callerid_split(value, name, sizeof(name), num, sizeof(num));
890 id->name.valid = 1;
891 id->name.str = ast_strdup(name);
892 if (!id->name.str) {
893 return ID_FIELD_INVALID;
894 }
895 id->number.valid = 1;
896 id->number.str = ast_strdup(num);
897 if (!id->number.str) {
898 return ID_FIELD_INVALID;
899 }
900 } else if (!strcasecmp("name", argv[0])) {
901 status = party_name_write(&id->name, argc - 1, argv + 1, value);
902 } else if (!strncasecmp("num", argv[0], 3)) {
903 /* Accept num[ber] */
904 status = party_number_write(&id->number, argc - 1, argv + 1, value);
905 } else if (!strncasecmp("subaddr", argv[0], 7)) {
906 /* Accept subaddr[ess] */
907 status = party_subaddress_write(&id->subaddress, argc - 1, argv + 1, value);
908 } else if (argc == 1 && !strcasecmp("tag", argv[0])) {
909 id->tag = ast_strdup(value);
910 ast_trim_blanks(id->tag);
911 } else if (argc == 1 && !strcasecmp("ton", argv[0])) {
912 /* ton is an alias for num-plan */
913 argv[0] = "plan";
914 status = party_number_write(&id->number, argc, argv, value);
915 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
916 int pres;
917
918 /*
919 * Accept pres[entation]
920 * This is the combined name/number presentation.
921 */
924
925 if (('0' <= val[0]) && (val[0] <= '9')) {
926 pres = atoi(val);
927 } else {
929 }
930
931 if (pres < 0) {
933 "Unknown combined presentation '%s', value unchanged\n", val);
935 } else {
936 id->name.presentation = pres;
937 id->number.presentation = pres;
938 }
939 } else {
941 }
942
943 return status;
944}
int ast_parse_caller_presentation(const char *data)
Convert caller ID text code to value (used in config file parsing)
Definition callerid.c:1343
static enum ID_FIELD_STATUS party_name_write(struct ast_party_name *name, int argc, char *argv[], const char *value)
static enum ID_FIELD_STATUS party_number_write(struct ast_party_number *number, int argc, char *argv[], const char *value)

References ast_callerid_split(), ast_log, ast_parse_caller_presentation(), ast_strdup, ast_strdupa, ast_trim_blanks(), id, ID_FIELD_INVALID, ID_FIELD_UNKNOWN, ID_FIELD_VALID, LOG_ERROR, name, party_name_write(), party_number_write(), party_subaddress_write(), status, and value.

Referenced by callerid_write(), connectedline_write(), and redirecting_write().

◆ party_name_read()

static enum ID_FIELD_STATUS party_name_read ( char *  buf,
size_t  len,
int  argc,
char *  argv[],
const struct ast_party_name name 
)
static

Definition at line 522 of file func_callerid.c.

523{
525
527
528 if (argc == 0) {
529 /* We want the name string */
530 if (name->valid && name->str) {
531 ast_copy_string(buf, name->str, len);
532 }
533 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
534 snprintf(buf, len, "%d", name->valid);
535 } else if (argc == 1 && !strcasecmp("charset", argv[0])) {
537 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
538 /* Accept pres[entation] */
540 } else {
542 }
543
544 return status;
545}
const char * ast_party_name_charset_str(int data)
Convert ast_party_name.char_set value to text code.
Definition callerid.c:1560

References ast_copy_string(), ast_named_caller_presentation(), ast_party_name_charset_str(), buf, ID_FIELD_UNKNOWN, ID_FIELD_VALID, len(), name, and status.

Referenced by party_id_read().

◆ party_name_write()

static enum ID_FIELD_STATUS party_name_write ( struct ast_party_name name,
int  argc,
char *  argv[],
const char *  value 
)
static

Definition at line 696 of file func_callerid.c.

697{
698 char *val;
700
702
703 if (argc == 0) {
704 /* We are setting the name string */
705 name->valid = 1;
706 name->str = ast_strdup(value);
707 ast_trim_blanks(name->str);
708 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
709 name->valid = atoi(value) ? 1 : 0;
710 } else if (argc == 1 && !strcasecmp("charset", argv[0])) {
711 int char_set;
712
715
716 if (('0' <= val[0]) && (val[0] <= '9')) {
717 char_set = atoi(val);
718 } else {
720 }
721
722 if (char_set < 0) {
724 "Unknown name char-set '%s', value unchanged\n", val);
726 } else {
727 name->char_set = char_set;
728 }
729 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
730 int pres;
731
732 /* Accept pres[entation] */
735
736 if (('0' <= val[0]) && (val[0] <= '9')) {
737 pres = atoi(val);
738 } else {
740 }
741
742 if (pres < 0) {
744 "Unknown name presentation '%s', value unchanged\n", val);
746 } else {
747 name->presentation = pres;
748 }
749 } else {
751 }
752
753 return status;
754}
int ast_party_name_charset_parse(const char *data)
Convert ast_party_name.char_set text code to value (used in config file parsing)
Definition callerid.c:1534

References ast_log, ast_parse_caller_presentation(), ast_party_name_charset_parse(), ast_strdup, ast_strdupa, ast_trim_blanks(), ID_FIELD_INVALID, ID_FIELD_UNKNOWN, ID_FIELD_VALID, LOG_ERROR, name, status, and value.

Referenced by party_id_write().

◆ party_number_read()

static enum ID_FIELD_STATUS party_number_read ( char *  buf,
size_t  len,
int  argc,
char *  argv[],
const struct ast_party_number number 
)
static

Definition at line 561 of file func_callerid.c.

562{
564
566
567 if (argc == 0) {
568 /* We want the number string */
569 if (number->valid && number->str) {
571 }
572 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
573 snprintf(buf, len, "%d", number->valid);
574 } else if (argc == 1 && !strcasecmp("plan", argv[0])) {
575 snprintf(buf, len, "%d", number->plan);
576 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
577 /* Accept pres[entation] */
579 } else {
581 }
582
583 return status;
584}

References ast_copy_string(), ast_named_caller_presentation(), buf, ID_FIELD_UNKNOWN, ID_FIELD_VALID, len(), and status.

Referenced by party_id_read().

◆ party_number_write()

static enum ID_FIELD_STATUS party_number_write ( struct ast_party_number number,
int  argc,
char *  argv[],
const char *  value 
)
static

Definition at line 770 of file func_callerid.c.

771{
772 char *val;
774
776
777 if (argc == 0) {
778 /* We are setting the number string */
779 number->valid = 1;
780 number->str = ast_strdup(value);
782 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
783 number->valid = atoi(value) ? 1 : 0;
784 } else if (argc == 1 && !strcasecmp("plan", argv[0])) {
787
788 if (('0' <= val[0]) && (val[0] <= '9')) {
789 number->plan = atoi(val);
790 } else {
792 "Unknown type-of-number/numbering-plan '%s', value unchanged\n", val);
794 }
795 } else if (argc == 1 && !strncasecmp("pres", argv[0], 4)) {
796 int pres;
797
798 /* Accept pres[entation] */
801
802 if (('0' <= val[0]) && (val[0] <= '9')) {
803 pres = atoi(val);
804 } else {
806 }
807
808 if (pres < 0) {
810 "Unknown number presentation '%s', value unchanged\n", val);
812 } else {
813 number->presentation = pres;
814 }
815 } else {
817 }
818
819 return status;
820}

References ast_log, ast_parse_caller_presentation(), ast_strdup, ast_strdupa, ast_trim_blanks(), ID_FIELD_INVALID, ID_FIELD_UNKNOWN, ID_FIELD_VALID, LOG_ERROR, status, and value.

Referenced by party_id_write().

◆ party_subaddress_read()

static enum ID_FIELD_STATUS party_subaddress_read ( char *  buf,
size_t  len,
int  argc,
char *  argv[],
const struct ast_party_subaddress subaddress 
)
static

Definition at line 600 of file func_callerid.c.

601{
603
605
606 if (argc == 0) {
607 /* We want the subaddress string */
608 if (subaddress->str) {
609 ast_copy_string(buf, subaddress->str, len);
610 }
611 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
612 snprintf(buf, len, "%d", subaddress->valid);
613 } else if (argc == 1 && !strcasecmp("type", argv[0])) {
614 snprintf(buf, len, "%d", subaddress->type);
615 } else if (argc == 1 && !strcasecmp("odd", argv[0])) {
616 snprintf(buf, len, "%d", subaddress->odd_even_indicator);
617 } else {
619 }
620
621 return status;
622}
unsigned char odd_even_indicator
TRUE if odd number of address signals.
Definition channel.h:328
unsigned char valid
TRUE if the subaddress information is valid/present.
Definition channel.h:330
char * str
Malloced subaddress string.
Definition channel.h:315
int type
Q.931 subaddress type.
Definition channel.h:322

References ast_copy_string(), buf, ID_FIELD_UNKNOWN, ID_FIELD_VALID, len(), ast_party_subaddress::odd_even_indicator, status, ast_party_subaddress::str, ast_party_subaddress::type, and ast_party_subaddress::valid.

Referenced by callerid_read(), and party_id_read().

◆ party_subaddress_write()

static enum ID_FIELD_STATUS party_subaddress_write ( struct ast_party_subaddress subaddress,
int  argc,
char *  argv[],
const char *  value 
)
static

Definition at line 836 of file func_callerid.c.

837{
839
841
842 if (argc == 0) {
843 /* We are setting the subaddress string */
844 subaddress->str = ast_strdup(value);
845 ast_trim_blanks(subaddress->str);
846 } else if (argc == 1 && !strcasecmp("valid", argv[0])) {
847 subaddress->valid = atoi(value) ? 1 : 0;
848 } else if (argc == 1 && !strcasecmp("type", argv[0])) {
849 subaddress->type = atoi(value) ? 2 : 0;
850 } else if (argc == 1 && !strcasecmp("odd", argv[0])) {
851 subaddress->odd_even_indicator = atoi(value) ? 1 : 0;
852 } else {
854 }
855
856 return status;
857}

References ast_strdup, ast_trim_blanks(), ID_FIELD_UNKNOWN, ID_FIELD_VALID, ast_party_subaddress::odd_even_indicator, status, ast_party_subaddress::str, ast_party_subaddress::type, ast_party_subaddress::valid, and value.

Referenced by callerid_write(), and party_id_write().

◆ redirecting_read()

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

Definition at line 1448 of file func_callerid.c.

1449{
1450 struct ast_party_members member = { 0, };
1451 char *read_what;
1452 const struct ast_party_redirecting *ast_redirecting;
1454
1455 /* Ensure that the buffer is empty */
1456 *buf = 0;
1457
1458 if (!chan) {
1459 return -1;
1460 }
1461
1462 read_what = ast_strdupa(data);
1463 AST_NONSTANDARD_APP_ARGS(member, read_what, '-');
1464 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
1465 /* Too few or too many subnames */
1466 return -1;
1467 }
1468
1469 ast_channel_lock(chan);
1470
1471 ast_redirecting = ast_channel_redirecting(chan);
1472 if (!strcasecmp("orig", member.subnames[0])) {
1473 if (member.argc == 2 && !strcasecmp("reason", member.subnames[1])) {
1475 ast_redirecting_reason_name(&ast_redirecting->orig_reason), len);
1476 } else {
1477 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1478 &ast_redirecting->orig);
1479 switch (status) {
1480 case ID_FIELD_VALID:
1481 case ID_FIELD_INVALID:
1482 break;
1483 default:
1484 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1485 break;
1486 }
1487 }
1488 } else if (!strcasecmp("from", member.subnames[0])) {
1489 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1490 &ast_redirecting->from);
1491 switch (status) {
1492 case ID_FIELD_VALID:
1493 case ID_FIELD_INVALID:
1494 break;
1495 default:
1496 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1497 break;
1498 }
1499 } else if (!strcasecmp("to", member.subnames[0])) {
1500 status = party_id_read(buf, len, member.argc - 1, member.subnames + 1,
1501 &ast_redirecting->to);
1502 switch (status) {
1503 case ID_FIELD_VALID:
1504 case ID_FIELD_INVALID:
1505 break;
1506 default:
1507 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1508 break;
1509 }
1510 } else if (member.argc == 1 && !strncasecmp("pres", member.subnames[0], 4)) {
1511 /*
1512 * Accept pres[entation]
1513 * This is the combined from name/number presentation.
1514 */
1517 ast_party_id_presentation(&ast_redirecting->from)), len);
1518 } else if (member.argc == 1 && !strcasecmp("reason", member.subnames[0])) {
1520 } else if (member.argc == 1 && !strcasecmp("count", member.subnames[0])) {
1521 snprintf(buf, len, "%d", ast_redirecting->count);
1522 } else if (1 < member.argc && !strcasecmp("priv", member.subnames[0])) {
1523 if (!strcasecmp("orig", member.subnames[1])) {
1524 status = party_id_read(buf, len, member.argc - 2, member.subnames + 2,
1525 &ast_redirecting->priv_orig);
1526 switch (status) {
1527 case ID_FIELD_VALID:
1528 case ID_FIELD_INVALID:
1529 break;
1530 default:
1531 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1532 break;
1533 }
1534 } else if (!strcasecmp("from", member.subnames[1])) {
1535 status = party_id_read(buf, len, member.argc - 2, member.subnames + 2,
1536 &ast_redirecting->priv_from);
1537 switch (status) {
1538 case ID_FIELD_VALID:
1539 case ID_FIELD_INVALID:
1540 break;
1541 default:
1542 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1543 break;
1544 }
1545 } else if (!strcasecmp("to", member.subnames[1])) {
1546 status = party_id_read(buf, len, member.argc - 2, member.subnames + 2,
1547 &ast_redirecting->priv_to);
1548 switch (status) {
1549 case ID_FIELD_VALID:
1550 case ID_FIELD_INVALID:
1551 break;
1552 default:
1553 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1554 break;
1555 }
1556 } else {
1557 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1558 }
1559 } else {
1560 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1561 }
1562
1563 ast_channel_unlock(chan);
1564
1565 return 0;
1566}
const char * ast_redirecting_reason_name(const struct ast_party_redirecting_reason *data)
Convert redirecting reason value to text code.
Definition callerid.c:1449
Redirecting Line information. RDNIS (Redirecting Directory Number Information Service) Where a call d...
Definition channel.h:524
struct ast_party_id priv_to
Call is redirecting to a new party (Sent to the caller) - private representation.
Definition channel.h:541
struct ast_party_redirecting_reason orig_reason
Reason for the redirection by the original party.
Definition channel.h:547
struct ast_party_redirecting_reason reason
Reason for the redirection.
Definition channel.h:544
struct ast_party_id priv_from
Who is redirecting the call (Sent to the party the call is redirected toward) - private representatio...
Definition channel.h:538
int count
Number of times the call was redirected.
Definition channel.h:550
struct ast_party_id to
Call is redirecting to a new party (Sent to the caller)
Definition channel.h:532
struct ast_party_id orig
Who originally redirected the call (Sent to the party the call is redirected toward)
Definition channel.h:526
struct ast_party_id priv_orig
Who originally redirected the call (Sent to the party the call is redirected toward) - private repres...
Definition channel.h:535

References ARRAY_LEN, ast_channel_lock, ast_channel_redirecting(), ast_channel_unlock, ast_copy_string(), ast_log, ast_named_caller_presentation(), AST_NONSTANDARD_APP_ARGS, ast_party_id_presentation(), ast_redirecting_reason_name(), ast_strdupa, buf, ast_party_redirecting::count, ast_party_redirecting::from, ID_FIELD_INVALID, ID_FIELD_VALID, len(), LOG_ERROR, ast_party_redirecting::orig, ast_party_redirecting::orig_reason, party_id_read(), ast_party_redirecting::priv_from, ast_party_redirecting::priv_orig, ast_party_redirecting::priv_to, ast_party_redirecting::reason, status, and ast_party_redirecting::to.

◆ redirecting_write()

static int redirecting_write ( struct ast_channel chan,
const char *  cmd,
char *  data,
const char *  value 
)
static

Definition at line 1580 of file func_callerid.c.

1581{
1582 struct ast_party_redirecting redirecting;
1584 char *val;
1585 char *parms;
1586 void (*set_it)(struct ast_channel *chan, const struct ast_party_redirecting *redirecting, const struct ast_set_party_redirecting *update);
1587 struct ast_party_func_args args = { 0, };
1588 struct ast_party_members member = { 0, };
1589 struct ast_flags opts;
1590 char *opt_args[REDIRECTING_OPT_ARG_ARRAY_SIZE];
1591
1592 if (!value || !chan) {
1593 return -1;
1594 }
1595
1596 parms = ast_strdupa(data);
1598 if (args.argc == 0) {
1599 /* Must have at least one argument. */
1600 return -1;
1601 }
1602
1603 AST_NONSTANDARD_APP_ARGS(member, args.member, '-');
1604 if (member.argc == 0 || ARRAY_LEN(member.subnames) <= member.argc) {
1605 /* Too few or too many subnames */
1606 return -1;
1607 }
1608
1609 if (ast_app_parse_options(redirecting_opts, &opts, opt_args, args.opts)) {
1610 /* General invalid option syntax. */
1611 return -1;
1612 }
1613
1614 /* Determine if the update indication inhibit option is present */
1617 } else {
1619 }
1620
1621 ast_channel_lock(chan);
1623 ast_channel_unlock(chan);
1624
1626
1627 if (!strcasecmp("orig", member.subnames[0])) {
1628 if (member.argc == 2 && !strcasecmp("reason", member.subnames[1])) {
1629 int reason;
1630
1633
1634 if (('0' <= val[0]) && (val[0] <= '9')) {
1635 reason = atoi(val);
1636 } else {
1638 }
1639
1640 if (reason < 0) {
1641 /* The argument passed into the function does not correspond to a pre-defined
1642 * reason, so we can just set the reason string to what was given and set the
1643 * code to be unknown
1644 */
1645 ast_log(LOG_WARNING, "Unknown redirecting reason '%s', defaulting to unknown\n", val);
1647 redirecting.orig_reason.str = val;
1648 set_it(chan, &redirecting, NULL);
1649 } else {
1650 redirecting.orig_reason.code = reason;
1651 redirecting.orig_reason.str = "";
1652 set_it(chan, &redirecting, NULL);
1653 }
1654 } else {
1655 status = party_id_write(&redirecting.orig, member.argc - 1, member.subnames + 1,
1656 value);
1657 switch (status) {
1658 case ID_FIELD_VALID:
1659 set_it(chan, &redirecting, NULL);
1660 break;
1661 case ID_FIELD_INVALID:
1662 break;
1663 default:
1664 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1665 break;
1666 }
1667 ast_party_redirecting_free(&redirecting);
1668 }
1669 } else if (!strcasecmp("from", member.subnames[0])) {
1670 status = party_id_write(&redirecting.from, member.argc - 1, member.subnames + 1,
1671 value);
1672 switch (status) {
1673 case ID_FIELD_VALID:
1674 set_it(chan, &redirecting, NULL);
1675 break;
1676 case ID_FIELD_INVALID:
1677 break;
1678 default:
1679 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1680 break;
1681 }
1682 ast_party_redirecting_free(&redirecting);
1683 } else if (!strcasecmp("to", member.subnames[0])) {
1684 status = party_id_write(&redirecting.to, member.argc - 1, member.subnames + 1, value);
1685 switch (status) {
1686 case ID_FIELD_VALID:
1687 set_it(chan, &redirecting, NULL);
1688 break;
1689 case ID_FIELD_INVALID:
1690 break;
1691 default:
1692 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1693 break;
1694 }
1695 ast_party_redirecting_free(&redirecting);
1696 } else if (member.argc == 1 && !strncasecmp("pres", member.subnames[0], 4)) {
1697 int pres;
1698
1701
1702 if (('0' <= val[0]) && (val[0] <= '9')) {
1703 pres = atoi(val);
1704 } else {
1706 }
1707
1708 if (pres < 0) {
1710 "Unknown redirecting combined presentation '%s', value unchanged\n", val);
1711 } else {
1712 redirecting.from.name.presentation = pres;
1713 redirecting.from.number.presentation = pres;
1714 redirecting.to.name.presentation = pres;
1715 redirecting.to.number.presentation = pres;
1716 set_it(chan, &redirecting, NULL);
1717 }
1718 } else if (member.argc == 1 && !strcasecmp("reason", member.subnames[0])) {
1719 int reason;
1720
1723
1724 if (('0' <= val[0]) && (val[0] <= '9')) {
1725 reason = atoi(val);
1726 } else {
1728 }
1729
1730 if (reason < 0) {
1731 /* The argument passed into the function does not correspond to a pre-defined
1732 * reason, so we can just set the reason string to what was given and set the
1733 * code to be unknown
1734 */
1735 ast_log(LOG_WARNING, "Unknown redirecting reason '%s', defaulting to unknown\n", val);
1737 redirecting.reason.str = val;
1738 set_it(chan, &redirecting, NULL);
1739 } else {
1740 redirecting.reason.code = reason;
1741 redirecting.reason.str = "";
1742 set_it(chan, &redirecting, NULL);
1743 }
1744 } else if (member.argc == 1 && !strcasecmp("count", member.subnames[0])) {
1747
1748 if (('0' <= val[0]) && (val[0] <= '9')) {
1749 redirecting.count = atoi(val);
1750 set_it(chan, &redirecting, NULL);
1751 } else {
1752 ast_log(LOG_ERROR, "Unknown redirecting count '%s', value unchanged\n", val);
1753 }
1754 } else if (1 < member.argc && !strcasecmp("priv", member.subnames[0])) {
1755 if (!strcasecmp("orig", member.subnames[1])) {
1756 status = party_id_write(&redirecting.priv_orig, member.argc - 2, member.subnames + 2,
1757 value);
1758 switch (status) {
1759 case ID_FIELD_VALID:
1760 set_it(chan, &redirecting, NULL);
1761 break;
1762 case ID_FIELD_INVALID:
1763 break;
1764 default:
1765 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1766 break;
1767 }
1768 ast_party_redirecting_free(&redirecting);
1769 } else if (!strcasecmp("from", member.subnames[1])) {
1770 status = party_id_write(&redirecting.priv_from, member.argc - 2, member.subnames + 2,
1771 value);
1772 switch (status) {
1773 case ID_FIELD_VALID:
1774 set_it(chan, &redirecting, NULL);
1775 break;
1776 case ID_FIELD_INVALID:
1777 break;
1778 default:
1779 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1780 break;
1781 }
1782 ast_party_redirecting_free(&redirecting);
1783 } else if (!strcasecmp("to", member.subnames[1])) {
1784 status = party_id_write(&redirecting.priv_to, member.argc - 2, member.subnames + 2, value);
1785 switch (status) {
1786 case ID_FIELD_VALID:
1787 set_it(chan, &redirecting, NULL);
1788 break;
1789 case ID_FIELD_INVALID:
1790 break;
1791 default:
1792 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1793 break;
1794 }
1795 ast_party_redirecting_free(&redirecting);
1796 } else {
1797 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1798 }
1799 } else {
1800 ast_log(LOG_ERROR, "Unknown redirecting data type '%s'.\n", data);
1801 }
1802
1803 return 0;
1804}
@ AST_REDIRECTING_REASON_UNKNOWN
Definition callerid.h:499
int ast_redirecting_reason_parse(const char *data)
Convert redirecting reason text code to value (used in config file parsing)
Definition callerid.c:1423
void ast_channel_set_redirecting(struct ast_channel *chan, const struct ast_party_redirecting *redirecting, const struct ast_set_party_redirecting *update)
Set the redirecting id information in the Asterisk channel.
Definition channel.c:9163
void ast_party_redirecting_set_init(struct ast_party_redirecting *init, const struct ast_party_redirecting *guide)
Initialize the given redirecting id structure using the given guide for a set update operation.
Definition channel.c:2139
void ast_channel_update_redirecting(struct ast_channel *chan, const struct ast_party_redirecting *redirecting, const struct ast_set_party_redirecting *update)
Indicate that the redirecting id has changed.
Definition channel.c:10328
void ast_party_redirecting_free(struct ast_party_redirecting *doomed)
Destroy the redirecting information contents.
Definition channel.c:2165
static const struct ast_app_option redirecting_opts[128]
#define LOG_WARNING
struct ast_party_name name
Subscriber name.
Definition channel.h:342
int presentation
Q.931 encoded presentation-indicator encoded field.
Definition channel.h:279
int presentation
Q.931 presentation-indicator and screening-indicator encoded fields.
Definition channel.h:297
int code
enum AST_REDIRECTING_REASON value for redirection
Definition channel.h:512
char * str
a string value for the redirecting reason
Definition channel.h:509
Indicate what information in ast_party_redirecting should be set.
Definition channel.h:557

References args, ARRAY_LEN, ast_app_parse_options(), ast_channel_lock, ast_channel_redirecting(), ast_channel_set_redirecting(), ast_channel_unlock, ast_channel_update_redirecting(), ast_log, AST_NONSTANDARD_APP_ARGS, ast_parse_caller_presentation(), ast_party_redirecting_free(), ast_party_redirecting_set_init(), ast_redirecting_reason_parse(), AST_REDIRECTING_REASON_UNKNOWN, ast_skip_blanks(), AST_STANDARD_APP_ARGS, ast_strdupa, ast_test_flag, ast_trim_blanks(), ast_party_redirecting_reason::code, ast_party_redirecting::count, ast_party_redirecting::from, ID_FIELD_INVALID, ID_FIELD_VALID, LOG_ERROR, LOG_WARNING, ast_party_id::name, NULL, ast_party_id::number, ast_party_redirecting::orig, ast_party_redirecting::orig_reason, party_id_write(), ast_party_name::presentation, ast_party_number::presentation, ast_party_redirecting::priv_from, ast_party_redirecting::priv_orig, ast_party_redirecting::priv_to, ast_party_redirecting::reason, REDIRECTING_OPT_ARG_ARRAY_SIZE, REDIRECTING_OPT_INHIBIT, redirecting_opts, status, ast_party_redirecting_reason::str, ast_party_redirecting::to, update(), and value.

◆ unload_module()

static int unload_module ( void  )
static

Definition at line 1832 of file func_callerid.c.

1833{
1837 return 0;
1838}
int ast_custom_function_unregister(struct ast_custom_function *acf)
Unregister a custom function.

References ast_custom_function_unregister(), callerid_function, connectedline_function, and redirecting_function.

Referenced by load_module().

Variable Documentation

◆ __mod_info

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_LOAD_ORDER , .description = "Party ID related dialplan functions (Caller-ID, Connected-line, Redirecting)" , .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 1864 of file func_callerid.c.

◆ ast_module_info

const struct ast_module_info* ast_module_info = &__mod_info
static

Definition at line 1864 of file func_callerid.c.

◆ callerid_function

struct ast_custom_function callerid_function
static

Definition at line 1806 of file func_callerid.c.

1806 {
1807 .name = "CALLERID",
1808 .read = callerid_read,
1809 .read_max = 256,
1810 .write = callerid_write,
1811};
static int callerid_write(struct ast_channel *chan, const char *cmd, char *data, const char *value)
static int callerid_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)

Referenced by load_module(), and unload_module().

◆ connectedline_function

struct ast_custom_function connectedline_function
static
Initial value:
= {
.name = "CONNECTEDLINE",
}
static int connectedline_write(struct ast_channel *chan, const char *cmd, char *data, const char *value)
static int connectedline_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)

Definition at line 1813 of file func_callerid.c.

1813 {
1814 .name = "CONNECTEDLINE",
1815 .read = connectedline_read,
1816 .write = connectedline_write,
1817};

Referenced by load_module(), and unload_module().

◆ connectedline_opts

const struct ast_app_option connectedline_opts[128] = { [ 'i' ] = { .flag = CONNECTED_LINE_OPT_INHIBIT }, }
static

Definition at line 492 of file func_callerid.c.

Referenced by connectedline_write().

◆ redirecting_function

struct ast_custom_function redirecting_function
static
Initial value:
= {
.name = "REDIRECTING",
}
static int redirecting_write(struct ast_channel *chan, const char *cmd, char *data, const char *value)
static int redirecting_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)

Definition at line 1819 of file func_callerid.c.

1819 {
1820 .name = "REDIRECTING",
1821 .read = redirecting_read,
1822 .write = redirecting_write,
1823};

Referenced by load_module(), and unload_module().

◆ redirecting_opts

const struct ast_app_option redirecting_opts[128] = { [ 'i' ] = { .flag = REDIRECTING_OPT_INHIBIT }, }
static

Definition at line 506 of file func_callerid.c.

Referenced by redirecting_write().