MT#55283 allow list iteration to return errors

Change-Id: Ic394f0fa4af09f2db6526f49d4e5e3fd4fdb04c5
pull/2097/head
Richard Fuchs 2 weeks ago
parent f7b5a4de5b
commit b91f58292f

@ -18,7 +18,7 @@ static void call_ng_flags_str_list(const ng_parser_t *, parser_arg list,
void (*callback)(str *, unsigned int, helper_arg), helper_arg);
static void call_ng_flags_list(const ng_parser_t *, parser_arg list,
void (*str_callback)(str *, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
const char *(*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
helper_arg);
static void call_ng_flags_esc_str_list(str *s, unsigned int, helper_arg);
@ -149,7 +149,7 @@ static void call_ng_flags_item_pair_ht_iter(str *key, unsigned int idx, helper_a
from_to[1] = *key;
}
static void call_ng_flags_item_pair_ht(const ng_parser_t *parser, parser_arg it, helper_arg arg) {
static const char *call_ng_flags_item_pair_ht(const ng_parser_t *parser, parser_arg it, helper_arg arg) {
str from_to[2] = {0};
if (!parser->is_list(it))
@ -166,10 +166,11 @@ static void call_ng_flags_item_pair_ht(const ng_parser_t *parser, parser_arg it,
*ht = str_case_value_ht_new();
t_hash_table_replace(*ht, s_copy_from, s_copy_to);
return;
return NULL;
err:
ilog(LOG_WARN, "SDP manipulations: Ignoring invalid contents of string-pair list");
return NULL;
}
/**
@ -338,7 +339,7 @@ INLINE void ng_t38_option(str *s, unsigned int idx, helper_arg arg) {
static void call_ng_flags_list(const ng_parser_t *parser, parser_arg list,
void (*str_callback)(str *, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
const char *(*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
helper_arg arg)
{
str s;
@ -1154,8 +1155,9 @@ static void call_ng_parse_block_mode(str *s, enum block_dtmf_mode *output) {
#endif
static void call_ng_flags_freqs(const ng_parser_t *parser, parser_arg value, sdp_ng_flags *out);
static void call_ng_flags_freqs_iter(const ng_parser_t *parser, parser_arg item, helper_arg arg) {
static const char *call_ng_flags_freqs_iter(const ng_parser_t *parser, parser_arg item, helper_arg arg) {
call_ng_flags_freqs(parser, item, arg.flags);
return NULL;
}
static void call_ng_flags_freqs(const ng_parser_t *parser, parser_arg value, sdp_ng_flags *out) {
unsigned int val;
@ -1243,7 +1245,7 @@ static void call_ng_codec(const ng_parser_t *parser, str *key, parser_arg value,
}
}
static void call_ng_codec_iter(const ng_parser_t *parser, parser_arg item, struct ng_media *media) {
static const char *call_ng_codec_iter(const ng_parser_t *parser, parser_arg item, struct ng_media *media) {
// we support two types here:
// the "transform" method supplies an extended list of codecs, as a list of dicts
// the "create" method uses a list of strings, similar to codec->offer
@ -1251,7 +1253,7 @@ static void call_ng_codec_iter(const ng_parser_t *parser, parser_arg item, struc
str s;
parser->get_str(item, &s);
call_ng_flags_esc_str_list(&s, 0, &media->codec_list);
return;
return NULL;
}
__auto_type codec = g_new0(struct ng_codec, 1);
@ -1264,6 +1266,8 @@ static void call_ng_codec_iter(const ng_parser_t *parser, parser_arg item, struc
if (codec->input.payload_type == -1 || codec->output.payload_type == -1)
ilog(LOG_WARN, "Incomplete codec definition");
return NULL;
}
static void call_ng_endpoint(const ng_parser_t *parser, str *key, parser_arg value, struct ng_media *media) {
@ -1315,10 +1319,11 @@ static void call_ng_media(const ng_parser_t *parser, str *key, parser_arg value,
}
}
static void call_ng_media_iter(const ng_parser_t *parser, parser_arg item, sdp_ng_flags *out) {
static const char *call_ng_media_iter(const ng_parser_t *parser, parser_arg item, sdp_ng_flags *out) {
__auto_type media = g_new0(struct ng_media, 1);
t_queue_push_tail(&out->medias, media);
parser->dict_iter(parser, item, call_ng_media, media);
return NULL;
}
void call_ng_main_flags(const ng_parser_t *parser, str *key, parser_arg value, helper_arg arg) {

@ -123,24 +123,28 @@ static bool bencode_is_list(bencode_item_t *arg) {
static bool bencode_is_int(bencode_item_t *arg) {
return arg->type == BENCODE_INTEGER;
}
static void bencode_list_iter(const ng_parser_t *parser, bencode_item_t *list,
static const char *bencode_list_iter(const ng_parser_t *parser, bencode_item_t *list,
void (*str_callback)(str *key, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *, bencode_item_t *, helper_arg),
const char *(*item_callback)(const ng_parser_t *, bencode_item_t *, helper_arg),
helper_arg arg)
{
if (list->type != BENCODE_LIST)
return;
return NULL; // return error?
str s;
unsigned int idx = 0;
for (bencode_item_t *it = list->child; it; it = it->sibling) {
if (bencode_get_str(it, &s) && str_callback)
str_callback(&s, idx, arg);
else if (item_callback)
item_callback(parser, it, arg);
else if (item_callback) {
const char *err = item_callback(parser, it, arg);
if (err)
return err;
}
else
ilog(LOG_DEBUG, "Ignoring non-string value in list");
idx++;
}
return NULL;
}
static long long bencode_get_int(bencode_item_t *arg) {
return arg->value;
@ -331,17 +335,17 @@ static bool json_dict_iter(const ng_parser_t *parser, JsonNode *input,
return true;
}
static void json_list_iter(const ng_parser_t *parser, JsonNode *list,
static const char *json_list_iter(const ng_parser_t *parser, JsonNode *list,
void (*str_callback)(str *key, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *parser, JsonNode *, helper_arg),
const char *(*item_callback)(const ng_parser_t *parser, JsonNode *, helper_arg),
helper_arg arg)
{
if (json_node_get_node_type(list) != JSON_NODE_ARRAY)
return;
return NULL; // return error?
JsonArray *a = json_node_get_array(list);
if (!a)
return;
return NULL; // return error?
unsigned int l = json_array_get_length(a);
for (unsigned int i = 0; i < l; i++) {
@ -353,9 +357,14 @@ static void json_list_iter(const ng_parser_t *parser, JsonNode *list,
if (s)
str_callback(STR_PTR(s), i, arg);
}
else
item_callback(parser, n, arg);
else {
const char *err = item_callback(parser, n, arg);
if (err)
return err;
}
}
return NULL;
}
static str *json_get_str(JsonNode *a, str *out) {
const char *s = json_node_get_string(a);

@ -147,13 +147,13 @@ static bool rtpp_dict_list_closing(rtpp_pos *pos) {
return true;
}
static void rtpp_list_iter(const ng_parser_t *parser, rtpp_pos *pos,
static const char *rtpp_list_iter(const ng_parser_t *parser, rtpp_pos *pos,
void (*str_callback)(str *key, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *, parser_arg, helper_arg), helper_arg arg)
const char *(*item_callback)(const ng_parser_t *, parser_arg, helper_arg), helper_arg arg)
{
// list opener
if (!skip_char(&pos->cur, '['))
return;
return NULL; // return error here?
unsigned int idx = 0;
@ -168,8 +168,11 @@ static void rtpp_list_iter(const ng_parser_t *parser, rtpp_pos *pos,
// does it start another list or dict?
if (pos->cur.s[0] == '[') {
if (item_callback)
item_callback(parser, pos, arg);
if (item_callback) {
const char *err = item_callback(parser, pos, arg);
if (err)
return err;
}
goto next;
}
@ -182,8 +185,11 @@ static void rtpp_list_iter(const ng_parser_t *parser, rtpp_pos *pos,
if (str_callback)
str_callback(&pos->cur, idx++, arg);
else if (item_callback)
item_callback(parser, pos, arg);
else if (item_callback) {
const char *err = item_callback(parser, pos, arg);
if (err)
return err;
}
if (end)
break;
goto next;
@ -193,7 +199,10 @@ next:
if (!str_token_sep(&pos->cur, &pos->remainder, ' '))
break;
}
return NULL;
}
static bool rtpp_dict_iter(const ng_parser_t *parser, rtpp_pos *pos,
void (*callback)(const ng_parser_t *, str *, parser_arg, helper_arg),
helper_arg arg)

@ -2034,7 +2034,7 @@ static int json_link_maps(call_t *c, struct redis_list *maps,
return 0;
}
static void json_build_ssrc_iter(const ng_parser_t *parser, parser_arg dict, helper_arg arg) {
static const char *json_build_ssrc_iter(const ng_parser_t *parser, parser_arg dict, helper_arg arg) {
struct call_media *md = arg.md;
uint32_t ssrc = parser_get_ll(dict, "ssrc");
@ -2053,6 +2053,8 @@ static void json_build_ssrc_iter(const ng_parser_t *parser, parser_arg dict, hel
payload_tracker_add(&se_out->tracker, parser_get_ll(dict, "out_payload_type"));
obj_put(&se_out->h);
}
return NULL;
}
static int json_build_ssrc(struct call_media *md, parser_arg arg) {

@ -104,9 +104,9 @@ struct ng_parser {
void (*callback)(const ng_parser_t *, str *, parser_arg, helper_arg),
helper_arg);
bool (*is_list)(parser_arg);
void (*list_iter)(const ng_parser_t *, parser_arg input,
const char *(*list_iter)(const ng_parser_t *, parser_arg input,
void (*str_callback)(str *key, unsigned int, helper_arg),
void (*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
const char *(*item_callback)(const ng_parser_t *, parser_arg, helper_arg),
helper_arg);
str *(*get_str)(parser_arg, str *s);
int (*strcmp)(parser_arg, const char *);

Loading…
Cancel
Save