Asterisk - The Open Source Telephony Project GIT-master-a358458
Data Structures | Macros | Enumerations | Functions | Variables
file.c File Reference

Generic File Format Support. More...

#include "asterisk.h"
#include <dirent.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <math.h>
#include "asterisk/_private.h"
#include "asterisk/paths.h"
#include "asterisk/mod_format.h"
#include "asterisk/cli.h"
#include "asterisk/channel.h"
#include "asterisk/sched.h"
#include "asterisk/translate.h"
#include "asterisk/utils.h"
#include "asterisk/lock.h"
#include "asterisk/app.h"
#include "asterisk/pbx.h"
#include "asterisk/linkedlists.h"
#include "asterisk/module.h"
#include "asterisk/astobj2.h"
#include "asterisk/test.h"
#include "asterisk/stasis.h"
#include "asterisk/json.h"
#include "asterisk/stasis_system.h"
#include "asterisk/media_cache.h"
Include dependency graph for file.c:

Go to the source code of this file.

Data Structures

struct  formats
 

Macros

#define exts_compare(list, type)   (type_in_list((list), (type), strcmp))
 
#define FORMAT   "%-10s %-10s %-20s\n"
 
#define FORMAT2   "%-10s %-10s %-20s\n"
 

Enumerations

enum  file_action {
  ACTION_EXISTS = 1 , ACTION_DELETE , ACTION_RENAME , ACTION_OPEN ,
  ACTION_COPY
}
 
enum  fsread_res { FSREAD_FAILURE , FSREAD_SUCCESS_SCHED , FSREAD_SUCCESS_NOSCHED }
 
enum  wrap_fn { WRAP_OPEN , WRAP_REWRITE }
 

Functions

static int __ast_file_read_dirs (const char *path, ast_file_on_file on_file, void *obj, int max_depth)
 
int __ast_format_def_register (const struct ast_format_def *f, struct ast_module *mod)
 Register a new file format capability. Adds a format to Asterisk's format abilities. More...
 
int ast_applystream (struct ast_channel *chan, struct ast_filestream *s)
 Applies a open stream to a channel. More...
 
int ast_closestream (struct ast_filestream *f)
 Closes a stream. More...
 
int ast_file_fdtemp (const char *path, char **filename, const char *template_name)
 Create a temporary file located at path. More...
 
int ast_file_init (void)
 
FILE * ast_file_mkftemp (char *template, mode_t mode)
 same as mkstemp, but return a FILE More...
 
int ast_file_read_dirs (const char *dir_name, ast_file_on_file on_file, void *obj, int max_depth)
 Recursively iterate through files and directories up to max_depth. More...
 
int ast_filecopy (const char *filename, const char *filename2, const char *fmt)
 Copies a file. More...
 
int ast_filedelete (const char *filename, const char *fmt)
 Deletes a file. More...
 
int ast_fileexists (const char *filename, const char *fmt, const char *preflang)
 Checks for the existence of a given file. More...
 
int ast_filerename (const char *filename, const char *filename2, const char *fmt)
 Renames a file. More...
 
int ast_format_def_unregister (const char *name)
 Unregisters a file format. More...
 
char * ast_format_str_reduce (char *fmts)
 
static int ast_fsread_audio (const void *data)
 
static int ast_fsread_video (const void *data)
 
int ast_get_extension_for_mime_type (const char *mime_type, char *buffer, size_t capacity)
 Get a suitable filename extension for the given MIME type. More...
 
struct ast_formatast_get_format_for_file_ext (const char *file_ext)
 Get the ast_format associated with the given file extension. More...
 
struct ast_filestreamast_openstream (struct ast_channel *chan, const char *filename, const char *preflang)
 Opens stream for use in seeking, playing. More...
 
struct ast_filestreamast_openstream_full (struct ast_channel *chan, const char *filename, const char *preflang, int asis)
 Opens stream for use in seeking, playing. More...
 
struct ast_filestreamast_openvstream (struct ast_channel *chan, const char *filename, const char *preflang)
 Opens stream for use in seeking, playing. More...
 
int ast_playstream (struct ast_filestream *s)
 Play a open stream on a channel. More...
 
int ast_ratestream (struct ast_filestream *fs)
 Return the sample rate of the stream's format. More...
 
static enum fsread_res ast_readaudio_callback (struct ast_filestream *s)
 
struct ast_filestreamast_readfile (const char *filename, const char *type, const char *comment, int flags, int check, mode_t mode)
 Starts reading from a file. More...
 
struct ast_frameast_readframe (struct ast_filestream *s)
 Read a frame from a filestream. More...
 
static enum fsread_res ast_readvideo_callback (struct ast_filestream *s)
 
int ast_seekstream (struct ast_filestream *fs, off_t sample_offset, int whence)
 Seeks into stream. More...
 
int ast_stopstream (struct ast_channel *tmp)
 Stops a stream. More...
 
int ast_stream_and_wait (struct ast_channel *chan, const char *file, const char *digits)
 stream file until digit If the file name is non-empty, try to play it. More...
 
int ast_stream_fastforward (struct ast_filestream *fs, off_t ms)
 Fast forward stream ms. More...
 
int ast_stream_rewind (struct ast_filestream *fs, off_t ms)
 Rewind stream ms. More...
 
int ast_streamfile (struct ast_channel *chan, const char *filename, const char *preflang)
 Streams a file. More...
 
off_t ast_tellstream (struct ast_filestream *fs)
 Tell where we are in a stream. More...
 
int ast_truncstream (struct ast_filestream *fs)
 Trunc stream at current location. More...
 
int ast_waitstream (struct ast_channel *c, const char *breakon)
 Waits for a stream to stop or digit to be pressed. More...
 
int ast_waitstream_exten (struct ast_channel *c, const char *context)
 Waits for a stream to stop or digit matching a valid one digit exten to be pressed. More...
 
int ast_waitstream_fr (struct ast_channel *c, const char *breakon, const char *forward, const char *reverse, int ms)
 Same as waitstream but allows stream to be forwarded or rewound. More...
 
int ast_waitstream_fr_w_cb (struct ast_channel *c, const char *breakon, const char *forward, const char *reverse, int ms, ast_waitstream_fr_cb cb)
 Same as waitstream_fr but allows a callback to be alerted when a user fastforwards or rewinds the file. More...
 
int ast_waitstream_full (struct ast_channel *c, const char *breakon, int audiofd, int cmdfd)
 
struct ast_filestreamast_writefile (const char *filename, const char *type, const char *comment, int flags, int check, mode_t mode)
 Starts writing a file. More...
 
int ast_writestream (struct ast_filestream *fs, struct ast_frame *f)
 Writes a frame to a stream. More...
 
static char * build_filename (const char *filename, const char *ext)
 construct a filename. Absolute pathnames are preserved, relative names are prefixed by the sounds/ directory. The wav49 suffix is replaced by 'WAV'. Returns a malloc'ed string to be freed by the caller. More...
 
static int copy (const char *infile, const char *outfile)
 
static void file_shutdown (void)
 
static int fileexists_core (const char *filename, const char *fmt, const char *preflang, char *buf, int buflen, struct ast_format_cap *result_cap)
 helper routine to locate a file with a given format and language preference. More...
 
static int fileexists_test (const char *filename, const char *fmt, const char *lang, char *buf, int buflen, struct ast_format_cap *result_cap)
 test if a file exists for a given format. More...
 
static int filehelper (const char *filename, const void *arg2, const char *fmt, const enum file_action action)
 
static void filestream_close (struct ast_filestream *f)
 
static void filestream_destructor (void *arg)
 
static int fn_wrapper (struct ast_filestream *s, const char *comment, enum wrap_fn mode)
 
static struct ast_filestreamget_filestream (struct ast_format_def *fmt, FILE *bfile)
 
static char * handle_cli_core_show_file_formats (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
 
static int is_absolute_path (const char *filename)
 
static int is_remote_path (const char *filename)
 
static struct ast_jsonjson_array_from_list (const char *list, const char *sep)
 
static int open_wrapper (struct ast_filestream *s)
 
static int publish_format_update (const struct ast_format_def *f, struct stasis_message_type *type)
 
static struct ast_frameread_frame (struct ast_filestream *s, int *whennext)
 
static int rewrite_wrapper (struct ast_filestream *s, const char *comment)
 
static int sanitize_waitstream_return (int return_value)
 
 STASIS_MESSAGE_TYPE_DEFN (ast_format_register_type)
 
 STASIS_MESSAGE_TYPE_DEFN (ast_format_unregister_type)
 
static int type_in_list (const char *list, const char *type, int(*cmp)(const char *s1, const char *s2))
 
static void waitstream_control (struct ast_channel *c, enum ast_waitstream_fr_cb_values type, ast_waitstream_fr_cb cb, int skip_ms)
 
static int waitstream_core (struct ast_channel *c, const char *breakon, const char *forward, const char *reverse, int skip_ms, int audiofd, int cmdfd, const char *context, ast_waitstream_fr_cb cb)
 the core of all waitstream() functions More...
 

Variables

int ast_language_is_prefix = 1
 The following variable controls the layout of localized sound files. If 0, use the historical layout with prefix just before the filename (i.e. digits/en/1.gsm , digits/it/1.gsm or default to digits/1.gsm), if 1 put the prefix at the beginning of the filename (i.e. en/digits/1.gsm, it/digits/1.gsm or default to digits/1.gsm). The latter permits a language to be entirely in one directory. More...
 
static struct ast_cli_entry cli_file []
 
static struct formats formats = { .first = NULL, .last = NULL, .lock = { PTHREAD_RWLOCK_INITIALIZER , NULL, {1, 0} } , }
 
static ast_mutex_t read_dirs_lock = { PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP , NULL, {1, 0} }
 Lock to hold when iterating over directories. More...
 

Detailed Description

Generic File Format Support.

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

Definition in file file.c.

Macro Definition Documentation

◆ exts_compare

#define exts_compare (   list,
  type 
)    (type_in_list((list), (type), strcmp))

Definition at line 386 of file file.c.

◆ FORMAT

#define FORMAT   "%-10s %-10s %-20s\n"

◆ FORMAT2

#define FORMAT2   "%-10s %-10s %-20s\n"

Enumeration Type Documentation

◆ file_action

Enumerator
ACTION_EXISTS 
ACTION_DELETE 
ACTION_RENAME 
ACTION_OPEN 
ACTION_COPY 

Definition at line 530 of file file.c.

530 {
531 ACTION_EXISTS = 1, /* return matching format if file exists, 0 otherwise */
532 ACTION_DELETE, /* delete file, return 0 on success, -1 on error */
533 ACTION_RENAME, /* rename file. return 0 on success, -1 on error */
535 ACTION_COPY /* copy file. return 0 on success, -1 on error */
536};
@ ACTION_OPEN
Definition: file.c:534
@ ACTION_EXISTS
Definition: file.c:531
@ ACTION_COPY
Definition: file.c:535
@ ACTION_DELETE
Definition: file.c:532
@ ACTION_RENAME
Definition: file.c:533

◆ fsread_res

enum fsread_res
Enumerator
FSREAD_FAILURE 
FSREAD_SUCCESS_SCHED 
FSREAD_SUCCESS_NOSCHED 

Definition at line 943 of file file.c.

943 {
947};
@ FSREAD_FAILURE
Definition: file.c:944
@ FSREAD_SUCCESS_SCHED
Definition: file.c:945
@ FSREAD_SUCCESS_NOSCHED
Definition: file.c:946

◆ wrap_fn

enum wrap_fn
Enumerator
WRAP_OPEN 
WRAP_REWRITE 

Definition at line 501 of file file.c.

@ WRAP_OPEN
Definition: file.c:501
@ WRAP_REWRITE
Definition: file.c:501

Function Documentation

◆ __ast_file_read_dirs()

static int __ast_file_read_dirs ( const char *  path,
ast_file_on_file  on_file,
void *  obj,
int  max_depth 
)
static

Definition at line 1156 of file file.c.

1158{
1159 DIR *dir;
1160 struct dirent *entry;
1161 int res;
1162
1163 if (!(dir = opendir(path))) {
1164 ast_log(LOG_ERROR, "Error opening directory - %s: %s\n",
1165 path, strerror(errno));
1166 return -1;
1167 }
1168
1169 --max_depth;
1170
1171 res = 0;
1172
1173 while ((entry = readdir(dir)) != NULL && !errno) {
1174 int is_file = 0;
1175 int is_dir = 0;
1176 RAII_VAR(char *, full_path, NULL, ast_free);
1177
1178 if (!strcmp(entry->d_name, ".") || !strcmp(entry->d_name, "..")) {
1179 continue;
1180 }
1181
1182/*
1183 * If the dirent structure has a d_type use it to determine if we are dealing with
1184 * a file or directory. Unfortunately if it doesn't have it, or if the type is
1185 * unknown, or a link then we'll need to use the stat function instead.
1186 */
1187#ifdef _DIRENT_HAVE_D_TYPE
1188 if (entry->d_type != DT_UNKNOWN && entry->d_type != DT_LNK) {
1189 is_file = entry->d_type == DT_REG;
1190 is_dir = entry->d_type == DT_DIR;
1191 } else
1192#endif
1193 {
1194 struct stat statbuf;
1195
1196 /*
1197 * Don't use alloca or we risk blowing out the stack if recursing
1198 * into subdirectories.
1199 */
1200 full_path = ast_malloc(strlen(path) + strlen(entry->d_name) + 2);
1201 if (!full_path) {
1202 return -1;
1203 }
1204 sprintf(full_path, "%s/%s", path, entry->d_name);
1205
1206 if (stat(full_path, &statbuf)) {
1207 ast_log(LOG_ERROR, "Error reading path stats - %s: %s\n",
1208 full_path, strerror(errno));
1209 /*
1210 * Output an error, but keep going. It could just be
1211 * a broken link and other files could be fine.
1212 */
1213 continue;
1214 }
1215
1216 is_file = S_ISREG(statbuf.st_mode);
1217 is_dir = S_ISDIR(statbuf.st_mode);
1218 }
1219
1220 if (is_file) {
1221 /* If the handler returns non-zero then stop */
1222 if ((res = on_file(path, entry->d_name, obj))) {
1223 break;
1224 }
1225 /* Otherwise move on to next item in directory */
1226 continue;
1227 }
1228
1229 if (!is_dir) {
1230 ast_debug(5, "Skipping %s: not a regular file or directory\n", full_path);
1231 continue;
1232 }
1233
1234 /* Only re-curse into sub-directories if not at the max depth */
1235 if (max_depth != 0) {
1236 if (!full_path) {
1237 /* Don't use alloca. See note above. */
1238 full_path = ast_malloc(strlen(path) + strlen(entry->d_name) + 2);
1239 if (!full_path) {
1240 return -1;
1241 }
1242 sprintf(full_path, "%s/%s", path, entry->d_name);
1243 }
1244
1245 if ((res = __ast_file_read_dirs(full_path, on_file, obj, max_depth))) {
1246 break;
1247 }
1248 }
1249 }
1250
1251 closedir(dir);
1252
1253 if (!res && errno) {
1254 ast_log(LOG_ERROR, "Error while reading directories - %s: %s\n",
1255 path, strerror(errno));
1256 res = -1;
1257 }
1258
1259 return res;
1260}
#define ast_free(a)
Definition: astmm.h:180
#define ast_malloc(len)
A wrapper for malloc()
Definition: astmm.h:191
#define ast_log
Definition: astobj2.c:42
static int __ast_file_read_dirs(const char *path, ast_file_on_file on_file, void *obj, int max_depth)
Definition: file.c:1156
#define ast_debug(level,...)
Log a DEBUG message.
#define LOG_ERROR
int errno
#define NULL
Definition: resample.c:96
Definition: search.h:40
#define RAII_VAR(vartype, varname, initval, dtor)
Declare a variable that will call a destructor function when it goes out of scope.
Definition: utils.h:941

References __ast_file_read_dirs(), ast_debug, ast_free, ast_log, ast_malloc, errno, LOG_ERROR, NULL, and RAII_VAR.

Referenced by __ast_file_read_dirs(), and ast_file_read_dirs().

◆ __ast_format_def_register()

int __ast_format_def_register ( const struct ast_format_def f,
struct ast_module mod 
)

Register a new file format capability. Adds a format to Asterisk's format abilities.

Return values
0on success
-1on failure

Definition at line 124 of file file.c.

125{
126 struct ast_format_def *tmp;
127
130 if (!strcasecmp(f->name, tmp->name)) {
132 ast_log(LOG_WARNING, "Tried to register '%s' format, already registered\n", f->name);
133 return -1;
134 }
135 }
136 if (!(tmp = ast_calloc(1, sizeof(*tmp)))) {
138 return -1;
139 }
140 *tmp = *f;
141 tmp->module = mod;
142 if (tmp->buf_size) {
143 /*
144 * Align buf_size properly, rounding up to the machine-specific
145 * alignment for pointers.
146 */
147 struct _test_align { void *a, *b; } p;
148 int align = (char *)&p.b - (char *)&p.a;
149 tmp->buf_size = ((f->buf_size + align - 1) / align) * align;
150 }
151
152 memset(&tmp->list, 0, sizeof(tmp->list));
153
156 ast_verb(5, "Registered file format %s, extension(s) %s\n", f->name, f->exts);
158
159 return 0;
160}
#define ast_calloc(num, len)
A wrapper for calloc()
Definition: astmm.h:202
static int tmp()
Definition: bt_open.c:389
static int publish_format_update(const struct ast_format_def *f, struct stasis_message_type *type)
Definition: file.c:93
struct stasis_message_type * ast_format_register_type(void)
Get the message type used for signaling a format registration.
#define ast_verb(level,...)
#define LOG_WARNING
#define AST_RWLIST_WRLOCK(head)
Write locks a list.
Definition: linkedlists.h:52
#define AST_RWLIST_UNLOCK(head)
Attempts to unlock a read/write based list.
Definition: linkedlists.h:151
#define AST_RWLIST_TRAVERSE
Definition: linkedlists.h:494
#define AST_RWLIST_INSERT_HEAD
Definition: linkedlists.h:718
Each supported file format is described by the following structure.
Definition: mod_format.h:43
char name[80]
Definition: mod_format.h:44
struct ast_format_def::@239 list
char exts[80]
Definition: mod_format.h:45
Definition: file.c:69
static struct test_val b
static struct test_val a

References a, ast_calloc, ast_format_register_type(), ast_log, AST_RWLIST_INSERT_HEAD, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_verb, b, ast_format_def::buf_size, ast_format_def::exts, ast_format_def::list, LOG_WARNING, ast_format_def::name, publish_format_update(), and tmp().

◆ ast_applystream()

int ast_applystream ( struct ast_channel chan,
struct ast_filestream s 
)

Applies a open stream to a channel.

Parameters
chanchannel to work
sast_filestream to apply
Return values
0on success.
-1on failure.

Definition at line 1057 of file file.c.

1058{
1059 s->owner = chan;
1060 return 0;
1061}
struct ast_channel * owner
Definition: mod_format.h:116

References ast_filestream::owner.

Referenced by ast_streamfile(), handle_getoption(), handle_recordfile(), handle_streamfile(), and speech_streamfile().

◆ ast_closestream()

int ast_closestream ( struct ast_filestream f)

Closes a stream.

Parameters
ffilestream to close Close a playback or recording stream
Return values
0on success.
-1on failure.

Definition at line 1111 of file file.c.

1112{
1113 /* This used to destroy the filestream, but it now just decrements a refcount.
1114 * We close the stream in order to quit queuing frames now, because we might
1115 * change the writeformat, which could result in a subsequent write error, if
1116 * the format is different. */
1117 if (f == NULL) {
1118 return 0;
1119 }
1121 ao2_ref(f, -1);
1122 return 0;
1123}
#define ao2_ref(o, delta)
Reference/unreference an object and return the old refcount.
Definition: astobj2.h:459
static void filestream_close(struct ast_filestream *f)
Definition: file.c:392

References ao2_ref, ast_filestream::f, filestream_close(), and NULL.

Referenced by __ast_play_and_record(), ast_hangup(), ast_moh_files_next(), ast_readfile(), ast_stopstream(), ast_writefile(), dictate_exec(), filehelper(), filestream_destructor(), gen_closestream(), handle_cli_file_convert(), handle_recordfile(), local_ast_moh_stop(), mixmonitor_ds_close_fs(), moh_files_release(), msg_create_from_file(), record_exec(), and recordthread().

◆ ast_file_fdtemp()

int ast_file_fdtemp ( const char *  path,
char **  filename,
const char *  template_name 
)

Create a temporary file located at path.

Note
The directory containing path will be created if it does not exist
This function assumes path does not end with a '/'
Parameters
pathThe directory path to create the file in
filenameFunction allocates memory and stores full filename (including path) here
template_namemkstemp template to use. Must end with XXXXXX.
Note
filename will need to be freed with ast_free if this function succeeds
Return values
-1on failure
Returns
file descriptor on success

Definition at line 202 of file file.c.

203{
204 int fd;
205
206 if (ast_asprintf(filename, "%s/%s", path, template_name) < 0) {
207 ast_log(LOG_ERROR, "Failed to set up temporary file path\n");
208 return -1;
209 }
210
211 ast_mkdir(path, 0644);
212
213 if ((fd = mkstemp(*filename)) < 0) {
214 ast_log(LOG_NOTICE, "Failed to create temporary file\n");
215 ast_free(*filename);
216 return -1;
217 }
218
219 return fd;
220}
#define ast_asprintf(ret, fmt,...)
A wrapper for asprintf()
Definition: astmm.h:267
#define LOG_NOTICE
int ast_mkdir(const char *path, int mode)
Recursively create directory path.
Definition: utils.c:2479

References ast_asprintf, ast_free, ast_log, ast_mkdir(), LOG_ERROR, and LOG_NOTICE.

◆ ast_file_init()

int ast_file_init ( void  )

Provided by file.c

Definition at line 2051 of file file.c.

2052{
2057 return 0;
2058}
int ast_register_cleanup(void(*func)(void))
Register a function to be executed before Asterisk gracefully exits.
Definition: clicompat.c:19
#define ast_cli_register_multiple(e, len)
Register multiple commands.
Definition: cli.h:265
static void file_shutdown(void)
Definition: file.c:2044
static struct ast_cli_entry cli_file[]
Definition: file.c:2040
struct stasis_message_type * ast_format_unregister_type(void)
Get the message type used for signaling a format unregistration.
#define STASIS_MESSAGE_TYPE_INIT(name)
Boiler-plate messaging macro for initializing message types.
Definition: stasis.h:1493
#define ARRAY_LEN(a)
Definition: utils.h:666

References ARRAY_LEN, ast_cli_register_multiple, ast_format_register_type(), ast_format_unregister_type(), ast_register_cleanup(), cli_file, file_shutdown(), and STASIS_MESSAGE_TYPE_INIT.

Referenced by asterisk_daemon().

◆ ast_file_mkftemp()

FILE * ast_file_mkftemp ( char *  template,
mode_t  mode 
)

same as mkstemp, but return a FILE

Parameters
templateThe template for the unique file name to generate. Modified in place to return the file name.
modeThe mode for file permissions
Returns
FILE handle to the temporary file on success or NULL if creation failed

Definition at line 187 of file file.c.

188{
189 FILE *p = NULL;
190 int pfd = mkstemp(template);
191 chmod(template, mode);
192 if (pfd > -1) {
193 p = fdopen(pfd, "w+");
194 if (!p) {
195 close(pfd);
196 pfd = -1;
197 }
198 }
199 return p;
200}

References ast_format_def::close, and NULL.

Referenced by AST_TEST_DEFINE(), sendmail(), and sendpage().

◆ ast_file_read_dirs()

int ast_file_read_dirs ( const char *  dir_name,
ast_file_on_file  on_file,
void *  obj,
int  max_depth 
)

Recursively iterate through files and directories up to max_depth.

Parameters
dir_namethe name of the directory to search
on_filecallback called on each file
objuser data object
max_depthre-curse into sub-directories up to a given maximum (-1 = infinite)
Return values
-1on failure
errnoon failure
0otherwise

Definition at line 1274 of file file.c.

1275{
1276 int res;
1277
1278 errno = 0;
1279
1280#if !defined(__GLIBC__)
1282#endif
1283
1284 res = __ast_file_read_dirs(dir_name, on_file, obj, max_depth);
1285
1286#if !defined(__GLIBC__)
1288#endif
1289
1290 return res;
1291}
static ast_mutex_t read_dirs_lock
Lock to hold when iterating over directories.
Definition: file.c:1271
#define ast_mutex_unlock(a)
Definition: lock.h:190
#define ast_mutex_lock(a)
Definition: lock.h:189

References __ast_file_read_dirs(), ast_mutex_lock, ast_mutex_unlock, errno, and read_dirs_lock.

Referenced by ast_media_index_update_for_file(), AST_TEST_DEFINE(), crypto_load(), module_load_helper(), and stasis_app_stored_recording_find_all().

◆ ast_filecopy()

int ast_filecopy ( const char *  oldname,
const char *  newname,
const char *  fmt 
)

Copies a file.

Parameters
oldnamename of the file you wish to copy (minus extension)
newnamename you wish the file to be copied to (minus extension)
fmtthe format of the file Copy a given file in a given format, or if fmt is NULL, then do so for all

Definition at line 1151 of file file.c.

1152{
1153 return filehelper(filename, filename2, fmt, ACTION_COPY);
1154}
static int filehelper(const char *filename, const void *arg2, const char *fmt, const enum file_action action)
Definition: file.c:549

References ACTION_COPY, filehelper(), ast_filestream::filename, and ast_filestream::fmt.

Referenced by copy_plain_file(), msg_create_from_file(), stasis_app_stored_recording_copy(), and vm_forwardoptions().

◆ ast_filedelete()

int ast_filedelete ( const char *  filename,
const char *  fmt 
)

Deletes a file.

Parameters
filenamename of the file you wish to delete (minus the extension)
fmtof the file Delete a given file in a given format, or if fmt is NULL, then do so for all

Definition at line 1141 of file file.c.

1142{
1143 return filehelper(filename, NULL, fmt, ACTION_DELETE);
1144}

References ACTION_DELETE, filehelper(), ast_filestream::filename, ast_filestream::fmt, and NULL.

Referenced by __ast_play_and_record(), announce_thread(), async_delete_name_rec_task(), conf_free(), conf_rec_name(), conf_run(), confbridge_exec(), dial_exec_full(), handle_cli_file_convert(), leave_voicemail(), mixmonitor_thread(), msg_create_from_file(), play_record_review(), record_exec(), recording_cancel(), setup_privacy_args(), and vm_delete().

◆ ast_fileexists()

int ast_fileexists ( const char *  filename,
const char *  fmt,
const char *  preflang 
)

Checks for the existence of a given file.

Parameters
filenamename of the file you wish to check, minus the extension
fmtthe format you wish to check (the extension)
preflang(the preferred language you wisht to find the file in) See if a given file exists in a given format. If fmt is NULL, any format is accepted.
Return values
0The file does not exist
1The file does exist.

Definition at line 1129 of file file.c.

1130{
1131 char *buf;
1132 int buflen;
1133
1134 if (preflang == NULL)
1135 preflang = "";
1136 buflen = strlen(preflang) + strlen(filename) + 4; /* room for everything */
1137 buf = ast_alloca(buflen);
1138 return fileexists_core(filename, fmt, preflang, buf, buflen, NULL) ? 1 : 0;
1139}
#define ast_alloca(size)
call __builtin_alloca to ensure we get gcc builtin semantics
Definition: astmm.h:288
char buf[BUFSIZE]
Definition: eagi_proxy.c:66
static int fileexists_core(const char *filename, const char *fmt, const char *preflang, char *buf, int buflen, struct ast_format_cap *result_cap)
helper routine to locate a file with a given format and language preference.
Definition: file.c:741

References ast_alloca, buf, fileexists_core(), ast_filestream::filename, ast_filestream::fmt, and NULL.

Referenced by announce_thread(), app_exec(), ast_get_character_str(), ast_get_digit_str(), ast_get_phonetic_str(), ast_moh_files_next(), common_exec(), conf_run(), dial_exec_full(), eivr_comm(), forward_message(), get_folder(), invent_message(), leave_voicemail(), meetme_menu_admin_extended(), minivm_delete_exec(), msg_create_from_file(), page_exec(), play_file(), play_message(), play_message_by_id_helper(), play_message_callerid(), readexten_exec(), record_exec(), retrydial_exec(), sayname(), setup_privacy_args(), sound_file_exists(), stasis_app_control_record(), vm_intro(), vm_msg_play(), vm_newuser_setup(), vm_options(), and vm_tempgreeting().

◆ ast_filerename()

int ast_filerename ( const char *  oldname,
const char *  newname,
const char *  fmt 
)

Renames a file.

Parameters
oldnamethe name of the file you wish to act upon (minus the extension)
newnamethe name you wish to rename the file to (minus the extension)
fmtthe format of the file Rename a given file in a given format, or if fmt is NULL, then do so for all
Return values
-1on failure

Definition at line 1146 of file file.c.

1147{
1148 return filehelper(filename, filename2, fmt, ACTION_RENAME);
1149}

References ACTION_RENAME, filehelper(), ast_filestream::filename, and ast_filestream::fmt.

Referenced by __ast_play_and_record(), forward_message(), leave_voicemail(), msg_create_from_file(), play_record_review(), rename_file(), and vm_forwardoptions().

◆ ast_format_def_unregister()

int ast_format_def_unregister ( const char *  name)

Unregisters a file format.

Parameters
namethe name of the format you wish to unregister Unregisters a format based on the name of the format.
Return values
0on success
-1on failure to unregister

Definition at line 162 of file file.c.

163{
164 struct ast_format_def *tmp;
165 int res = -1;
166
169 if (!strcasecmp(name, tmp->name)) {
172 ast_free(tmp);
173 res = 0;
174 }
175 }
178
179 if (!res)
180 ast_verb(5, "Unregistered format %s\n", name);
181 else
182 ast_log(LOG_WARNING, "Tried to unregister format %s, already unregistered\n", name);
183
184 return res;
185}
static const char name[]
Definition: format_mp3.c:68
#define AST_RWLIST_REMOVE_CURRENT
Definition: linkedlists.h:570
#define AST_RWLIST_TRAVERSE_SAFE_BEGIN
Definition: linkedlists.h:545
#define AST_RWLIST_TRAVERSE_SAFE_END
Definition: linkedlists.h:617

References ast_format_unregister_type(), ast_free, ast_log, AST_RWLIST_REMOVE_CURRENT, AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_verb, ast_format_def::list, LOG_WARNING, name, publish_format_update(), and tmp().

Referenced by unload_module().

◆ ast_format_str_reduce()

char * ast_format_str_reduce ( char *  fmts)

Remove duplicate formats from a format string.

Parameters
fmtsa format string, this string will be modified
Return values
NULLerror
Returns
a pointer to the reduced format string, this is a pointer to fmts

Definition at line 1894 of file file.c.

1895{
1896 struct ast_format_def *f;
1897 struct ast_format_def *fmts_ptr[AST_MAX_FORMATS];
1898 char *fmts_str[AST_MAX_FORMATS];
1899 char *stringp, *type;
1900 char *orig = fmts;
1901 int i, j, x, first, found = 0;
1902 int len = strlen(fmts) + 1;
1903 int res;
1904
1905 if (AST_RWLIST_RDLOCK(&formats)) {
1906 ast_log(LOG_WARNING, "Unable to lock format list\n");
1907 return NULL;
1908 }
1909
1910 stringp = ast_strdupa(fmts);
1911
1912 for (x = 0; (type = strsep(&stringp, "|")) && x < AST_MAX_FORMATS; x++) {
1914 if (exts_compare(f->exts, type)) {
1915 found = 1;
1916 break;
1917 }
1918 }
1919
1920 fmts_str[x] = type;
1921 if (found) {
1922 fmts_ptr[x] = f;
1923 } else {
1924 fmts_ptr[x] = NULL;
1925 }
1926 }
1928
1929 first = 1;
1930 for (i = 0; i < x; i++) {
1931 /* ignore invalid entries */
1932 if (!fmts_ptr[i]) {
1933 ast_log(LOG_WARNING, "ignoring unknown format '%s'\n", fmts_str[i]);
1934 continue;
1935 }
1936
1937 /* special handling for the first entry */
1938 if (first) {
1939 res = snprintf(fmts, len, "%s", fmts_str[i]);
1940 fmts += res;
1941 len -= res;
1942 first = 0;
1943 continue;
1944 }
1945
1946 found = 0;
1947 for (j = 0; j < i; j++) {
1948 /* this is a duplicate */
1949 if (fmts_ptr[j] == fmts_ptr[i]) {
1950 found = 1;
1951 break;
1952 }
1953 }
1954
1955 if (!found) {
1956 res = snprintf(fmts, len, "|%s", fmts_str[i]);
1957 fmts += res;
1958 len -= res;
1959 }
1960 }
1961
1962 if (first) {
1963 ast_log(LOG_WARNING, "no known formats found in format list (%s)\n", orig);
1964 return NULL;
1965 }
1966
1967 return orig;
1968}
struct sla_ringing_trunk * first
Definition: app_sla.c:332
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition: astmm.h:298
static const char type[]
Definition: chan_ooh323.c:109
#define exts_compare(list, type)
Definition: file.c:386
#define AST_MAX_FORMATS
Definition: file.h:44
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
char * strsep(char **str, const char *delims)
#define AST_RWLIST_RDLOCK(head)
Read locks a list.
Definition: linkedlists.h:78

References ast_log, AST_MAX_FORMATS, AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_strdupa, ast_format_def::exts, exts_compare, first, len(), ast_format_def::list, LOG_WARNING, NULL, strsep(), and type.

Referenced by actual_load_config(), and AST_TEST_DEFINE().

◆ ast_fsread_audio()

static int ast_fsread_audio ( const void *  data)
static

Definition at line 999 of file file.c.

1000{
1001 struct ast_filestream *fs = (struct ast_filestream *)data;
1002 enum fsread_res res;
1003
1004 res = ast_readaudio_callback(fs);
1005
1006 if (res == FSREAD_SUCCESS_SCHED)
1007 return 1;
1008
1009 return 0;
1010}
fsread_res
Definition: file.c:943
static enum fsread_res ast_readaudio_callback(struct ast_filestream *s)
Definition: file.c:951
This structure is allocated by file.c in one chunk, together with buf_size and desc_size bytes of mem...
Definition: mod_format.h:101

References ast_readaudio_callback(), and FSREAD_SUCCESS_SCHED.

Referenced by ast_readaudio_callback().

◆ ast_fsread_video()

static int ast_fsread_video ( const void *  data)
static

Definition at line 1044 of file file.c.

1045{
1046 struct ast_filestream *fs = (struct ast_filestream *)data;
1047 enum fsread_res res;
1048
1049 res = ast_readvideo_callback(fs);
1050
1051 if (res == FSREAD_SUCCESS_SCHED)
1052 return 1;
1053
1054 return 0;
1055}
static enum fsread_res ast_readvideo_callback(struct ast_filestream *s)
Definition: file.c:1014

References ast_readvideo_callback(), and FSREAD_SUCCESS_SCHED.

Referenced by ast_readvideo_callback().

◆ ast_get_extension_for_mime_type()

int ast_get_extension_for_mime_type ( const char *  mime_type,
char *  buffer,
size_t  capacity 
)

Get a suitable filename extension for the given MIME type.

Parameters
mime_typeThe MIME type for which to find extensions
bufferA pointer to a buffer to receive the extension
capacityThe size of 'buffer' in bytes
Return values
1if an extension was found for the provided MIME type
0if the MIME type was not found

Definition at line 2019 of file file.c.

2020{
2021 struct ast_format_def *f;
2023
2024 ast_assert(buffer && capacity);
2025
2027 if (type_in_list(f->mime_types, mime_type, strcasecmp)) {
2028 size_t item_len = strcspn(f->exts, "|");
2029 size_t bytes_written = snprintf(buffer, capacity, ".%.*s", (int) item_len, f->exts);
2030 if (bytes_written < capacity) {
2031 /* Only return success if we didn't truncate */
2032 return 1;
2033 }
2034 }
2035 }
2036
2037 return 0;
2038}
ast_mutex_t lock
Definition: app_sla.c:331
static int type_in_list(const char *list, const char *type, int(*cmp)(const char *s1, const char *s2))
Definition: file.c:373
#define SCOPED_RDLOCK(varname, lock)
scoped lock specialization for read locks
Definition: lock.h:594
char mime_types[80]
Definition: mod_format.h:47
ast_rwlock_t lock
Definition: file.c:69
#define ast_assert(a)
Definition: utils.h:739

References ast_assert, AST_RWLIST_TRAVERSE, ast_format_def::exts, ast_format_def::list, lock, formats::lock, ast_format_def::mime_types, SCOPED_RDLOCK, and type_in_list().

Referenced by derive_extension_from_mime_type().

◆ ast_get_format_for_file_ext()

struct ast_format * ast_get_format_for_file_ext ( const char *  file_ext)

Get the ast_format associated with the given file extension.

Since
12
Parameters
file_extThe file extension for which to find the format
Return values
NULLif not found
Returns
A pointer to the ast_format associated with this file extension

Definition at line 2006 of file file.c.

2007{
2008 struct ast_format_def *f;
2011 if (exts_compare(f->exts, file_ext)) {
2012 return f->format;
2013 }
2014 }
2015
2016 return NULL;
2017}
struct ast_format * format
Definition: mod_format.h:48

References AST_RWLIST_TRAVERSE, ast_format_def::exts, exts_compare, ast_format_def::format, ast_format_def::list, lock, formats::lock, NULL, and SCOPED_RDLOCK.

Referenced by ast_ari_bridges_record(), ast_ari_channels_record(), ast_ari_recordings_get_stored_file(), file_extension_from_string(), is_recording(), and process_media_file().

◆ ast_openstream()

struct ast_filestream * ast_openstream ( struct ast_channel chan,
const char *  filename,
const char *  preflang 
)

Opens stream for use in seeking, playing.

Parameters
chanchannel to work with
filenameto use
preflangprefered language to use
Returns
a ast_filestream pointer if it opens the file.
Return values
NULLon error.

Definition at line 790 of file file.c.

791{
792 return ast_openstream_full(chan, filename, preflang, 0);
793}
struct ast_filestream * ast_openstream_full(struct ast_channel *chan, const char *filename, const char *preflang, int asis)
Opens stream for use in seeking, playing.
Definition: file.c:795

References ast_openstream_full(), and ast_filestream::filename.

Referenced by ast_streamfile(), dictate_exec(), handle_getoption(), handle_streamfile(), and speech_streamfile().

◆ ast_openstream_full()

struct ast_filestream * ast_openstream_full ( struct ast_channel chan,
const char *  filename,
const char *  preflang,
int  asis 
)

Opens stream for use in seeking, playing.

Parameters
chanchannel to work with
filenameto use
preflangprefered language to use
asisif set, don't clear generators
Return values
aast_filestream pointer if it opens the file.
NULLon error.

Definition at line 795 of file file.c.

797{
798 /*
799 * Use fileexists_core() to find a file in a compatible
800 * language and format, set up a suitable translator,
801 * and open the stream.
802 */
803 struct ast_format_cap *file_fmt_cap;
804 int res;
805 int buflen;
806 char *buf;
807
808 if (!asis) {
809 /* do this first, otherwise we detect the wrong writeformat */
810 ast_stopstream(chan);
811 if (ast_channel_generator(chan))
813 }
814 if (preflang == NULL)
815 preflang = "";
816 buflen = strlen(preflang) + strlen(filename) + 4;
817 buf = ast_alloca(buflen);
818
819 if (!(file_fmt_cap = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT))) {
820 return NULL;
821 }
822 if (!fileexists_core(filename, NULL, preflang, buf, buflen, file_fmt_cap) ||
824
825 ast_log(LOG_WARNING, "File %s does not exist in any format\n", filename);
826 ao2_ref(file_fmt_cap, -1);
827 return NULL;
828 }
829
830 /* Set the channel to a format we can work with and save off the previous format. */
831 ast_channel_lock(chan);
833 /* Set the channel to the best format that exists for the file. */
834 res = ast_set_write_format_from_cap(chan, file_fmt_cap);
835 ast_channel_unlock(chan);
836 /* don't need this anymore now that the channel's write format is set. */
837 ao2_ref(file_fmt_cap, -1);
838
839 if (res == -1) { /* No format available that works with this channel */
840 return NULL;
841 }
842 res = filehelper(buf, chan, NULL, ACTION_OPEN);
843 if (res >= 0)
844 return ast_channel_stream(chan);
845 return NULL;
846}
void ast_channel_set_oldwriteformat(struct ast_channel *chan, struct ast_format *format)
#define ast_channel_lock(chan)
Definition: channel.h:2922
void ast_deactivate_generator(struct ast_channel *chan)
Definition: channel.c:2893
struct ast_format * ast_channel_writeformat(struct ast_channel *chan)
struct ast_generator * ast_channel_generator(const struct ast_channel *chan)
struct ast_filestream * ast_channel_stream(const struct ast_channel *chan)
#define ast_channel_unlock(chan)
Definition: channel.h:2923
int ast_set_write_format_from_cap(struct ast_channel *chan, struct ast_format_cap *formats)
Sets write format on channel chan Set write format for channel to whichever component of "format" is ...
Definition: channel.c:5821
@ AST_MEDIA_TYPE_AUDIO
Definition: codec.h:32
int ast_stopstream(struct ast_channel *tmp)
Stops a stream.
Definition: file.c:222
@ AST_FORMAT_CAP_FLAG_DEFAULT
Definition: format_cap.h:38
int ast_format_cap_has_type(const struct ast_format_cap *cap, enum ast_media_type type)
Find out if the capabilities structure has any formats of a specific type.
Definition: format_cap.c:613
#define ast_format_cap_alloc(flags)
Allocate a new ast_format_cap structure.
Definition: format_cap.h:49
Format capabilities structure, holds formats + preference order + etc.
Definition: format_cap.c:54

References ACTION_OPEN, ao2_ref, ast_alloca, ast_channel_generator(), ast_channel_lock, ast_channel_set_oldwriteformat(), ast_channel_stream(), ast_channel_unlock, ast_channel_writeformat(), ast_deactivate_generator(), ast_format_cap_alloc, AST_FORMAT_CAP_FLAG_DEFAULT, ast_format_cap_has_type(), ast_log, AST_MEDIA_TYPE_AUDIO, ast_set_write_format_from_cap(), ast_stopstream(), buf, fileexists_core(), filehelper(), LOG_WARNING, and NULL.

Referenced by ast_moh_files_next(), ast_openstream(), and gen_nextfile().

◆ ast_openvstream()

struct ast_filestream * ast_openvstream ( struct ast_channel chan,
const char *  filename,
const char *  preflang 
)

Opens stream for use in seeking, playing.

Parameters
chanchannel to work with
filenameto use
preflangprefered language to use
Returns
a ast_filestream pointer if it opens the file.
Return values
NULLon error.

Definition at line 848 of file file.c.

850{
851 /* As above, but for video. But here we don't have translators
852 * so we must enforce a format.
853 */
854 struct ast_format_cap *nativeformats, *tmp_cap;
855 char *buf;
856 int buflen;
857 int i, fd;
858
859 if (preflang == NULL) {
860 preflang = "";
861 }
862 buflen = strlen(preflang) + strlen(filename) + 4;
863 buf = ast_alloca(buflen);
864
865 ast_channel_lock(chan);
866 nativeformats = ao2_bump(ast_channel_nativeformats(chan));
867 ast_channel_unlock(chan);
868
869 /* is the channel capable of video without translation ?*/
870 if (!ast_format_cap_has_type(nativeformats, AST_MEDIA_TYPE_VIDEO)) {
871 ao2_cleanup(nativeformats);
872 return NULL;
873 }
875 ao2_cleanup(nativeformats);
876 return NULL;
877 }
878 /* Video is supported, so see what video formats exist for this file */
879 if (!fileexists_core(filename, NULL, preflang, buf, buflen, tmp_cap)) {
880 ao2_ref(tmp_cap, -1);
881 ao2_cleanup(nativeformats);
882 return NULL;
883 }
884
885 /* iterate over file formats and pick the first one compatible with the channel's native formats */
886 for (i = 0; i < ast_format_cap_count(tmp_cap); ++i) {
887 struct ast_format *format = ast_format_cap_get_format(tmp_cap, i);
888
889 if ((ast_format_get_type(format) != AST_MEDIA_TYPE_VIDEO) ||
890 !ast_format_cap_iscompatible(nativeformats, tmp_cap)) {
891 ao2_ref(format, -1);
892 continue;
893 }
894
895 fd = filehelper(buf, chan, ast_format_get_name(format), ACTION_OPEN);
896 if (fd >= 0) {
897 ao2_ref(format, -1);
898 ao2_ref(tmp_cap, -1);
899 ao2_cleanup(nativeformats);
900 return ast_channel_vstream(chan);
901 }
902 ast_log(LOG_WARNING, "File %s has video but couldn't be opened\n", filename);
903 ao2_ref(format, -1);
904 }
905 ao2_ref(tmp_cap, -1);
906 ao2_cleanup(nativeformats);
907
908 return NULL;
909}
#define ao2_cleanup(obj)
Definition: astobj2.h:1934
#define ao2_bump(obj)
Bump refcount on an AO2 object by one, returning the object.
Definition: astobj2.h:480
struct ast_format_cap * ast_channel_nativeformats(const struct ast_channel *chan)
struct ast_filestream * ast_channel_vstream(const struct ast_channel *chan)
@ AST_MEDIA_TYPE_VIDEO
Definition: codec.h:33
enum ast_media_type ast_format_get_type(const struct ast_format *format)
Get the media type of a format.
Definition: format.c:354
const char * ast_format_get_name(const struct ast_format *format)
Get the name associated with a format.
Definition: format.c:334
struct ast_format * ast_format_cap_get_format(const struct ast_format_cap *cap, int position)
Get the format at a specific index.
Definition: format_cap.c:400
int ast_format_cap_iscompatible(const struct ast_format_cap *cap1, const struct ast_format_cap *cap2)
Determine if any joint capabilities exist between two capabilities structures.
Definition: format_cap.c:653
size_t ast_format_cap_count(const struct ast_format_cap *cap)
Get the number of formats present within the capabilities structure.
Definition: format_cap.c:395
Definition of a media format.
Definition: format.c:43

References ACTION_OPEN, ao2_bump, ao2_cleanup, ao2_ref, ast_alloca, ast_channel_lock, ast_channel_nativeformats(), ast_channel_unlock, ast_channel_vstream(), ast_format_cap_alloc, ast_format_cap_count(), AST_FORMAT_CAP_FLAG_DEFAULT, ast_format_cap_get_format(), ast_format_cap_has_type(), ast_format_cap_iscompatible(), ast_format_get_name(), ast_format_get_type(), ast_log, AST_MEDIA_TYPE_VIDEO, buf, fileexists_core(), filehelper(), LOG_WARNING, and NULL.

Referenced by ast_streamfile(), handle_getoption(), and handle_streamfile().

◆ ast_playstream()

int ast_playstream ( struct ast_filestream s)

Play a open stream on a channel.

Parameters
sfilestream to play
Return values
0on success.
-1on failure.

Definition at line 1063 of file file.c.

1064{
1065 enum fsread_res res;
1066
1068 res = ast_readaudio_callback(s);
1069 else
1070 res = ast_readvideo_callback(s);
1071
1072 return (res == FSREAD_FAILURE) ? -1 : 0;
1073}
struct ast_format_def * fmt
Definition: mod_format.h:103

References ast_format_get_type(), AST_MEDIA_TYPE_AUDIO, ast_readaudio_callback(), ast_readvideo_callback(), ast_filestream::fmt, ast_format_def::format, and FSREAD_FAILURE.

Referenced by ast_streamfile(), handle_getoption(), handle_streamfile(), and speech_streamfile().

◆ ast_ratestream()

int ast_ratestream ( struct ast_filestream fs)

Return the sample rate of the stream's format.

Parameters
fsfs to act on
Returns
sample rate in Hz

Definition at line 1090 of file file.c.

1091{
1093}
unsigned int ast_format_get_sample_rate(const struct ast_format *format)
Get the sample rate of a media format.
Definition: format.c:379

References ast_format_get_sample_rate(), ast_filestream::fmt, and ast_format_def::format.

Referenced by msg_create_from_file().

◆ ast_readaudio_callback()

static enum fsread_res ast_readaudio_callback ( struct ast_filestream s)
static

Definition at line 951 of file file.c.

952{
953 int whennext = 0;
954
955 while (!whennext) {
956 struct ast_frame *fr;
957
958 if (s->orig_chan_name && strcasecmp(ast_channel_name(s->owner), s->orig_chan_name)) {
959 goto return_failure;
960 }
961
962 fr = read_frame(s, &whennext);
963
964 if (!fr /* stream complete */ || ast_write(s->owner, fr) /* error writing */) {
965 if (fr) {
966 ast_debug(2, "Failed to write frame\n");
967 ast_frfree(fr);
968 }
969 goto return_failure;
970 }
971
972 if (fr) {
973 ast_frfree(fr);
974 }
975 }
976
977 if (whennext != s->lasttimeout) {
978 if (ast_channel_timingfd(s->owner) > -1) {
979 float samp_rate = (float) ast_format_get_sample_rate(s->fmt->format);
980 unsigned int rate;
981
982 rate = (unsigned int) roundf(samp_rate / ((float) whennext));
983
985 } else {
987 }
988 s->lasttimeout = whennext;
990 }
992
993return_failure:
995 ast_settimeout(s->owner, 0, NULL, NULL);
996 return FSREAD_FAILURE;
997}
const char * ast_channel_name(const struct ast_channel *chan)
int ast_settimeout_full(struct ast_channel *c, unsigned int rate, int(*func)(const void *data), void *data, unsigned int is_ao2_obj)
Definition: channel.c:3185
void ast_channel_streamid_set(struct ast_channel *chan, int value)
int ast_write(struct ast_channel *chan, struct ast_frame *frame)
Write a frame to a channel This function writes the given frame to the indicated channel.
Definition: channel.c:5144
int ast_channel_timingfd(const struct ast_channel *chan)
int ast_settimeout(struct ast_channel *c, unsigned int rate, int(*func)(const void *data), void *data)
Enable or disable timer ticks for a channel.
Definition: channel.c:3180
struct ast_sched_context * ast_channel_sched(const struct ast_channel *chan)
static int ast_fsread_audio(const void *data)
Definition: file.c:999
static struct ast_frame * read_frame(struct ast_filestream *s, int *whennext)
Definition: file.c:911
float roundf(float x)
#define ast_frfree(fr)
int ast_sched_add(struct ast_sched_context *con, int when, ast_sched_cb callback, const void *data) attribute_warn_unused_result
Adds a scheduled event.
Definition: sched.c:567
const char * orig_chan_name
Definition: mod_format.h:125
Data structure associated with a single frame of data.

References ast_channel_name(), ast_channel_sched(), ast_channel_streamid_set(), ast_channel_timingfd(), ast_debug, ast_format_get_sample_rate(), ast_frfree, ast_fsread_audio(), ast_sched_add(), ast_settimeout(), ast_settimeout_full(), ast_write(), ast_filestream::fmt, ast_format_def::format, FSREAD_FAILURE, FSREAD_SUCCESS_NOSCHED, FSREAD_SUCCESS_SCHED, ast_filestream::lasttimeout, NULL, ast_filestream::orig_chan_name, ast_filestream::owner, read_frame(), and roundf().

Referenced by ast_fsread_audio(), and ast_playstream().

◆ ast_readfile()

struct ast_filestream * ast_readfile ( const char *  filename,
const char *  type,
const char *  comment,
int  flags,
int  check,
mode_t  mode 
)

Starts reading from a file.

Parameters
filenamethe name of the file to read from
typeformat of file you wish to read from
commentcomment to go with
flagsfile flags
check(unimplemented, hence negligible)
modeOpen mode Open an incoming file stream. flags are flags for the open() command, and if check is non-zero, then it will not read a file if there are any files that start with that name and have an extension Please note, this is a blocking function. Program execution will not return until ast_waitstream completes it's execution.
Returns
a struct ast_filestream on success.
Return values
NULLon failure.

Definition at line 1371 of file file.c.

1372{
1373 FILE *bfile;
1374 struct ast_format_def *f;
1375 struct ast_filestream *fs = NULL;
1376 char *fn;
1377 int format_found = 0;
1378
1380
1381 AST_RWLIST_TRAVERSE(&formats, f, list) {
1382 fs = NULL;
1383 if (!exts_compare(f->exts, type))
1384 continue;
1385 else
1386 format_found = 1;
1387
1389 if (!fn) {
1390 continue;
1391 }
1392 errno = 0;
1393 bfile = fopen(fn, "r");
1394
1395 if (!bfile || (fs = get_filestream(f, bfile)) == NULL || open_wrapper(fs) ) {
1396 ast_log(LOG_WARNING, "Unable to open %s\n", fn);
1397 if (fs) {
1398 ast_closestream(fs);
1399 }
1400 fs = NULL;
1401 bfile = NULL;
1402 ast_free(fn);
1403 break;
1404 }
1405 /* found it */
1406 fs->trans = NULL;
1407 fs->fmt = f;
1408 fs->flags = flags;
1409 fs->mode = mode;
1411 fs->vfs = NULL;
1412 ast_free(fn);
1413 break;
1414 }
1415
1417 if (!format_found)
1418 ast_log(LOG_WARNING, "No such format '%s'\n", type);
1419
1420 return fs;
1421}
#define ast_strdup(str)
A wrapper for strdup()
Definition: astmm.h:241
static char * build_filename(const char *filename, const char *ext)
construct a filename. Absolute pathnames are preserved, relative names are prefixed by the sounds/ di...
Definition: file.c:349
int ast_closestream(struct ast_filestream *f)
Closes a stream.
Definition: file.c:1111
static int open_wrapper(struct ast_filestream *s)
Definition: file.c:525
static struct ast_filestream * get_filestream(struct ast_format_def *fmt, FILE *bfile)
Definition: file.c:463
struct ast_filestream * vfs
Definition: mod_format.h:110
struct ast_trans_pvt * trans
Definition: mod_format.h:112
char * filename
Definition: mod_format.h:107

References ast_closestream(), ast_free, ast_log, AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_strdup, build_filename(), errno, exts_compare, ast_filestream::f, ast_filestream::filename, ast_filestream::flags, ast_filestream::fmt, get_filestream(), LOG_WARNING, ast_filestream::mode, NULL, open_wrapper(), ast_filestream::trans, type, and ast_filestream::vfs.

Referenced by __ast_play_and_record(), handle_cli_file_convert(), and msg_create_from_file().

◆ ast_readframe()

struct ast_frame * ast_readframe ( struct ast_filestream s)

Read a frame from a filestream.

Parameters
sast_filestream to act on
Returns
a frame.
Return values
NULLif read failed.

Definition at line 936 of file file.c.

937{
938 int whennext = 0;
939
940 return read_frame(s, &whennext);
941}

References read_frame().

Referenced by __ast_play_and_record(), dictate_exec(), gen_readframe(), handle_cli_file_convert(), and moh_files_readframe().

◆ ast_readvideo_callback()

static enum fsread_res ast_readvideo_callback ( struct ast_filestream s)
static

Definition at line 1014 of file file.c.

1015{
1016 int whennext = 0;
1017
1018 while (!whennext) {
1019 struct ast_frame *fr = read_frame(s, &whennext);
1020
1021 if (!fr /* stream complete */ || ast_write(s->owner, fr) /* error writing */) {
1022 if (fr) {
1023 ast_debug(2, "Failed to write frame\n");
1024 ast_frfree(fr);
1025 }
1027 return FSREAD_FAILURE;
1028 }
1029
1030 if (fr) {
1031 ast_frfree(fr);
1032 }
1033 }
1034
1035 if (whennext != s->lasttimeout) {
1037 s->lasttimeout = whennext;
1039 }
1040
1041 return FSREAD_SUCCESS_SCHED;
1042}
void ast_channel_vstreamid_set(struct ast_channel *chan, int value)
static int ast_fsread_video(const void *data)
Definition: file.c:1044

References ast_channel_sched(), ast_channel_vstreamid_set(), ast_debug, ast_format_get_sample_rate(), ast_frfree, ast_fsread_video(), ast_sched_add(), ast_write(), ast_filestream::fmt, ast_format_def::format, FSREAD_FAILURE, FSREAD_SUCCESS_NOSCHED, FSREAD_SUCCESS_SCHED, ast_filestream::lasttimeout, ast_filestream::owner, and read_frame().

Referenced by ast_fsread_video(), and ast_playstream().

◆ ast_seekstream()

int ast_seekstream ( struct ast_filestream fs,
off_t  sample_offset,
int  whence 
)

Seeks into stream.

Parameters
fsast_filestream to perform seek on
sample_offsetnumbers of samples to seek
whenceSEEK_SET, SEEK_CUR, SEEK_END
Return values
0on success.
-1on failure.

Definition at line 1075 of file file.c.

1076{
1077 return fs->fmt->seek(fs, sample_offset, whence);
1078}
int(* seek)(struct ast_filestream *, off_t, int)
Definition: mod_format.h:68

References ast_filestream::fmt, and ast_format_def::seek.

Referenced by ast_moh_files_next(), ast_stream_fastforward(), ast_stream_rewind(), ast_streamfile(), control_streamfile(), dictate_exec(), handle_getoption(), handle_recordfile(), handle_streamfile(), msg_create_from_file(), and speech_streamfile().

◆ ast_stopstream()

int ast_stopstream ( struct ast_channel c)

Stops a stream.

Parameters
cThe channel you wish to stop playback on

Stop playback of a stream

Return values
0always
Note
The channel does not need to be locked before calling this function.

Definition at line 222 of file file.c.

223{
225
226 /* Stop a running stream if there is one */
227 if (ast_channel_stream(tmp)) {
231 ast_log(LOG_WARNING, "Unable to restore format back to %s\n", ast_format_get_name(ast_channel_oldwriteformat(tmp)));
232 }
233 /* Stop the video stream too */
234 if (ast_channel_vstream(tmp) != NULL) {
237 }
238
240
241 return 0;
242}
void ast_channel_stream_set(struct ast_channel *chan, struct ast_filestream *value)
struct ast_format * ast_channel_oldwriteformat(struct ast_channel *chan)
int ast_set_write_format(struct ast_channel *chan, struct ast_format *format)
Sets write format on channel chan.
Definition: channel.c:5803
void ast_channel_vstream_set(struct ast_channel *chan, struct ast_filestream *value)

References ast_channel_lock, ast_channel_oldwriteformat(), ast_channel_stream(), ast_channel_stream_set(), ast_channel_unlock, ast_channel_vstream(), ast_channel_vstream_set(), ast_closestream(), ast_format_get_name(), ast_log, ast_set_write_format(), LOG_WARNING, NULL, and tmp().

Referenced by action_playback_and_continue(), adsi_transmit_message_full(), agent_alert(), announce_to_dial(), ast_openstream_full(), ast_play_and_wait(), ast_readstring_full(), ast_say_enumeration_full_da(), ast_say_enumeration_full_de(), ast_say_enumeration_full_en(), ast_say_enumeration_full_he(), ast_say_enumeration_full_is(), ast_say_enumeration_full_vi(), ast_say_number_full_cs(), ast_say_number_full_da(), ast_say_number_full_de(), ast_say_number_full_en_GB(), ast_say_number_full_es(), ast_say_number_full_fr(), ast_say_number_full_gr(), ast_say_number_full_he(), ast_say_number_full_hu(), ast_say_number_full_is(), ast_say_number_full_it(), ast_say_number_full_ja(), ast_say_number_full_ka(), ast_say_number_full_nl(), ast_say_number_full_no(), ast_say_number_full_pt(), ast_say_number_full_ru(), ast_say_number_full_se(), ast_say_number_full_th(), ast_say_number_full_ur(), ast_say_number_full_vi(), ast_say_number_full_zh(), ast_stream_and_wait(), background_detect_exec(), conf_exec(), conf_run(), control_streamfile(), dial_exec_full(), directory_exec(), grab_transfer(), handle_getoption(), handle_speechrecognize(), handle_streamfile(), isAnsweringMachine(), ivr_dispatch(), leave_voicemail(), meetme_menu_admin(), meetme_menu_admin_extended(), minivm_greet_exec(), mp3_exec(), pbx_builtin_background(), pl_odtworz_plik(), play_file(), play_files_helper(), play_mailbox_owner(), playback_exec(), queue_exec(), read_exec(), readexten_exec(), record_exec(), recordthread(), s_streamwait3(), say_filenames(), select_item_seq(), send_waveform_to_channel(), speech_background(), vm_authenticate(), vm_execmain(), wait_for_winner(), waitstream_core(), and zapateller_exec().

◆ ast_stream_and_wait()

int ast_stream_and_wait ( struct ast_channel chan,
const char *  file,
const char *  digits 
)

stream file until digit If the file name is non-empty, try to play it.

Note
If digits == "" then we can simply check for non-zero.
If a failure is encountered, the stream will be closed before returning.
Return values
0if success.
-1if error.
digitif interrupted by a digit.

Definition at line 1878 of file file.c.

1879{
1880 int res = 0;
1881 if (!ast_strlen_zero(file)) {
1882 res = ast_streamfile(chan, file, ast_channel_language(chan));
1883 if (!res) {
1884 res = ast_waitstream(chan, digits);
1885 }
1886 }
1887 if (res == -1) {
1888 ast_stopstream(chan);
1889 }
1890
1891 return res;
1892}
const char * ast_channel_language(const struct ast_channel *chan)
int ast_streamfile(struct ast_channel *chan, const char *filename, const char *preflang)
Streams a file.
Definition: file.c:1293
int ast_waitstream(struct ast_channel *c, const char *breakon)
Waits for a stream to stop or digit to be pressed.
Definition: file.c:1840
static force_inline int attribute_pure ast_strlen_zero(const char *s)
Definition: strings.h:65

References ast_channel_language(), ast_stopstream(), ast_streamfile(), ast_strlen_zero(), ast_waitstream(), and make_ari_stubs::file.

Referenced by __ast_play_and_record(), action_playback(), action_toggle_mute_participants(), agent_alert(), agent_login_exec(), announce_user_count(), app_exec(), ast_bridge_channel_playfile(), ast_pickup_call(), ast_record_review(), bridge_features_duration_callback(), confbridge_exec(), directory_exec(), forward_message(), grab_transfer(), invent_message(), ivr_dispatch(), join_conference_bridge(), leave_voicemail(), limits_interval_playback(), mixmonitor_thread(), park_app_exec(), parked_call_app_exec(), play_file(), play_files_helper(), play_mailbox_owner(), play_message_callerid(), play_prompt_to_user(), play_record_review(), playback_common(), sayname(), select_item_seq(), setup_mixmonitor_ds(), stream_failsound(), vm_forwardoptions(), vmsayname_exec(), and wait_file2().

◆ ast_stream_fastforward()

int ast_stream_fastforward ( struct ast_filestream fs,
off_t  ms 
)

Fast forward stream ms.

Parameters
fsfilestream to act on
msmilliseconds to move
Return values
0on success.
-1on failure.

Definition at line 1095 of file file.c.

1096{
1097 return ast_seekstream(fs, ms * DEFAULT_SAMPLES_PER_MS, SEEK_CUR);
1098}
#define DEFAULT_SAMPLES_PER_MS
Definition: asterisk.h:49
int ast_seekstream(struct ast_filestream *fs, off_t sample_offset, int whence)
Seeks into stream.
Definition: file.c:1075

References ast_seekstream(), and DEFAULT_SAMPLES_PER_MS.

Referenced by waitstream_control().

◆ ast_stream_rewind()

int ast_stream_rewind ( struct ast_filestream fs,
off_t  ms 
)

Rewind stream ms.

Parameters
fsfilestream to act on
msmilliseconds to move
Return values
0on success.
-1on failure.

Definition at line 1100 of file file.c.

1101{
1102 off_t offset = ast_tellstream(fs);
1103 if (ms * DEFAULT_SAMPLES_PER_MS > offset) {
1104 /* Don't even bother asking the file format to seek to a negative offset... */
1105 ast_debug(1, "Restarting, rather than seeking to negative offset %ld\n", (long) (offset - (ms * DEFAULT_SAMPLES_PER_MS)));
1106 return ast_seekstream(fs, 0, SEEK_SET);
1107 }
1108 return ast_seekstream(fs, -ms * DEFAULT_SAMPLES_PER_MS, SEEK_CUR);
1109}
off_t ast_tellstream(struct ast_filestream *fs)
Tell where we are in a stream.
Definition: file.c:1085

References ast_debug, ast_seekstream(), ast_tellstream(), and DEFAULT_SAMPLES_PER_MS.

Referenced by __ast_play_and_record(), handle_recordfile(), record_exec(), and waitstream_control().

◆ ast_streamfile()

int ast_streamfile ( struct ast_channel c,
const char *  filename,
const char *  preflang 
)

Streams a file.

Parameters
cchannel to stream the file to
filenamethe name of the file you wish to stream, minus the extension
preflangthe preferred language you wish to have the file streamed to you in Prepares a channel for the streaming of a file. To start the stream, afterward do a ast_waitstream() on the channel Also, it will stop any existing streams on the channel.
Return values
0on success.
-1on failure.

Definition at line 1293 of file file.c.

1295{
1296 struct ast_filestream *fs = NULL;
1297 struct ast_filestream *vfs = NULL;
1298 off_t pos;
1299 int seekattempt;
1300 int res;
1301 char custom_filename[256];
1302 char *tmp_filename;
1303
1304 /* If file with the same name exists in /var/lib/asterisk/sounds/custom directory, use that file.
1305 * Otherwise, use the original file*/
1306
1308 memset(custom_filename, 0, sizeof(custom_filename));
1309 snprintf(custom_filename, sizeof(custom_filename), "custom/%s", filename);
1310 fs = ast_openstream(chan, custom_filename, preflang);
1311 if (fs) {
1312 tmp_filename = custom_filename;
1313 ast_debug(3, "Found file %s in custom directory\n", filename);
1314 }
1315 }
1316
1317 if (!fs) {
1318 fs = ast_openstream(chan, filename, preflang);
1319 if (!fs) {
1320 struct ast_str *codec_buf = ast_str_alloca(AST_FORMAT_CAP_NAMES_LEN);
1321 ast_channel_lock(chan);
1322 ast_log(LOG_WARNING, "Unable to open %s (format %s): %s\n",
1323 filename, ast_format_cap_get_names(ast_channel_nativeformats(chan), &codec_buf), strerror(errno));
1324 ast_channel_unlock(chan);
1325 return -1;
1326 }
1327 tmp_filename = (char *)filename;
1328 }
1329
1330 /* check to see if there is any data present (not a zero length file),
1331 * done this way because there is no where for ast_openstream_full to
1332 * return the file had no data. */
1333 pos = ftello(fs->f);
1334 seekattempt = fseeko(fs->f, -1, SEEK_END);
1335 if (seekattempt) {
1336 if (errno == EINVAL) {
1337 /* Zero-length file, as opposed to a pipe */
1338 return 0;
1339 } else {
1340 ast_seekstream(fs, 0, SEEK_SET);
1341 }
1342 } else {
1343 fseeko(fs->f, pos, SEEK_SET);
1344 }
1345
1346 vfs = ast_openvstream(chan, tmp_filename, preflang);
1347 if (vfs) {
1348 ast_debug(1, "Ooh, found a video stream, too, format %s\n", ast_format_get_name(vfs->fmt->format));
1349 }
1350
1353 if (ast_applystream(chan, fs))
1354 return -1;
1355 if (vfs && ast_applystream(chan, vfs))
1356 return -1;
1357 ast_test_suite_event_notify("PLAYBACK", "Message: %s\r\nChannel: %s", tmp_filename, ast_channel_name(chan));
1358 res = ast_playstream(fs);
1359 if (!res && vfs)
1360 res = ast_playstream(vfs);
1361
1362 if (VERBOSITY_ATLEAST(3)) {
1363 ast_channel_lock(chan);
1364 ast_verb(3, "<%s> Playing '%s.%s' (language '%s')\n", ast_channel_name(chan), tmp_filename, ast_format_get_name(ast_channel_writeformat(chan)), preflang ? preflang : "default");
1365 ast_channel_unlock(chan);
1366 }
1367
1368 return res;
1369}
struct ast_flags * ast_channel_flags(struct ast_channel *chan)
@ AST_FLAG_MASQ_NOSTREAM
Definition: channel.h:1014
struct ast_filestream * ast_openstream(struct ast_channel *chan, const char *filename, const char *preflang)
Opens stream for use in seeking, playing.
Definition: file.c:790
int ast_applystream(struct ast_channel *chan, struct ast_filestream *s)
Applies a open stream to a channel.
Definition: file.c:1057
struct ast_filestream * ast_openvstream(struct ast_channel *chan, const char *filename, const char *preflang)
Opens stream for use in seeking, playing.
Definition: file.c:848
static int is_absolute_path(const char *filename)
Definition: file.c:675
int ast_playstream(struct ast_filestream *s)
Play a open stream on a channel.
Definition: file.c:1063
#define AST_FORMAT_CAP_NAMES_LEN
Definition: format_cap.h:324
const char * ast_format_cap_get_names(const struct ast_format_cap *cap, struct ast_str **buf)
Get the names of codecs of a set of formats.
Definition: format_cap.c:734
#define VERBOSITY_ATLEAST(level)
#define ast_opt_sounds_search_custom
Definition: options.h:138
#define ast_str_alloca(init_len)
Definition: strings.h:848
Support for dynamic strings.
Definition: strings.h:623
#define ast_test_suite_event_notify(s, f,...)
Definition: test.h:189
#define ast_test_flag(p, flag)
Definition: utils.h:63

References ast_applystream(), ast_channel_flags(), ast_channel_lock, ast_channel_name(), ast_channel_nativeformats(), ast_channel_unlock, ast_channel_writeformat(), ast_debug, AST_FLAG_MASQ_NOSTREAM, ast_format_cap_get_names(), AST_FORMAT_CAP_NAMES_LEN, ast_format_get_name(), ast_log, ast_openstream(), ast_openvstream(), ast_opt_sounds_search_custom, ast_playstream(), ast_seekstream(), ast_str_alloca, ast_strdup, ast_test_flag, ast_test_suite_event_notify, ast_verb, errno, ast_filestream::f, ast_filestream::filename, ast_filestream::fmt, ast_format_def::format, is_absolute_path(), LOG_WARNING, NULL, ast_filestream::orig_chan_name, VERBOSITY_ATLEAST, and ast_filestream::vfs.

Referenced by __analog_ss_thread(), action_playback_and_continue(), analog_ss_thread(), announce_thread(), announce_to_dial(), app_exec(), ast_app_getdata_full(), ast_app_getdata_terminator(), ast_play_and_wait(), ast_say_date_da(), ast_say_date_de(), ast_say_date_en(), ast_say_date_fr(), ast_say_date_gr(), ast_say_date_he(), ast_say_date_hu(), ast_say_date_is(), ast_say_date_ja(), ast_say_date_ka(), ast_say_date_nl(), ast_say_date_th(), ast_say_date_with_format_gr(), ast_say_datetime_en(), ast_say_datetime_fr(), ast_say_datetime_from_now_en(), ast_say_datetime_from_now_fr(), ast_say_datetime_from_now_he(), ast_say_datetime_from_now_ka(), ast_say_datetime_gr(), ast_say_datetime_he(), ast_say_datetime_ja(), ast_say_datetime_nl(), ast_say_datetime_pt(), ast_say_datetime_th(), ast_say_datetime_zh(), ast_say_enumeration_full_da(), ast_say_enumeration_full_de(), ast_say_enumeration_full_en(), ast_say_enumeration_full_he(), ast_say_enumeration_full_is(), ast_say_enumeration_full_vi(), ast_say_number_full_cs(), ast_say_number_full_da(), ast_say_number_full_de(), ast_say_number_full_en_GB(), ast_say_number_full_es(), ast_say_number_full_fr(), ast_say_number_full_gr(), ast_say_number_full_he(), ast_say_number_full_hu(), ast_say_number_full_is(), ast_say_number_full_it(), ast_say_number_full_ja(), ast_say_number_full_ka(), ast_say_number_full_nl(), ast_say_number_full_no(), ast_say_number_full_pt(), ast_say_number_full_ru(), ast_say_number_full_se(), ast_say_number_full_th(), ast_say_number_full_ur(), ast_say_number_full_vi(), ast_say_number_full_zh(), ast_say_time_de(), ast_say_time_en(), ast_say_time_fr(), ast_say_time_gr(), ast_say_time_hu(), ast_say_time_ja(), ast_say_time_ka(), ast_say_time_nl(), ast_say_time_zh(), ast_stream_and_wait(), auth_exec(), background_detect_exec(), common_exec(), conf_exec(), conf_get_pin(), conf_run(), control_streamfile(), dial_exec_full(), do_directory(), find_conf_realtime(), forward_message(), gr_say_number_female(), handle_recordfile(), invent_message(), isAnsweringMachine(), leave_voicemail(), meetme_menu_admin(), meetme_menu_admin_extended(), meetme_menu_normal(), minivm_greet_exec(), page_exec(), pbx_builtin_background(), pl_odtworz_plik(), play_and_wait(), play_file(), play_record_review(), playback_exec(), privacy_exec(), readexten_exec(), record_exec(), retrydial_exec(), s_streamwait3(), say_filenames(), select_item_menu(), setup_privacy_args(), vm_authenticate(), wait_file(), and wait_for_winner().

◆ ast_tellstream()

off_t ast_tellstream ( struct ast_filestream fs)

Tell where we are in a stream.

Parameters
fsfs to act on
Returns
a long as a sample offset into stream

Definition at line 1085 of file file.c.

1086{
1087 return fs->fmt->tell(fs);
1088}
off_t(* tell)(struct ast_filestream *fs)
Definition: mod_format.h:70

References ast_filestream::fmt, and ast_format_def::tell.

Referenced by __ast_play_and_record(), ast_moh_files_next(), ast_stream_rewind(), control_streamfile(), handle_getoption(), handle_recordfile(), handle_speechrecognize(), handle_streamfile(), msg_create_from_file(), waitstream_control(), and waitstream_core().

◆ ast_truncstream()

int ast_truncstream ( struct ast_filestream fs)

Trunc stream at current location.

Parameters
fsfilestream to act on
Return values
0on success.
-1on failure.

Definition at line 1080 of file file.c.

1081{
1082 return fs->fmt->trunc(fs);
1083}
int(* trunc)(struct ast_filestream *fs)
Definition: mod_format.h:69

References ast_filestream::fmt, and ast_format_def::trunc.

Referenced by __ast_play_and_record(), handle_recordfile(), and record_exec().

◆ ast_waitstream()

int ast_waitstream ( struct ast_channel c,
const char *  breakon 
)

Waits for a stream to stop or digit to be pressed.

Parameters
cchannel to waitstream on
breakonstring of DTMF digits to break upon Begins playback of a stream... Wait for a stream to stop or for any one of a given digit to arrive,
Return values
0if the stream finishes
characterif it was interrupted by the channel.
-1on error

Definition at line 1840 of file file.c.

1841{
1842 int res;
1843
1844 res = waitstream_core(c, breakon, NULL, NULL, 0, -1, -1, NULL, NULL /* no callback */);
1845
1846 return sanitize_waitstream_return(res);
1847}
static int sanitize_waitstream_return(int return_value)
Definition: file.c:1823
static int waitstream_core(struct ast_channel *c, const char *breakon, const char *forward, const char *reverse, int skip_ms, int audiofd, int cmdfd, const char *context, ast_waitstream_fr_cb cb)
the core of all waitstream() functions
Definition: file.c:1613
static struct test_val c

References c, NULL, sanitize_waitstream_return(), and waitstream_core().

Referenced by __analog_ss_thread(), action_playback_and_continue(), analog_ss_thread(), announce_thread(), announce_to_dial(), app_exec(), ast_play_and_wait(), ast_say_date_da(), ast_say_date_de(), ast_say_date_en(), ast_say_date_fr(), ast_say_date_gr(), ast_say_date_he(), ast_say_date_hu(), ast_say_date_is(), ast_say_date_ja(), ast_say_date_ka(), ast_say_date_nl(), ast_say_date_th(), ast_say_date_with_format_gr(), ast_say_datetime_en(), ast_say_datetime_fr(), ast_say_datetime_from_now_en(), ast_say_datetime_from_now_fr(), ast_say_datetime_from_now_he(), ast_say_datetime_from_now_ka(), ast_say_datetime_gr(), ast_say_datetime_he(), ast_say_datetime_ja(), ast_say_datetime_nl(), ast_say_datetime_pt(), ast_say_datetime_th(), ast_say_datetime_zh(), ast_say_enumeration_full_da(), ast_say_enumeration_full_de(), ast_say_enumeration_full_en(), ast_say_enumeration_full_he(), ast_say_enumeration_full_is(), ast_say_enumeration_full_vi(), ast_say_number_full_cs(), ast_say_number_full_da(), ast_say_number_full_de(), ast_say_number_full_en_GB(), ast_say_number_full_es(), ast_say_number_full_fr(), ast_say_number_full_gr(), ast_say_number_full_he(), ast_say_number_full_hu(), ast_say_number_full_is(), ast_say_number_full_it(), ast_say_number_full_ja(), ast_say_number_full_ka(), ast_say_number_full_nl(), ast_say_number_full_no(), ast_say_number_full_pt(), ast_say_number_full_ru(), ast_say_number_full_se(), ast_say_number_full_th(), ast_say_number_full_ur(), ast_say_number_full_vi(), ast_say_number_full_zh(), ast_say_time_de(), ast_say_time_en(), ast_say_time_fr(), ast_say_time_gr(), ast_say_time_he(), ast_say_time_hu(), ast_say_time_ja(), ast_say_time_ka(), ast_say_time_nl(), ast_say_time_zh(), ast_stream_and_wait(), auth_exec(), common_exec(), conf_exec(), conf_get_pin(), conf_run(), directory_exec(), find_conf_realtime(), gr_say_number_female(), handle_recordfile(), invent_message(), leave_voicemail(), meetme_menu_admin(), meetme_menu_admin_extended(), meetme_menu_normal(), minivm_greet_exec(), page_exec(), pbx_builtin_background(), pl_odtworz_plik(), play_and_wait(), play_file(), play_record_review(), playback_exec(), privacy_exec(), record_exec(), retrydial_exec(), s_streamwait3(), say_filenames(), select_item_menu(), setup_privacy_args(), vm_authenticate(), and wait_file().

◆ ast_waitstream_exten()

int ast_waitstream_exten ( struct ast_channel c,
const char *  context 
)

Waits for a stream to stop or digit matching a valid one digit exten to be pressed.

Parameters
cchannel to waitstream on
contextstring of context to match digits to break upon Begins playback of a stream... Wait for a stream to stop or for any one of a valid extension digit to arrive,
Return values
0if the stream finishes.
characterif it was interrupted.
-1on error.

Definition at line 1859 of file file.c.

1860{
1861 int res;
1862
1863 /* Waitstream, with return in the case of a valid 1 digit extension */
1864 /* in the current or specified context being pressed */
1865 if (!context)
1867 res = waitstream_core(c, NULL, NULL, NULL, 0,
1868 -1, -1, context, NULL /* no callback */);
1869
1870 return sanitize_waitstream_return(res);
1871}
const char * ast_channel_context(const struct ast_channel *chan)

References ast_channel_context(), c, voicemailpwcheck::context, NULL, sanitize_waitstream_return(), and waitstream_core().

Referenced by pbx_builtin_background().

◆ ast_waitstream_fr()

int ast_waitstream_fr ( struct ast_channel c,
const char *  breakon,
const char *  forward,
const char *  rewind,
int  ms 
)

Same as waitstream but allows stream to be forwarded or rewound.

Parameters
cchannel to waitstream on
breakonstring of DTMF digits to break upon
forwardDTMF digit to fast forward upon
rewindDTMF digit to rewind upon
msHow many miliseconds to skip forward/back Begins playback of a stream... Wait for a stream to stop or for any one of a given digit to arrive,
Return values
0if the stream finishes.
characterif it was interrupted,
Returns
the value of the control frame if it was interrupted by some other party,
Return values
-1on error.

Definition at line 1809 of file file.c.

1810{
1811 return waitstream_core(c, breakon, forward, reverse, ms,
1812 -1 /* no audiofd */, -1 /* no cmdfd */, NULL /* no context */, NULL /* no callback */);
1813}

References c, NULL, and waitstream_core().

Referenced by control_streamfile().

◆ ast_waitstream_fr_w_cb()

int ast_waitstream_fr_w_cb ( struct ast_channel c,
const char *  breakon,
const char *  forward,
const char *  rewind,
int  ms,
ast_waitstream_fr_cb  cb 
)

Same as waitstream_fr but allows a callback to be alerted when a user fastforwards or rewinds the file.

Parameters
cchannel to waitstream on
breakonstring of DTMF digits to break upon
forwardDTMF digit to fast forward upon
rewindDTMF digit to rewind upon
msHow many milliseconds to skip forward/back
cbto call when rewind or fastforward occurs. Begins playback of a stream... Wait for a stream to stop or for any one of a given digit to arrive,
Return values
0if the stream finishes.
characterif it was interrupted,
Returns
the value of the control frame if it was interrupted by some other party,
Return values
-1on error.

Definition at line 1798 of file file.c.

1804{
1805 return waitstream_core(c, breakon, forward, reverse, ms,
1806 -1 /* no audiofd */, -1 /* no cmdfd */, NULL /* no context */, cb);
1807}

References c, NULL, and waitstream_core().

Referenced by control_streamfile().

◆ ast_waitstream_full()

int ast_waitstream_full ( struct ast_channel c,
const char *  breakon,
int  audiofd,
int  monfd 
)

◆ ast_writefile()

struct ast_filestream * ast_writefile ( const char *  filename,
const char *  type,
const char *  comment,
int  flags,
int  check,
mode_t  mode 
)

Starts writing a file.

Parameters
filenamethe name of the file to write to
typeformat of file you wish to write out to
commentcomment to go with
flagsoutput file flags
check(unimplemented, hence negligible)
modeOpen mode Create an outgoing file stream. oflags are flags for the open() command, and if check is non-zero, then it will not write a file if there are any files that start with that name and have an extension Please note, this is a blocking function. Program execution will not return until ast_waitstream completes it's execution.
Returns
a struct ast_filestream on success.
Return values
NULLon failure.

Definition at line 1423 of file file.c.

1424{
1425 int fd, myflags = 0;
1426 /* compiler claims this variable can be used before initialization... */
1427 FILE *bfile = NULL;
1428 struct ast_format_def *f;
1429 struct ast_filestream *fs = NULL;
1430 char *buf = NULL;
1431 size_t size = 0;
1432 int format_found = 0;
1433
1435
1436 /* set the O_TRUNC flag if and only if there is no O_APPEND specified */
1437 /* We really can't use O_APPEND as it will break WAV header updates */
1438 if (flags & O_APPEND) {
1439 flags &= ~O_APPEND;
1440 } else {
1441 myflags = O_TRUNC;
1442 }
1443
1444 myflags |= O_WRONLY | O_CREAT;
1445
1446 /* XXX need to fix this - we should just do the fopen,
1447 * not open followed by fdopen()
1448 */
1449 AST_RWLIST_TRAVERSE(&formats, f, list) {
1450 char *fn, *orig_fn = NULL;
1451 if (fs)
1452 break;
1453
1454 if (!exts_compare(f->exts, type))
1455 continue;
1456 else
1457 format_found = 1;
1458
1460 if (!fn) {
1461 continue;
1462 }
1463 fd = open(fn, flags | myflags, mode);
1464 if (fd > -1) {
1465 /* fdopen() the resulting file stream */
1466 bfile = fdopen(fd, ((flags | myflags) & O_RDWR) ? "w+" : "w");
1467 if (!bfile) {
1468 ast_log(LOG_WARNING, "Whoa, fdopen failed: %s!\n", strerror(errno));
1469 close(fd);
1470 fd = -1;
1471 }
1472 }
1473
1474 if (ast_opt_cache_record_files && (fd > -1)) {
1475 char *c;
1476
1477 fclose(bfile); /* this also closes fd */
1478 /*
1479 We touch orig_fn just as a place-holder so other things (like vmail) see the file is there.
1480 What we are really doing is writing to record_cache_dir until we are done then we will mv the file into place.
1481 */
1482 orig_fn = ast_strdup(fn);
1483 for (c = fn; *c; c++)
1484 if (*c == '/')
1485 *c = '_';
1486
1487 size = strlen(fn) + strlen(record_cache_dir) + 2;
1488 buf = ast_malloc(size);
1489 strcpy(buf, record_cache_dir);
1490 strcat(buf, "/");
1491 strcat(buf, fn);
1492 ast_free(fn);
1493 fn = buf;
1494 fd = open(fn, flags | myflags, mode);
1495 if (fd > -1) {
1496 /* fdopen() the resulting file stream */
1497 bfile = fdopen(fd, ((flags | myflags) & O_RDWR) ? "w+" : "w");
1498 if (!bfile) {
1499 ast_log(LOG_WARNING, "Whoa, fdopen failed: %s!\n", strerror(errno));
1500 close(fd);
1501 fd = -1;
1502 }
1503 }
1504 }
1505 if (fd > -1) {
1506 errno = 0;
1507 fs = get_filestream(f, bfile);
1508 if (fs) {
1509 if ((fs->write_buffer = ast_malloc(32768))) {
1510 setvbuf(fs->f, fs->write_buffer, _IOFBF, 32768);
1511 }
1512 }
1513 if (!fs || rewrite_wrapper(fs, comment)) {
1514 ast_log(LOG_WARNING, "Unable to rewrite %s\n", fn);
1515 close(fd);
1516 if (orig_fn) {
1517 unlink(fn);
1518 unlink(orig_fn);
1519 ast_free(orig_fn);
1520 }
1521 if (fs) {
1522 ast_closestream(fs);
1523 fs = NULL;
1524 }
1525 /*
1526 * 'fn' was has either been allocated from build_filename, or that was freed
1527 * and now 'fn' points to memory allocated for 'buf'. Either way the memory
1528 * now needs to be released.
1529 */
1530 ast_free(fn);
1531 continue;
1532 }
1533 fs->trans = NULL;
1534 fs->fmt = f;
1535 fs->flags = flags;
1536 fs->mode = mode;
1537 if (orig_fn) {
1538 fs->realfilename = orig_fn;
1539 fs->filename = fn;
1540 /*
1541 * The above now manages the memory allocated for 'orig_fn' and 'fn', so
1542 * set them to NULL, so they don't get released at the end of the loop.
1543 */
1544 orig_fn = NULL;
1545 fn = NULL;
1546 } else {
1547 fs->realfilename = NULL;
1549 }
1550 fs->vfs = NULL;
1551 /* If truncated, we'll be at the beginning; if not truncated, then append */
1552 f->seek(fs, 0, SEEK_END);
1553 } else if (errno != EEXIST) {
1554 ast_log(LOG_WARNING, "Unable to open file %s: %s\n", fn, strerror(errno));
1555 if (orig_fn)
1556 unlink(orig_fn);
1557 }
1558 /* Free 'fn', or if 'fn' points to 'buf' then free 'buf' */
1559 ast_free(fn);
1560 ast_free(orig_fn);
1561 }
1562
1564
1565 if (!format_found)
1566 ast_log(LOG_WARNING, "No such format '%s'\n", type);
1567
1568 return fs;
1569}
#define comment
Definition: ael_lex.c:965
static int rewrite_wrapper(struct ast_filestream *s, const char *comment)
Definition: file.c:520
char record_cache_dir[AST_CACHE_DIR_LEN]
Definition: options.c:96
#define ast_opt_cache_record_files
Definition: options.h:120
char * realfilename
Definition: mod_format.h:108
char * write_buffer
Definition: mod_format.h:126

References ast_closestream(), ast_free, ast_log, ast_malloc, ast_opt_cache_record_files, AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_strdup, buf, build_filename(), c, comment, errno, exts_compare, ast_filestream::f, ast_filestream::filename, ast_filestream::flags, ast_filestream::fmt, get_filestream(), LOG_WARNING, ast_filestream::mode, NULL, ast_filestream::realfilename, record_cache_dir, rewrite_wrapper(), ast_filestream::trans, type, ast_filestream::vfs, and ast_filestream::write_buffer.

Referenced by __ast_play_and_record(), ast_writestream(), dictate_exec(), handle_cli_file_convert(), handle_recordfile(), mixmonitor_save_prep(), record_exec(), and recordthread().

◆ ast_writestream()

int ast_writestream ( struct ast_filestream fs,
struct ast_frame f 
)

Writes a frame to a stream.

Parameters
fsfilestream to write to
fframe to write to the filestream Send a frame to a filestream – note: does NOT free the frame, call ast_frfree manually
Return values
0on success.
-1on failure.

Definition at line 244 of file file.c.

245{
246 int res = -1;
247 if (f->frametype == AST_FRAME_VIDEO) {
249 /* This is the audio portion. Call the video one... */
250 if (!fs->vfs && fs->filename) {
251 const char *type = ast_format_get_name(f->subclass.format);
252 fs->vfs = ast_writefile(fs->filename, type, NULL, fs->flags, 0, fs->mode);
253 ast_debug(1, "Opened video output file\n");
254 }
255 if (fs->vfs)
256 return ast_writestream(fs->vfs, f);
257 /* else ignore */
258 return 0;
259 }
260 } else if (f->frametype != AST_FRAME_VOICE) {
261 ast_log(LOG_WARNING, "Tried to write non-voice frame\n");
262 return -1;
263 }
265 res = fs->fmt->write(fs, f);
266 if (res < 0)
267 ast_log(LOG_WARNING, "Natural write failed\n");
268 else if (res > 0)
269 ast_log(LOG_WARNING, "Huh??\n");
270 } else {
271 /* XXX If they try to send us a type of frame that isn't the normal frame, and isn't
272 the one we've setup a translator for, we do the "wrong thing" XXX */
275 fs->trans = NULL;
276 }
277 if (!fs->trans) {
279 }
280 if (!fs->trans) {
281 ast_log(LOG_WARNING, "Unable to translate to format %s, source format %s\n",
283 } else {
284 struct ast_frame *trf;
286 /* Get the translated frame but don't consume the original in case they're using it on another stream */
287 if ((trf = ast_translate(fs->trans, f, 0))) {
288 struct ast_frame *cur;
289
290 /* the translator may have returned multiple frames, so process them */
291 for (cur = trf; cur; cur = AST_LIST_NEXT(cur, frame_list)) {
292 if ((res = fs->fmt->write(fs, trf))) {
293 ast_log(LOG_WARNING, "Translated frame write failed\n");
294 break;
295 }
296 }
297 ast_frfree(trf);
298 } else {
299 res = 0;
300 }
301 }
302 }
303 return res;
304}
#define ao2_replace(dst, src)
Replace one object reference with another cleaning up the original.
Definition: astobj2.h:501
int ast_writestream(struct ast_filestream *fs, struct ast_frame *f)
Writes a frame to a stream.
Definition: file.c:244
struct ast_filestream * ast_writefile(const char *filename, const char *type, const char *comment, int flags, int check, mode_t mode)
Starts writing a file.
Definition: file.c:1423
enum ast_format_cmp_res ast_format_cmp(const struct ast_format *format1, const struct ast_format *format2)
Compare two formats.
Definition: format.c:201
@ AST_FORMAT_CMP_EQUAL
Definition: format.h:36
@ AST_FORMAT_CMP_NOT_EQUAL
Definition: format.h:38
@ AST_FRAME_VIDEO
@ AST_FRAME_VOICE
#define AST_LIST_NEXT(elm, field)
Returns the next entry in the list after the given entry.
Definition: linkedlists.h:439
struct ast_format * lastwriteformat
Definition: mod_format.h:114
int(* write)(struct ast_filestream *, struct ast_frame *)
Definition: mod_format.h:66
struct ast_format * format
struct ast_frame_subclass subclass
enum ast_frame_type frametype
struct ast_frame * ast_translate(struct ast_trans_pvt *tr, struct ast_frame *f, int consume)
translates one or more frames Apply an input frame into the translator and receive zero or one output...
Definition: translate.c:566
void ast_translator_free_path(struct ast_trans_pvt *tr)
Frees a translator path Frees the given translator path structure.
Definition: translate.c:476
struct ast_trans_pvt * ast_translator_build_path(struct ast_format *dest, struct ast_format *source)
Builds a translator path Build a path (possibly NULL) from source to dest.
Definition: translate.c:486

References ao2_replace, ast_debug, ast_format_cmp(), AST_FORMAT_CMP_EQUAL, AST_FORMAT_CMP_NOT_EQUAL, ast_format_get_name(), ast_format_get_type(), AST_FRAME_VIDEO, AST_FRAME_VOICE, ast_frfree, AST_LIST_NEXT, ast_log, AST_MEDIA_TYPE_AUDIO, ast_translate(), ast_translator_build_path(), ast_translator_free_path(), ast_writefile(), ast_writestream(), ast_filestream::filename, ast_filestream::flags, ast_filestream::fmt, ast_frame_subclass::format, ast_format_def::format, ast_frame::frametype, ast_filestream::lastwriteformat, LOG_WARNING, ast_filestream::mode, ast_format_def::name, NULL, ast_frame::subclass, ast_filestream::trans, type, ast_filestream::vfs, and ast_format_def::write.

Referenced by __ast_play_and_record(), ast_writestream(), dictate_exec(), handle_cli_file_convert(), handle_recordfile(), mixmonitor_thread(), record_exec(), and recordthread().

◆ build_filename()

static char * build_filename ( const char *  filename,
const char *  ext 
)
static

construct a filename. Absolute pathnames are preserved, relative names are prefixed by the sounds/ directory. The wav49 suffix is replaced by 'WAV'. Returns a malloc'ed string to be freed by the caller.

Definition at line 349 of file file.c.

350{
351 char *fn = NULL;
352
353 /* The wav49 -> WAV translation is duplicated in apps/app_mixmonitor.c, so
354 if you change it here you need to change it there as well */
355 if (!strcmp(ext, "wav49"))
356 ext = "WAV";
357
358 if (filename[0] == '/') {
359 if (ast_asprintf(&fn, "%s.%s", filename, ext) < 0) {
360 fn = NULL;
361 }
362 } else {
363 if (ast_asprintf(&fn, "%s/sounds/%s.%s",
364 ast_config_AST_DATA_DIR, filename, ext) < 0) {
365 fn = NULL;
366 }
367 }
368 return fn;
369}
const char * ext
Definition: http.c:150
const char * ast_config_AST_DATA_DIR
Definition: options.c:158

References ast_asprintf, ast_config_AST_DATA_DIR, ext, and NULL.

Referenced by ast_readfile(), ast_writefile(), and filehelper().

◆ copy()

static int copy ( const char *  infile,
const char *  outfile 
)
static

Definition at line 306 of file file.c.

307{
308 int ifd, ofd, len;
309 char buf[4096]; /* XXX make it larger. */
310
311 if ((ifd = open(infile, O_RDONLY)) < 0) {
312 ast_log(LOG_WARNING, "Unable to open %s in read-only mode\n", infile);
313 return -1;
314 }
315 if ((ofd = open(outfile, O_WRONLY | O_TRUNC | O_CREAT, AST_FILE_MODE)) < 0) {
316 ast_log(LOG_WARNING, "Unable to open %s in write-only mode\n", outfile);
317 close(ifd);
318 return -1;
319 }
320 while ( (len = read(ifd, buf, sizeof(buf)) ) ) {
321 int res;
322 if (len < 0) {
323 ast_log(LOG_WARNING, "Read failed on %s: %s\n", infile, strerror(errno));
324 break;
325 }
326 /* XXX handle partial writes */
327 res = write(ofd, buf, len);
328 if (res != len) {
329 ast_log(LOG_WARNING, "Write failed on %s (%d of %d): %s\n", outfile, res, len, strerror(errno));
330 len = -1; /* error marker */
331 break;
332 }
333 }
334 close(ifd);
335 close(ofd);
336 if (len < 0) {
337 unlink(outfile);
338 return -1; /* error */
339 }
340 return 0; /* success */
341}
#define AST_FILE_MODE
Definition: asterisk.h:32

References AST_FILE_MODE, ast_log, buf, errno, len(), and LOG_WARNING.

Referenced by filehelper().

◆ file_shutdown()

static void file_shutdown ( void  )
static

Definition at line 2044 of file file.c.

2045{
2049}
int ast_cli_unregister_multiple(struct ast_cli_entry *e, int len)
Unregister multiple commands.
Definition: clicompat.c:30
#define STASIS_MESSAGE_TYPE_CLEANUP(name)
Boiler-plate messaging macro for cleaning up message types.
Definition: stasis.h:1515

References ARRAY_LEN, ast_cli_unregister_multiple(), ast_format_register_type(), ast_format_unregister_type(), cli_file, and STASIS_MESSAGE_TYPE_CLEANUP.

Referenced by ast_file_init().

◆ fileexists_core()

static int fileexists_core ( const char *  filename,
const char *  fmt,
const char *  preflang,
char *  buf,
int  buflen,
struct ast_format_cap result_cap 
)
static

helper routine to locate a file with a given format and language preference.

Note
Try preflang, preflang with stripped '_' suffices, or NULL.
The last parameter(s) point to a buffer of sufficient size, which on success is filled with the matching filename.
Parameters
filenameName of the file.
fmtFormat to look for the file in. OPTIONAL
preflangThe perfered language
bufReturns the matching filename
buflenSize of the buf
result_capOPTIONAL format capabilities result structure returns what formats the file was found in.
Return values
1true. file exists and result format is set
0false. file does not exist.

Definition at line 741 of file file.c.

743{
744 char *lang;
745
746 if (buf == NULL) {
747 return 0;
748 }
749
750 /* We try languages in the following order:
751 * preflang (may include dialect and style codes)
752 * lang (preflang without dialect - if any)
753 * <none>
754 * default (unless the same as preflang or lang without dialect)
755 */
756
757 lang = ast_strdupa(preflang);
758
759 /* Try preferred language, including removing any style or dialect codes */
760 while (!ast_strlen_zero(lang)) {
761 char *end;
762
763 if (fileexists_test(filename, fmt, lang, buf, buflen, result_cap)) {
764 return 1;
765 }
766
767 if ((end = strrchr(lang, '_')) != NULL) {
768 *end = '\0';
769 continue;
770 }
771
772 break;
773 }
774
775 /* Try without any language */
776 if (fileexists_test(filename, fmt, NULL, buf, buflen, result_cap)) {
777 return 1;
778 }
779
780 /* Finally try the default language unless it was already tried before */
781 if ((ast_strlen_zero(preflang) || strcmp(preflang, DEFAULT_LANGUAGE)) && (ast_strlen_zero(lang) || strcmp(lang, DEFAULT_LANGUAGE))) {
782 if ((fileexists_test(filename, fmt, DEFAULT_LANGUAGE, buf, buflen, result_cap)) > 0) {
783 return 1;
784 }
785 }
786
787 return 0;
788}
#define DEFAULT_LANGUAGE
Definition: asterisk.h:46
char * end
Definition: eagi_proxy.c:73
static int fileexists_test(const char *filename, const char *fmt, const char *lang, char *buf, int buflen, struct ast_format_cap *result_cap)
test if a file exists for a given format.
Definition: file.c:691

References ast_strdupa, ast_strlen_zero(), buf, DEFAULT_LANGUAGE, end, fileexists_test(), ast_filestream::filename, ast_filestream::fmt, and NULL.

Referenced by ast_fileexists(), ast_openstream_full(), and ast_openvstream().

◆ fileexists_test()

static int fileexists_test ( const char *  filename,
const char *  fmt,
const char *  lang,
char *  buf,
int  buflen,
struct ast_format_cap result_cap 
)
static

test if a file exists for a given format.

Note
result_cap is OPTIONAL
Return values
1true and result_cap represents format capabilities file exists in.
0false

Definition at line 691 of file file.c.

693{
694 if (buf == NULL) {
695 return 0;
696 }
697
698 if (is_remote_path(filename) && !ast_media_cache_retrieve(filename, NULL, buf, buflen)) {
699 return filehelper(buf, result_cap, NULL, ACTION_EXISTS);
700 }
701
702 if (ast_language_is_prefix && !is_absolute_path(filename)) { /* new layout */
703 if (lang) {
704 snprintf(buf, buflen, "%s/%s", lang, filename);
705 } else {
706 snprintf(buf, buflen, "%s", filename);
707 }
708 } else { /* old layout */
709 strcpy(buf, filename); /* first copy the full string */
710 if (lang) {
711 /* insert the language and suffix if needed */
712 const char *c = strrchr(filename, '/');
713 int offset = c ? c - filename + 1 : 0; /* points right after the last '/' */
714 snprintf(buf + offset, buflen - offset, "%s/%s", lang, filename + offset);
715 }
716 }
717
718 return filehelper(buf, result_cap, fmt, ACTION_EXISTS);
719}
int ast_language_is_prefix
The following variable controls the layout of localized sound files. If 0, use the historical layout ...
Definition: file.c:67
static int is_remote_path(const char *filename)
Definition: file.c:680
int ast_media_cache_retrieve(const char *uri, const char *preferred_file_name, char *file_path, size_t len)
Retrieve an item from the cache.
Definition: media_cache.c:157

References ACTION_EXISTS, ast_language_is_prefix, ast_media_cache_retrieve(), buf, c, filehelper(), ast_filestream::filename, ast_filestream::fmt, is_absolute_path(), is_remote_path(), and NULL.

Referenced by fileexists_core().

◆ filehelper()

static int filehelper ( const char *  filename,
const void *  arg2,
const char *  fmt,
const enum file_action  action 
)
static

Definition at line 549 of file file.c.

550{
551 struct ast_format_def *f;
552 int res = (action == ACTION_EXISTS) ? 0 : -1;
553
555 /* Check for a specific format */
557 char *ext = NULL;
558 char storage[strlen(f->exts) + 1];
559 char *stringp;
560
561 if (fmt && !exts_compare(f->exts, fmt))
562 continue;
563
564 /* Look for a file matching the supported extensions.
565 * The file must exist, and for OPEN, must match
566 * one of the formats supported by the channel.
567 */
568 strcpy(storage, f->exts); /* safe - this is in the stack so does not need to be freed */
569 stringp = storage;
570 while ( (ext = strsep(&stringp, "|")) ) {
571 struct stat st;
572 char *fn = build_filename(filename, ext);
573
574 if (fn == NULL)
575 continue;
576
577 if ( stat(fn, &st) ) { /* file not existent */
578 ast_free(fn);
579 continue;
580 }
581 /* for 'OPEN' we need to be sure that the format matches
582 * what the channel can process
583 */
584 if (action == ACTION_OPEN) {
585 struct ast_channel *chan = (struct ast_channel *)arg2;
586 FILE *bfile;
587 struct ast_filestream *s;
588
590 !(((ast_format_get_type(f->format) == AST_MEDIA_TYPE_AUDIO) && fmt) ||
591 ((ast_format_get_type(f->format) == AST_MEDIA_TYPE_VIDEO) && fmt))) {
592 ast_free(fn);
593 continue; /* not a supported format */
594 }
595 if ( (bfile = fopen(fn, "r")) == NULL) {
596 ast_free(fn);
597 continue; /* cannot open file */
598 }
599 s = get_filestream(f, bfile);
600 if (!s) {
601 fclose(bfile);
602 ast_free(fn); /* cannot allocate descriptor */
603 continue;
604 }
605 if (open_wrapper(s)) {
606 ast_free(fn);
608 continue; /* cannot run open on file */
609 }
610 if (st.st_size == 0) {
611 ast_log(LOG_WARNING, "File %s detected to have zero size.\n", fn);
612 }
613 /* ok this is good for OPEN */
614 res = 1; /* found */
615 s->lasttimeout = -1;
616 s->fmt = f;
617 s->trans = NULL;
618 s->filename = NULL;
620 if (ast_channel_stream(chan))
622 ast_channel_stream_set(chan, s);
623 } else {
624 if (ast_channel_vstream(chan))
627 }
628 ast_free(fn);
629 break;
630 }
631 switch (action) {
632 case ACTION_OPEN:
633 break; /* will never get here */
634
635 case ACTION_EXISTS: /* return the matching format */
636 /* if arg2 is present, it is a format capabilities structure.
637 * Add this format to the set of formats this file can be played in */
638 if (arg2) {
639 ast_format_cap_append((struct ast_format_cap *) arg2, f->format, 0);
640 }
641 res = 1; /* file does exist and format it exists in is returned in arg2 */
642 break;
643
644 case ACTION_DELETE:
645 if ( (res = unlink(fn)) )
646 ast_log(LOG_WARNING, "unlink(%s) failed: %s\n", fn, strerror(errno));
647 break;
648
649 case ACTION_RENAME:
650 case ACTION_COPY: {
651 char *nfn = build_filename((const char *)arg2, ext);
652 if (!nfn)
653 ast_log(LOG_WARNING, "Out of memory\n");
654 else {
655 res = action == ACTION_COPY ? copy(fn, nfn) : rename(fn, nfn);
656 if (res)
657 ast_log(LOG_WARNING, "%s(%s,%s) failed: %s\n",
658 action == ACTION_COPY ? "copy" : "rename",
659 fn, nfn, strerror(errno));
660 ast_free(nfn);
661 }
662 }
663 break;
664
665 default:
666 ast_log(LOG_WARNING, "Unknown helper %u\n", action);
667 }
668 ast_free(fn);
669 }
670 }
672 return res;
673}
static int copy(const char *infile, const char *outfile)
Definition: file.c:306
#define ast_format_cap_append(cap, format, framing)
Add format capability to capabilities structure.
Definition: format_cap.h:99
Main Channel structure associated with a channel.

References ACTION_COPY, ACTION_DELETE, ACTION_EXISTS, ACTION_OPEN, ACTION_RENAME, ast_channel_stream(), ast_channel_stream_set(), ast_channel_vstream(), ast_channel_vstream_set(), ast_channel_writeformat(), ast_closestream(), ast_format_cap_append, ast_format_cmp(), AST_FORMAT_CMP_NOT_EQUAL, ast_format_get_type(), ast_free, ast_log, AST_MEDIA_TYPE_AUDIO, AST_MEDIA_TYPE_VIDEO, AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, build_filename(), copy(), errno, ext, ast_format_def::exts, exts_compare, ast_filestream::f, ast_filestream::filename, ast_filestream::fmt, ast_format_def::format, get_filestream(), ast_filestream::lasttimeout, ast_format_def::list, LOG_WARNING, NULL, open_wrapper(), strsep(), and ast_filestream::trans.

Referenced by ast_filecopy(), ast_filedelete(), ast_filerename(), ast_openstream_full(), ast_openvstream(), and fileexists_test().

◆ filestream_close()

static void filestream_close ( struct ast_filestream f)
static

Definition at line 392 of file file.c.

393{
394 enum ast_media_type format_type = ast_format_get_type(f->fmt->format);
395
396 if (!f->owner) {
397 return;
398 }
399
400 /* Stop a running stream if there is one */
401 switch (format_type)
402 {
406 ast_settimeout(f->owner, 0, NULL, NULL);
407 break;
411 break;
412 default:
413 ast_log(AST_LOG_WARNING, "Unable to schedule deletion of filestream with unsupported type %s\n", f->fmt->name);
414 break;
415 }
416}
int ast_channel_vstreamid(const struct ast_channel *chan)
int ast_channel_streamid(const struct ast_channel *chan)
ast_media_type
Types of media.
Definition: codec.h:30
#define AST_LOG_WARNING
#define AST_SCHED_DEL_ACCESSOR(sched, obj, getter, setter)
Definition: sched.h:59

References ast_channel_sched(), ast_channel_stream_set(), ast_channel_streamid(), ast_channel_streamid_set(), ast_channel_vstream_set(), ast_channel_vstreamid(), ast_channel_vstreamid_set(), ast_format_get_type(), ast_log, AST_LOG_WARNING, AST_MEDIA_TYPE_AUDIO, AST_MEDIA_TYPE_VIDEO, AST_SCHED_DEL_ACCESSOR, ast_settimeout(), ast_filestream::fmt, ast_format_def::format, ast_format_def::name, NULL, and ast_filestream::owner.

Referenced by ast_closestream(), and filestream_destructor().

◆ filestream_destructor()

static void filestream_destructor ( void *  arg)
static

Definition at line 418 of file file.c.

419{
420 struct ast_filestream *f = arg;
421 int status;
422 int pid = -1;
423
424 /* Stop a running stream if there is one */
426
427 /* destroy the translator on exit */
428 if (f->trans)
430
431 if (f->fmt->close) {
432 void (*closefn)(struct ast_filestream *) = f->fmt->close;
433 closefn(f);
434 }
435
436 if (f->f) {
437 fclose(f->f);
438 }
439
440 if (f->realfilename && f->filename) {
441 pid = ast_safe_fork(0);
442 if (!pid) {
443 execl("/bin/mv", "mv", "-f", f->filename, f->realfilename, SENTINEL);
444 _exit(1);
445 }
446 else if (pid > 0) {
447 /* Block the parent until the move is complete.*/
448 waitpid(pid, &status, 0);
449 }
450 }
451
452 ast_free(f->filename);
453 ast_free(f->realfilename);
454 if (f->vfs)
455 ast_closestream(f->vfs);
456 ast_free(f->write_buffer);
457 ast_free((void *)f->orig_chan_name);
458 ao2_cleanup(f->lastwriteformat);
459 ao2_cleanup(f->fr.subclass.format);
460 ast_module_unref(f->fmt->module);
461}
jack_status_t status
Definition: app_jack.c:146
#define SENTINEL
Definition: compiler.h:87
int ast_safe_fork(int stop_reaper)
Common routine to safely fork without a chance of a signal handler firing badly in the child.
Definition: main/app.c:3197
#define ast_module_unref(mod)
Release a reference to the module.
Definition: module.h:469

References ao2_cleanup, ast_closestream(), ast_free, ast_module_unref, ast_safe_fork(), ast_translator_free_path(), ast_filestream::f, filestream_close(), SENTINEL, and status.

Referenced by get_filestream().

◆ fn_wrapper()

static int fn_wrapper ( struct ast_filestream s,
const char *  comment,
enum wrap_fn  mode 
)
static

Definition at line 503 of file file.c.

504{
505 struct ast_format_def *f = s->fmt;
506 int ret = -1;
507 int (*openfn)(struct ast_filestream *s);
508
509 if (mode == WRAP_OPEN && (openfn = f->open) && openfn(s))
510 ast_log(LOG_WARNING, "Unable to open format %s\n", f->name);
511 else if (mode == WRAP_REWRITE && f->rewrite && f->rewrite(s, comment))
512 ast_log(LOG_WARNING, "Unable to rewrite format %s\n", f->name);
513 else {
514 /* preliminary checks succeed. */
515 ret = 0;
516 }
517 return ret;
518}

References ast_log, comment, ast_filestream::f, ast_filestream::fmt, LOG_WARNING, ast_filestream::mode, WRAP_OPEN, and WRAP_REWRITE.

Referenced by open_wrapper(), and rewrite_wrapper().

◆ get_filestream()

static struct ast_filestream * get_filestream ( struct ast_format_def fmt,
FILE *  bfile 
)
static

Definition at line 463 of file file.c.

464{
465 struct ast_filestream *s;
466 int l = sizeof(*s) + fmt->buf_size + fmt->desc_size; /* total allocation size */
467
469 return NULL;
470 }
471
473 if (!s) {
475 return NULL;
476 }
477 s->fmt = fmt;
478 s->f = bfile;
479
480 if (fmt->desc_size)
481 s->_private = ((char *)(s + 1)) + fmt->buf_size;
482 if (fmt->buf_size)
483 s->buf = (char *)(s + 1);
484 s->fr.src = fmt->name;
485
490 }
491 s->fr.mallocd = 0;
493
494 return s;
495}
if(!yyg->yy_init)
Definition: ast_expr2f.c:854
#define ao2_alloc(data_size, destructor_fn)
Definition: astobj2.h:409
static void filestream_destructor(void *arg)
Definition: file.c:418
#define ast_module_running_ref(mod)
Hold a reference to the module if it is running.
Definition: module.h:455
struct ast_frame fr
frame produced by read, typically
Definition: mod_format.h:122
void * _private
Definition: mod_format.h:124
struct ast_module * module
Definition: mod_format.h:93
const char * src

References ast_filestream::_private, ao2_alloc, ao2_bump, ast_format_get_type(), AST_FRAME_VIDEO, AST_FRAME_VOICE, AST_MEDIA_TYPE_AUDIO, AST_MEDIA_TYPE_VIDEO, ast_module_running_ref, ast_module_unref, ast_filestream::buf, ast_format_def::buf_size, ast_format_def::desc_size, ast_filestream::f, filestream_destructor(), ast_filestream::fmt, ast_frame_subclass::format, ast_format_def::format, ast_filestream::fr, ast_frame::frametype, if(), ast_frame::mallocd, ast_format_def::module, ast_format_def::name, NULL, ast_frame::src, and ast_frame::subclass.

Referenced by ast_readfile(), ast_writefile(), and filehelper().

◆ handle_cli_core_show_file_formats()

static char * handle_cli_core_show_file_formats ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
)
static

Definition at line 1970 of file file.c.

1971{
1972#define FORMAT "%-10s %-10s %-20s\n"
1973#define FORMAT2 "%-10s %-10s %-20s\n"
1974 struct ast_format_def *f;
1975 int count_fmt = 0;
1976
1977 switch (cmd) {
1978 case CLI_INIT:
1979 e->command = "core show file formats";
1980 e->usage =
1981 "Usage: core show file formats\n"
1982 " Displays currently registered file formats (if any).\n";
1983 return NULL;
1984 case CLI_GENERATE:
1985 return NULL;
1986 }
1987
1988 if (a->argc != 4)
1989 return CLI_SHOWUSAGE;
1990
1991 ast_cli(a->fd, FORMAT, "Format", "Name", "Extensions");
1992 ast_cli(a->fd, FORMAT, "------", "----", "----------");
1993
1996 ast_cli(a->fd, FORMAT2, ast_format_get_name(f->format), f->name, f->exts);
1997 count_fmt++;
1998 }
2000 ast_cli(a->fd, "%d file formats registered.\n", count_fmt);
2001 return CLI_SUCCESS;
2002#undef FORMAT
2003#undef FORMAT2
2004}
#define CLI_SHOWUSAGE
Definition: cli.h:45
#define CLI_SUCCESS
Definition: cli.h:44
void ast_cli(int fd, const char *fmt,...)
Definition: clicompat.c:6
@ CLI_INIT
Definition: cli.h:152
@ CLI_GENERATE
Definition: cli.h:153
#define FORMAT
#define FORMAT2
char * command
Definition: cli.h:186
const char * usage
Definition: cli.h:177

References a, ast_cli(), ast_format_get_name(), AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_format_def::exts, ast_format_def::format, FORMAT, FORMAT2, ast_format_def::list, ast_format_def::name, NULL, and ast_cli_entry::usage.

◆ is_absolute_path()

static int is_absolute_path ( const char *  filename)
static

Definition at line 675 of file file.c.

676{
677 return filename[0] == '/';
678}

References ast_filestream::filename.

Referenced by ast_streamfile(), and fileexists_test().

◆ is_remote_path()

static int is_remote_path ( const char *  filename)
static

Definition at line 680 of file file.c.

681{
682 return strstr(filename, "://") ? 1 : 0;
683}

References ast_filestream::filename.

Referenced by fileexists_test().

◆ json_array_from_list()

static struct ast_json * json_array_from_list ( const char *  list,
const char *  sep 
)
static

Definition at line 74 of file file.c.

75{
77 char *stringp, *ext;
78
79 stringp = ast_strdupa(list); /* this is in the stack so does not need to be freed */
80 if (!array || !stringp) {
81 return NULL;
82 }
83
84 while ((ext = strsep(&stringp, sep))) {
86 return NULL;
87 }
88 }
89
90 return ast_json_ref(array);
91}
static int array(struct ast_channel *chan, const char *cmd, char *var, const char *value)
struct ast_json * ast_json_string_create(const char *value)
Construct a JSON string from value.
Definition: json.c:278
void ast_json_unref(struct ast_json *value)
Decrease refcount on value. If refcount reaches zero, value is freed.
Definition: json.c:73
int ast_json_array_append(struct ast_json *array, struct ast_json *value)
Append to an array.
Definition: json.c:378
struct ast_json * ast_json_array_create(void)
Create a empty JSON array.
Definition: json.c:362
struct ast_json * ast_json_ref(struct ast_json *value)
Increase refcount on value.
Definition: json.c:67
Abstract JSON element (object, array, string, int, ...).

References array(), ast_json_array_append(), ast_json_array_create(), ast_json_ref(), ast_json_string_create(), ast_json_unref(), ast_strdupa, ext, NULL, RAII_VAR, and strsep().

Referenced by publish_format_update().

◆ open_wrapper()

static int open_wrapper ( struct ast_filestream s)
static

Definition at line 525 of file file.c.

526{
527 return fn_wrapper(s, NULL, WRAP_OPEN);
528}
static int fn_wrapper(struct ast_filestream *s, const char *comment, enum wrap_fn mode)
Definition: file.c:503

References fn_wrapper(), NULL, and WRAP_OPEN.

Referenced by ast_readfile(), and filehelper().

◆ publish_format_update()

static int publish_format_update ( const struct ast_format_def f,
struct stasis_message_type type 
)
static

Definition at line 93 of file file.c.

94{
95 RAII_VAR(struct stasis_message *, msg, NULL, ao2_cleanup);
96 RAII_VAR(struct ast_json_payload *, json_payload, NULL, ao2_cleanup);
97 RAII_VAR(struct ast_json *, json_object, NULL, ast_json_unref);
98
99 if (!type) {
100 return -1;
101 }
102
103 json_object = ast_json_pack("{s: s, s: o}",
104 "format", f->name,
105 "extensions", json_array_from_list(f->exts, "|"));
106 if (!json_object) {
107 return -1;
108 }
109
110 json_payload = ast_json_payload_create(json_object);
111 if (!json_payload) {
112 return -1;
113 }
114
115 msg = stasis_message_create(type, json_payload);
116 if (!msg) {
117 return -1;
118 }
119
121 return 0;
122}
static struct ast_json * json_array_from_list(const char *list, const char *sep)
Definition: file.c:74
struct ast_json_payload * ast_json_payload_create(struct ast_json *json)
Create an ao2 object to pass json blobs as data payloads for stasis.
Definition: json.c:756
struct ast_json * ast_json_pack(char const *format,...)
Helper for creating complex JSON values.
Definition: json.c:612
struct stasis_message * stasis_message_create(struct stasis_message_type *type, void *data)
Create a new message.
void stasis_publish(struct stasis_topic *topic, struct stasis_message *message)
Publish a message to a topic's subscribers.
Definition: stasis.c:1511
struct stasis_topic * ast_system_topic(void)
A Stasis Message Bus API topic which publishes messages regarding system changes.

References ao2_cleanup, ast_json_pack(), ast_json_payload_create(), ast_json_unref(), ast_system_topic(), ast_format_def::exts, json_array_from_list(), ast_format_def::name, NULL, RAII_VAR, stasis_message_create(), stasis_publish(), and type.

Referenced by __ast_format_def_register(), and ast_format_def_unregister().

◆ read_frame()

static struct ast_frame * read_frame ( struct ast_filestream s,
int *  whennext 
)
static

Definition at line 911 of file file.c.

912{
913 struct ast_frame *fr, *new_fr;
914
915 if (!s || !s->fmt) {
916 return NULL;
917 }
918
919 if (!(fr = s->fmt->read(s, whennext))) {
920 return NULL;
921 }
922
923 if (!(new_fr = ast_frisolate(fr))) {
924 ast_frfree(fr);
925 return NULL;
926 }
927
928 if (new_fr != fr) {
929 ast_frfree(fr);
930 fr = new_fr;
931 }
932
933 return fr;
934}
#define ast_frisolate(fr)
Makes a frame independent of any static storage.
struct ast_frame *(* read)(struct ast_filestream *, int *whennext)
Definition: mod_format.h:74

References ast_frfree, ast_frisolate, ast_filestream::fmt, NULL, and ast_format_def::read.

Referenced by ast_audiohook_read_frame_all(), ast_readaudio_callback(), ast_readframe(), ast_readvideo_callback(), and audiohook_read_frame_helper().

◆ rewrite_wrapper()

static int rewrite_wrapper ( struct ast_filestream s,
const char *  comment 
)
static

Definition at line 520 of file file.c.

521{
522 return fn_wrapper(s, comment, WRAP_REWRITE);
523}

References comment, fn_wrapper(), and WRAP_REWRITE.

Referenced by ast_writefile().

◆ sanitize_waitstream_return()

static int sanitize_waitstream_return ( int  return_value)
static

Definition at line 1823 of file file.c.

1824{
1825 switch (return_value) {
1829 /* Fall through and set return_value to 0 */
1830 return_value = 0;
1831 break;
1832 default:
1833 /* Do nothing */
1834 break;
1835 }
1836
1837 return return_value;
1838}
@ AST_CONTROL_STREAM_RESTART
@ AST_CONTROL_STREAM_SUSPEND
@ AST_CONTROL_STREAM_STOP

References AST_CONTROL_STREAM_RESTART, AST_CONTROL_STREAM_STOP, and AST_CONTROL_STREAM_SUSPEND.

Referenced by ast_waitstream(), ast_waitstream_exten(), and ast_waitstream_full().

◆ STASIS_MESSAGE_TYPE_DEFN() [1/2]

STASIS_MESSAGE_TYPE_DEFN ( ast_format_register_type  )

◆ STASIS_MESSAGE_TYPE_DEFN() [2/2]

STASIS_MESSAGE_TYPE_DEFN ( ast_format_unregister_type  )

◆ type_in_list()

static int type_in_list ( const char *  list,
const char *  type,
int(*)(const char *s1, const char *s2)  cmp 
)
static

Definition at line 373 of file file.c.

374{
375 char *stringp = ast_strdupa(list), *item;
376
377 while ((item = strsep(&stringp, "|"))) {
378 if (!cmp(item, type)) {
379 return 1;
380 }
381 }
382
383 return 0;
384}
static struct aco_type item
Definition: test_config.c:1463

References ast_strdupa, item, strsep(), and type.

Referenced by ast_get_extension_for_mime_type().

◆ waitstream_control()

static void waitstream_control ( struct ast_channel c,
enum ast_waitstream_fr_cb_values  type,
ast_waitstream_fr_cb  cb,
int  skip_ms 
)
static

Definition at line 1571 of file file.c.

1575{
1576 switch (type)
1577 {
1579 {
1580 int eoftest;
1582 eoftest = fgetc(ast_channel_stream(c)->f);
1583 if (feof(ast_channel_stream(c)->f)) {
1585 } else {
1586 ungetc(eoftest, ast_channel_stream(c)->f);
1587 }
1588 }
1589 break;
1592 break;
1593 default:
1594 break;
1595 }
1596
1597 if (cb) {
1598 long ms_len = ast_tellstream(ast_channel_stream(c)) / (ast_format_get_sample_rate(ast_channel_stream(c)->fmt->format) / 1000);
1599 cb(c, ms_len, type);
1600 }
1601
1602 ast_test_suite_event_notify("PLAYBACK","Channel: %s\r\n"
1603 "Control: %s\r\n"
1604 "SkipMs: %d\r\n",
1606 (type == AST_WAITSTREAM_CB_FASTFORWARD) ? "FastForward" : "Rewind",
1607 skip_ms);
1608}
int ast_stream_rewind(struct ast_filestream *fs, off_t ms)
Rewind stream ms.
Definition: file.c:1100
int ast_stream_fastforward(struct ast_filestream *fs, off_t ms)
Fast forward stream ms.
Definition: file.c:1095
@ AST_WAITSTREAM_CB_FASTFORWARD
Definition: file.h:56
@ AST_WAITSTREAM_CB_REWIND
Definition: file.h:55

References ast_channel_name(), ast_channel_stream(), ast_format_get_sample_rate(), ast_stream_fastforward(), ast_stream_rewind(), ast_tellstream(), ast_test_suite_event_notify, AST_WAITSTREAM_CB_FASTFORWARD, AST_WAITSTREAM_CB_REWIND, c, ast_filestream::f, ast_filestream::fmt, ast_format_def::format, and type.

Referenced by waitstream_core().

◆ waitstream_core()

static int waitstream_core ( struct ast_channel c,
const char *  breakon,
const char *  forward,
const char *  reverse,
int  skip_ms,
int  audiofd,
int  cmdfd,
const char *  context,
ast_waitstream_fr_cb  cb 
)
static

the core of all waitstream() functions

Definition at line 1613 of file file.c.

1622{
1623 const char *orig_chan_name = NULL;
1624
1625 int err = 0;
1626
1627 if (!breakon)
1628 breakon = "";
1629 if (!forward)
1630 forward = "";
1631 if (!reverse)
1632 reverse = "";
1633
1634 /* Switch the channel to end DTMF frame only. waitstream_core doesn't care about the start of DTMF. */
1636
1638 orig_chan_name = ast_strdupa(ast_channel_name(c));
1639
1640 if (ast_channel_stream(c) && cb) {
1641 long ms_len = ast_tellstream(ast_channel_stream(c)) / (ast_format_get_sample_rate(ast_channel_stream(c)->fmt->format) / 1000);
1642 cb(c, ms_len, AST_WAITSTREAM_CB_START);
1643 }
1644
1645 while (ast_channel_stream(c)) {
1646 int res;
1647 int ms;
1648
1649 if (orig_chan_name && strcasecmp(orig_chan_name, ast_channel_name(c))) {
1651 err = 1;
1652 break;
1653 }
1654
1656
1657 if (ms < 0 && !ast_channel_timingfunc(c)) {
1659 break;
1660 }
1661 if (ms < 0)
1662 ms = 1000;
1663 if (cmdfd < 0) {
1664 res = ast_waitfor(c, ms);
1665 if (res < 0) {
1666 ast_log(LOG_WARNING, "Select failed (%s)\n", strerror(errno));
1668 return res;
1669 }
1670 } else {
1671 int outfd;
1672 struct ast_channel *rchan = ast_waitfor_nandfds(&c, 1, &cmdfd, (cmdfd > -1) ? 1 : 0, NULL, &outfd, &ms);
1673 if (!rchan && (outfd < 0) && (ms)) {
1674 /* Continue */
1675 if (errno == EINTR)
1676 continue;
1677 ast_log(LOG_WARNING, "Wait failed (%s)\n", strerror(errno));
1679 return -1;
1680 } else if (outfd > -1) { /* this requires cmdfd set */
1681 /* The FD we were watching has something waiting */
1683 return 1;
1684 }
1685 /* if rchan is set, it is 'c' */
1686 res = rchan ? 1 : 0; /* map into 'res' values */
1687 }
1688 if (res > 0) {
1689 struct ast_frame *fr = ast_read(c);
1690 if (!fr) {
1692 return -1;
1693 }
1694 switch (fr->frametype) {
1695 case AST_FRAME_DTMF_END:
1696 if (context) {
1697 const char exten[2] = { fr->subclass.integer, '\0' };
1698 if (ast_exists_extension(c, context, exten, 1,
1699 S_COR(ast_channel_caller(c)->id.number.valid, ast_channel_caller(c)->id.number.str, NULL))) {
1700 res = fr->subclass.integer;
1701 ast_frfree(fr);
1703 return res;
1704 }
1705 } else {
1706 res = fr->subclass.integer;
1707 if (strchr(forward, res)) {
1709 } else if (strchr(reverse, res)) {
1711 } else if (strchr(breakon, res)) {
1712 ast_test_suite_event_notify("PLAYBACK","Channel: %s\r\n"
1713 "Control: %s\r\n",
1715 "Break");
1716
1717 ast_frfree(fr);
1719 return res;
1720 }
1721 }
1722 break;
1723 case AST_FRAME_CONTROL:
1724 switch (fr->subclass.integer) {
1728 /* Fall-through and break out */
1729 ast_test_suite_event_notify("PLAYBACK","Channel: %s\r\n"
1730 "Control: %s\r\n",
1732 "Break");
1733 res = fr->subclass.integer;
1734 ast_frfree(fr);
1736 return res;
1738 if (!skip_ms) {
1739 skip_ms = 3000;
1740 }
1742 break;
1744 if (!skip_ms) {
1745 skip_ms = 3000;
1746 }
1748 break;
1749 case AST_CONTROL_HANGUP:
1750 case AST_CONTROL_BUSY:
1752 ast_frfree(fr);
1754 return -1;
1757 case AST_CONTROL_ANSWER:
1761 case AST_CONTROL_HOLD:
1762 case AST_CONTROL_UNHOLD:
1765 case AST_CONTROL_AOC:
1768 case AST_CONTROL_FLASH:
1769 case AST_CONTROL_WINK:
1770 case -1:
1771 /* Unimportant */
1772 break;
1773 default:
1774 ast_log(LOG_WARNING, "Unexpected control subclass '%d'\n", fr->subclass.integer);
1775 }
1776 break;
1777 case AST_FRAME_VOICE:
1778 /* Write audio if appropriate */
1779 if (audiofd > -1) {
1780 if (write(audiofd, fr->data.ptr, fr->datalen) < 0) {
1781 ast_log(LOG_WARNING, "write() failed: %s\n", strerror(errno));
1782 }
1783 }
1784 default:
1785 /* Ignore all others */
1786 break;
1787 }
1788 ast_frfree(fr);
1789 }
1791 }
1792
1794
1795 return (err || ast_channel_softhangup_internal_flag(c)) ? -1 : 0;
1796}
struct ast_channel * ast_waitfor_nandfds(struct ast_channel **c, int n, int *fds, int nfds, int *exception, int *outfd, int *ms)
Waits for activity on a group of channels.
Definition: channel.c:2988
void ast_channel_clear_flag(struct ast_channel *chan, unsigned int flag)
Clear a flag on a channel.
Definition: channel.c:11034
int ast_waitfor(struct ast_channel *chan, int ms)
Wait for input on a channel.
Definition: channel.c:3162
struct ast_frame * ast_read(struct ast_channel *chan)
Reads a frame.
Definition: channel.c:4257
void ast_channel_set_flag(struct ast_channel *chan, unsigned int flag)
Set a flag on a channel.
Definition: channel.c:11027
ast_timing_func_t ast_channel_timingfunc(const struct ast_channel *chan)
@ AST_FLAG_END_DTMF_ONLY
Definition: channel.h:1007
int ast_channel_softhangup_internal_flag(struct ast_channel *chan)
struct ast_party_caller * ast_channel_caller(struct ast_channel *chan)
static void waitstream_control(struct ast_channel *c, enum ast_waitstream_fr_cb_values type, ast_waitstream_fr_cb cb, int skip_ms)
Definition: file.c:1571
@ AST_WAITSTREAM_CB_START
Definition: file.h:57
@ AST_FRAME_DTMF_END
@ AST_FRAME_CONTROL
@ AST_CONTROL_SRCUPDATE
@ AST_CONTROL_WINK
@ AST_CONTROL_PROGRESS
@ AST_CONTROL_BUSY
@ AST_CONTROL_UNHOLD
@ AST_CONTROL_VIDUPDATE
@ AST_CONTROL_STREAM_REVERSE
@ AST_CONTROL_REDIRECTING
@ AST_CONTROL_CONGESTION
@ AST_CONTROL_ANSWER
@ AST_CONTROL_RINGING
@ AST_CONTROL_HANGUP
@ AST_CONTROL_HOLD
@ AST_CONTROL_CONNECTED_LINE
@ AST_CONTROL_STREAM_FORWARD
@ AST_CONTROL_FLASH
@ AST_CONTROL_AOC
@ AST_CONTROL_SRCCHANGE
@ AST_CONTROL_PVT_CAUSE_CODE
@ AST_CONTROL_UPDATE_RTP_PEER
int ast_exists_extension(struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid)
Determine whether an extension exists.
Definition: pbx.c:4175
int ast_sched_runq(struct ast_sched_context *con)
Runs the queue.
Definition: sched.c:786
int ast_sched_wait(struct ast_sched_context *con) attribute_warn_unused_result
Determines number of seconds until the next outstanding event to take place.
Definition: sched.c:433
#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
union ast_frame::@226 data
Number structure.
Definition: app_followme.c:154

References ast_channel_caller(), ast_channel_clear_flag(), ast_channel_flags(), ast_channel_name(), ast_channel_sched(), ast_channel_set_flag(), ast_channel_softhangup_internal_flag(), ast_channel_stream(), ast_channel_timingfunc(), AST_CONTROL_ANSWER, AST_CONTROL_AOC, AST_CONTROL_BUSY, AST_CONTROL_CONGESTION, AST_CONTROL_CONNECTED_LINE, AST_CONTROL_FLASH, AST_CONTROL_HANGUP, AST_CONTROL_HOLD, AST_CONTROL_PROGRESS, AST_CONTROL_PVT_CAUSE_CODE, AST_CONTROL_REDIRECTING, AST_CONTROL_RINGING, AST_CONTROL_SRCCHANGE, AST_CONTROL_SRCUPDATE, AST_CONTROL_STREAM_FORWARD, AST_CONTROL_STREAM_RESTART, AST_CONTROL_STREAM_REVERSE, AST_CONTROL_STREAM_STOP, AST_CONTROL_STREAM_SUSPEND, AST_CONTROL_UNHOLD, AST_CONTROL_UPDATE_RTP_PEER, AST_CONTROL_VIDUPDATE, AST_CONTROL_WINK, ast_exists_extension(), AST_FLAG_END_DTMF_ONLY, AST_FLAG_MASQ_NOSTREAM, ast_format_get_sample_rate(), AST_FRAME_CONTROL, AST_FRAME_DTMF_END, AST_FRAME_VOICE, ast_frfree, ast_log, ast_read(), ast_sched_runq(), ast_sched_wait(), ast_stopstream(), ast_strdupa, ast_tellstream(), ast_test_flag, ast_test_suite_event_notify, ast_waitfor(), ast_waitfor_nandfds(), AST_WAITSTREAM_CB_FASTFORWARD, AST_WAITSTREAM_CB_REWIND, AST_WAITSTREAM_CB_START, c, voicemailpwcheck::context, ast_frame::data, ast_frame::datalen, errno, ast_filestream::fmt, ast_format_def::format, ast_frame::frametype, ast_frame_subclass::integer, LOG_WARNING, NULL, ast_filestream::orig_chan_name, ast_frame::ptr, S_COR, ast_frame::subclass, and waitstream_control().

Referenced by ast_waitstream(), ast_waitstream_exten(), ast_waitstream_fr(), ast_waitstream_fr_w_cb(), and ast_waitstream_full().

Variable Documentation

◆ ast_language_is_prefix

int ast_language_is_prefix = 1

The following variable controls the layout of localized sound files. If 0, use the historical layout with prefix just before the filename (i.e. digits/en/1.gsm , digits/it/1.gsm or default to digits/1.gsm), if 1 put the prefix at the beginning of the filename (i.e. en/digits/1.gsm, it/digits/1.gsm or default to digits/1.gsm). The latter permits a language to be entirely in one directory.

This is settable in asterisk.conf.

Definition at line 67 of file file.c.

Referenced by fileexists_test(), handle_show_settings(), load_asterisk_conf(), and main().

◆ cli_file

struct ast_cli_entry cli_file[]
static
Initial value:
= {
{ .handler = handle_cli_core_show_file_formats , .summary = "Displays file formats" ,}
}
static char * handle_cli_core_show_file_formats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
Definition: file.c:1970

Definition at line 2040 of file file.c.

Referenced by ast_file_init(), and file_shutdown().

◆ formats

struct formats formats = { .first = NULL, .last = NULL, .lock = { PTHREAD_RWLOCK_INITIALIZER , NULL, {1, 0} } , }
static

Referenced by load_engine().

◆ read_dirs_lock

ast_mutex_t read_dirs_lock = { PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP , NULL, {1, 0} }
static

Lock to hold when iterating over directories.

Currently, 'readdir' is not required to be thread-safe. In most modern implementations it should be safe to make concurrent calls into 'readdir' that specify different directory streams (glibc would be one of these). However, since it is potentially unsafe for some implementations we'll use our own locking in order to achieve synchronization for those.

Definition at line 1271 of file file.c.

Referenced by ast_file_read_dirs().