summaryrefslogtreecommitdiff
path: root/main
diff options
context:
space:
mode:
Diffstat (limited to 'main')
-rw-r--r--main/app.c26
-rw-r--r--main/asterisk.c1
-rw-r--r--main/astobj2.c13
-rw-r--r--main/channel.c10
-rw-r--r--main/format_compatibility.c4
-rw-r--r--main/frame.c69
-rw-r--r--main/libasteriskpj.c2
-rw-r--r--main/strings.c21
8 files changed, 97 insertions, 49 deletions
diff --git a/main/app.c b/main/app.c
index 58aa3a0fd..ee7cef26b 100644
--- a/main/app.c
+++ b/main/app.c
@@ -1422,22 +1422,20 @@ static struct ast_frame *make_silence(const struct ast_frame *orig)
size_t size;
size_t datalen;
size_t samples = 0;
- struct ast_frame *next;
if (!orig) {
return NULL;
}
+ do {
+ if (ast_format_cmp(orig->subclass.format, ast_format_slin) == AST_FORMAT_CMP_NOT_EQUAL) {
+ ast_log(LOG_WARNING, "Attempting to silence non-slin frame\n");
+ return NULL;
+ }
- if (ast_format_cmp(orig->subclass.format, ast_format_slin) == AST_FORMAT_CMP_NOT_EQUAL) {
- ast_log(LOG_WARNING, "Attempting to silence non-slin frame\n");
- return NULL;
- }
-
- for (next = AST_LIST_NEXT(orig, frame_list);
- orig;
- orig = next, next = orig ? AST_LIST_NEXT(orig, frame_list) : NULL) {
samples += orig->samples;
- }
+
+ orig = AST_LIST_NEXT(orig, frame_list);
+ } while (orig);
ast_verb(4, "Silencing %zu samples\n", samples);
@@ -1455,7 +1453,7 @@ static struct ast_frame *make_silence(const struct ast_frame *orig)
silence->samples = samples;
silence->datalen = datalen;
- silence->subclass.format = ast_format_slin;
+ silence->subclass.format = ao2_bump(ast_format_slin);
return silence;
}
@@ -1661,14 +1659,13 @@ static int __ast_play_and_record(struct ast_channel *chan, const char *playfile,
/* It's all good */
res = 0;
} else {
- RAII_VAR(struct ast_frame *, silence, NULL, ast_frame_dtor);
+ struct ast_frame *silence = NULL;
struct ast_frame *orig = f;
if (muted) {
silence = make_silence(orig);
if (!silence) {
- ast_log(LOG_WARNING,
- "Error creating silence\n");
+ ast_log(LOG_WARNING, "Error creating silence\n");
break;
}
f = silence;
@@ -1679,6 +1676,7 @@ static int __ast_play_and_record(struct ast_channel *chan, const char *playfile,
}
res = ast_writestream(others[x], f);
}
+ ast_frame_dtor(silence);
f = orig;
}
diff --git a/main/asterisk.c b/main/asterisk.c
index 2236e8c69..994dfbeb7 100644
--- a/main/asterisk.c
+++ b/main/asterisk.c
@@ -325,6 +325,7 @@ int ast_verb_sys_level;
int option_verbose; /*!< Verbosity level */
int option_debug; /*!< Debug level */
+int ast_pjproject_max_log_level = -1;/* Default to -1 to know if we have read the level from pjproject yet. */
int ast_option_pjproject_log_level;
double ast_option_maxload; /*!< Max load avg on system */
int ast_option_maxcalls; /*!< Max number of active calls */
diff --git a/main/astobj2.c b/main/astobj2.c
index 7320c5efb..569db0b7b 100644
--- a/main/astobj2.c
+++ b/main/astobj2.c
@@ -421,6 +421,19 @@ static int internal_ao2_ref(void *user_data, int delta, const char *file, int li
if (0 < current_value) {
/* The object still lives. */
+#define EXCESSIVE_REF_COUNT 100000
+
+ if (EXCESSIVE_REF_COUNT <= current_value && ret < EXCESSIVE_REF_COUNT) {
+ char excessive_ref_buf[100];
+
+ /* We just reached or went over the excessive ref count trigger */
+ snprintf(excessive_ref_buf, sizeof(excessive_ref_buf),
+ "Excessive refcount %d reached on ao2 object %p",
+ current_value, user_data);
+ ast_log(__LOG_ERROR, file, line, func, "%s\n", excessive_ref_buf);
+
+ __ast_assert_failed(0, excessive_ref_buf, file, line, func);
+ }
return ret;
}
diff --git a/main/channel.c b/main/channel.c
index 637488a9c..f305cc8bb 100644
--- a/main/channel.c
+++ b/main/channel.c
@@ -4889,16 +4889,18 @@ int ast_sendtext(struct ast_channel *chan, const char *text)
if (ast_channel_tech(chan)->write_text && (ast_format_cap_has_type(ast_channel_nativeformats(chan), AST_MEDIA_TYPE_TEXT))) {
struct ast_frame f;
+ memset(&f, 0, sizeof(f));
f.frametype = AST_FRAME_TEXT;
f.src = "DIALPLAN";
f.mallocd = AST_MALLOCD_DATA;
f.datalen = strlen(text);
f.data.ptr = ast_strdup(text);
- f.offset = 0;
- f.seqno = 0;
-
f.subclass.format = ast_format_t140;
- res = ast_channel_tech(chan)->write_text(chan, &f);
+
+ if (f.data.ptr) {
+ res = ast_channel_tech(chan)->write_text(chan, &f);
+ ast_frfree(&f);
+ }
} else if (ast_channel_tech(chan)->send_text) {
res = ast_channel_tech(chan)->send_text(chan, text);
}
diff --git a/main/format_compatibility.c b/main/format_compatibility.c
index cf66af282..0f1dff7c8 100644
--- a/main/format_compatibility.c
+++ b/main/format_compatibility.c
@@ -264,10 +264,10 @@ struct ast_format *ast_format_compatibility_bitfield2format(uint64_t bitfield)
/*! T.140 RED Text format RFC 4103 */
case AST_FORMAT_T140_RED:
- return ast_format_t140;
+ return ast_format_t140_red;
/*! T.140 Text format - ITU T.140, RFC 4103 */
case AST_FORMAT_T140:
- return ast_format_t140_red;
+ return ast_format_t140;
}
return NULL;
}
diff --git a/main/frame.c b/main/frame.c
index b5ab9853d..4261b04dd 100644
--- a/main/frame.c
+++ b/main/frame.c
@@ -84,9 +84,9 @@ static struct ast_frame *ast_frame_header_new(void)
if ((frames = ast_threadstorage_get(&frame_cache, sizeof(*frames)))) {
if ((f = AST_LIST_REMOVE_HEAD(&frames->list, frame_list))) {
size_t mallocd_len = f->mallocd_hdr_len;
+
memset(f, 0, sizeof(*f));
f->mallocd_hdr_len = mallocd_len;
- f->mallocd = AST_MALLOCD_HDR;
frames->size--;
return f;
}
@@ -141,12 +141,12 @@ static void __frame_free(struct ast_frame *fr, int cache)
#endif
if (fr->mallocd & AST_MALLOCD_DATA) {
- if (fr->data.ptr)
+ if (fr->data.ptr) {
ast_free(fr->data.ptr - fr->offset);
+ }
}
if (fr->mallocd & AST_MALLOCD_SRC) {
- if (fr->src)
- ast_free((void *) fr->src);
+ ast_free((void *) fr->src);
}
if (fr->mallocd & AST_MALLOCD_HDR) {
if ((fr->frametype == AST_FRAME_VOICE) || (fr->frametype == AST_FRAME_VIDEO) ||
@@ -208,14 +208,14 @@ struct ast_frame *ast_frisolate(struct ast_frame *fr)
return NULL;
}
out->frametype = fr->frametype;
+ out->subclass = fr->subclass;
if ((fr->frametype == AST_FRAME_VOICE) || (fr->frametype == AST_FRAME_VIDEO) ||
(fr->frametype == AST_FRAME_IMAGE)) {
- out->subclass.format = ao2_bump(fr->subclass.format);
- } else {
- memcpy(&out->subclass, &fr->subclass, sizeof(out->subclass));
+ ao2_bump(out->subclass.format);
}
out->datalen = fr->datalen;
out->samples = fr->samples;
+ out->mallocd = AST_MALLOCD_HDR;
out->offset = fr->offset;
/* Copy the timing data */
ast_copy_flags(out, fr, AST_FLAGS_ALL);
@@ -228,47 +228,64 @@ struct ast_frame *ast_frisolate(struct ast_frame *fr)
out = fr;
}
- if (!(fr->mallocd & AST_MALLOCD_SRC) && fr->src) {
- if (!(out->src = ast_strdup(fr->src))) {
- if (out != fr) {
- ast_free(out);
+ if (fr->src) {
+ /* The original frame has a source string */
+ if (!(fr->mallocd & AST_MALLOCD_SRC)) {
+ /*
+ * The original frame has a non-malloced source string.
+ *
+ * Duplicate the string and put it into the isolated frame
+ * which may also be the original frame.
+ */
+ newdata = ast_strdup(fr->src);
+ if (!newdata) {
+ if (out != fr) {
+ ast_frame_free(out, 0);
+ }
+ return NULL;
}
- return NULL;
+ out->src = newdata;
+ out->mallocd |= AST_MALLOCD_SRC;
+ } else if (out != fr) {
+ /* Steal the source string from the original frame. */
+ out->src = fr->src;
+ fr->src = NULL;
+ fr->mallocd &= ~AST_MALLOCD_SRC;
+ out->mallocd |= AST_MALLOCD_SRC;
}
- } else {
- out->src = fr->src;
- fr->src = NULL;
- fr->mallocd &= ~AST_MALLOCD_SRC;
}
if (!(fr->mallocd & AST_MALLOCD_DATA)) {
+ /* The original frame has a non-malloced data buffer. */
if (!fr->datalen) {
+ /* Actually it's just an int so we can simply copy it. */
out->data.uint32 = fr->data.uint32;
- out->mallocd = AST_MALLOCD_HDR | AST_MALLOCD_SRC;
return out;
}
- if (!(newdata = ast_malloc(fr->datalen + AST_FRIENDLY_OFFSET))) {
- if (out->src != fr->src) {
- ast_free((void *) out->src);
- }
+ /*
+ * Duplicate the data buffer and put it into the isolated frame
+ * which may also be the original frame.
+ */
+ newdata = ast_malloc(fr->datalen + AST_FRIENDLY_OFFSET);
+ if (!newdata) {
if (out != fr) {
- ast_free(out);
+ ast_frame_free(out, 0);
}
return NULL;
}
newdata += AST_FRIENDLY_OFFSET;
out->offset = AST_FRIENDLY_OFFSET;
- out->datalen = fr->datalen;
memcpy(newdata, fr->data.ptr, fr->datalen);
out->data.ptr = newdata;
- } else {
+ out->mallocd |= AST_MALLOCD_DATA;
+ } else if (out != fr) {
+ /* Steal the data buffer from the original frame. */
out->data = fr->data;
memset(&fr->data, 0, sizeof(fr->data));
fr->mallocd &= ~AST_MALLOCD_DATA;
+ out->mallocd |= AST_MALLOCD_DATA;
}
- out->mallocd = AST_MALLOCD_HDR | AST_MALLOCD_SRC | AST_MALLOCD_DATA;
-
return out;
}
diff --git a/main/libasteriskpj.c b/main/libasteriskpj.c
index 2d92b599d..80c4d1896 100644
--- a/main/libasteriskpj.c
+++ b/main/libasteriskpj.c
@@ -47,7 +47,7 @@ ASTERISK_REGISTER_FILE()
int ast_pj_init(void)
{
#ifdef HAVE_PJPROJECT_BUNDLED
- pj_log_set_level(ast_option_pjproject_log_level);
+ AST_PJPROJECT_INIT_LOG_LEVEL();
pj_init();
#endif
return 0;
diff --git a/main/strings.c b/main/strings.c
index 7cb55def0..7f2025abe 100644
--- a/main/strings.c
+++ b/main/strings.c
@@ -186,15 +186,32 @@ static int str_hash(const void *obj, const int flags)
return ast_str_hash(obj);
}
+static int str_sort(const void *lhs, const void *rhs, int flags)
+{
+ if ((flags & OBJ_SEARCH_MASK) == OBJ_SEARCH_PARTIAL_KEY) {
+ return strncmp(lhs, rhs, strlen(rhs));
+ } else {
+ return strcmp(lhs, rhs);
+ }
+}
+
static int str_cmp(void *lhs, void *rhs, int flags)
{
- return strcmp(lhs, rhs) ? 0 : CMP_MATCH;
+ int cmp = 0;
+
+ if ((flags & OBJ_SEARCH_MASK) == OBJ_SEARCH_PARTIAL_KEY) {
+ cmp = strncmp(lhs, rhs, strlen(rhs));
+ } else {
+ cmp = strcmp(lhs, rhs);
+ }
+
+ return cmp ? 0 : CMP_MATCH;
}
//struct ao2_container *ast_str_container_alloc_options(enum ao2_container_opts opts, int buckets)
struct ao2_container *ast_str_container_alloc_options(enum ao2_alloc_opts opts, int buckets)
{
- return ao2_container_alloc_options(opts, buckets, str_hash, str_cmp);
+ return ao2_container_alloc_hash(opts, 0, buckets, str_hash, str_sort, str_cmp);
}
int ast_str_container_add(struct ao2_container *str_container, const char *add)