Wed Jan 8 2020 09:50:15

Asterisk developer's documentation


monitor.h File Reference

Channel monitoring. More...

Go to the source code of this file.

Data Structures

struct  ast_channel_monitor
 

Macros

#define X_JOIN   4
 
#define X_REC_IN   1
 
#define X_REC_OUT   2
 

Enumerations

enum  AST_MONITORING_STATE { AST_MONITOR_RUNNING, AST_MONITOR_PAUSED }
 

Functions

int ast_monitor_change_fname (struct ast_channel *chan, const char *fname_base, int need_lock)
 Change monitored filename of channel. More...
 
int ast_monitor_pause (struct ast_channel *chan)
 Pause monitoring of channel. More...
 
void ast_monitor_setjoinfiles (struct ast_channel *chan, int turnon)
 
int ast_monitor_start (struct ast_channel *chan, const char *format_spec, const char *fname_base, int need_lock, int stream_action)
 Start monitoring a channel. More...
 
int ast_monitor_stop (struct ast_channel *chan, int need_lock)
 Stop monitoring channel. More...
 
int ast_monitor_unpause (struct ast_channel *chan)
 Unpause monitoring of channel. More...
 

Detailed Description

Channel monitoring.

Definition in file monitor.h.

Macro Definition Documentation

#define X_JOIN   4

Definition at line 37 of file monitor.h.

Referenced by start_monitor_exec().

#define X_REC_IN   1
#define X_REC_OUT   2

Enumeration Type Documentation

Enumerator
AST_MONITOR_RUNNING 
AST_MONITOR_PAUSED 

Definition at line 29 of file monitor.h.

Function Documentation

int ast_monitor_change_fname ( struct ast_channel chan,
const char *  fname_base,
int  need_lock 
)

Change monitored filename of channel.

Parameters
chan
fname_basenew filename
need_lock
Return values
0on success.
-1on failure.
Note
We cannot just compare filenames, due to symlinks, relative paths, and other possible filesystem issues. We could use realpath(3), but its use is discouraged. However, if we try to create the same file from two different paths, the second will fail, and so we have our notification that the filenames point to the same path.

Remember, also, that we're using the basename of the file (i.e. the file without the format suffix), so it does not already exist and we aren't interfering with the recording itself.

Definition at line 566 of file res_monitor.c.

References ast_config_AST_MONITOR_DIR, ast_copy_string(), ast_debug, ast_log(), ast_mkdir(), ast_strdupa, ast_strlen_zero(), doexit, errno, ast_channel_monitor::filename_base, ast_channel_monitor::filename_changed, LOCK_IF_NEEDED, LOG_ERROR, LOG_WARNING, ast_channel::monitor, name, ast_channel::name, and UNLOCK_IF_NEEDED.

Referenced by change_monitor_action(), change_monitor_exec(), start_monitor_action(), and start_monitor_exec().

567 {
568  if (ast_strlen_zero(fname_base)) {
569  ast_log(LOG_WARNING, "Cannot change monitor filename of channel %s to null\n", chan->name);
570  return -1;
571  }
572 
573  LOCK_IF_NEEDED(chan, need_lock);
574 
575  if (chan->monitor) {
576  int directory = strchr(fname_base, '/') ? 1 : 0;
577  const char *absolute = *fname_base == '/' ? "" : ast_config_AST_MONITOR_DIR;
578  const char *absolute_suffix = *fname_base == '/' ? "" : "/";
579  char tmpstring[sizeof(chan->monitor->filename_base)] = "";
580  int i, fd[2] = { -1, -1 }, doexit = 0;
581 
582  /* before continuing, see if we're trying to rename the file to itself... */
583  snprintf(tmpstring, sizeof(tmpstring), "%s%s%s", absolute, absolute_suffix, fname_base);
584 
585  /* try creating the directory just in case it doesn't exist */
586  if (directory) {
587  char *name = ast_strdupa(tmpstring);
588  ast_mkdir(dirname(name), 0777);
589  }
590 
591  /*!
592  * \note We cannot just compare filenames, due to symlinks, relative
593  * paths, and other possible filesystem issues. We could use
594  * realpath(3), but its use is discouraged. However, if we try to
595  * create the same file from two different paths, the second will
596  * fail, and so we have our notification that the filenames point to
597  * the same path.
598  *
599  * Remember, also, that we're using the basename of the file (i.e.
600  * the file without the format suffix), so it does not already exist
601  * and we aren't interfering with the recording itself.
602  */
603  ast_debug(2, "comparing tmpstring %s to filename_base %s\n", tmpstring, chan->monitor->filename_base);
604 
605  if ((fd[0] = open(tmpstring, O_CREAT | O_WRONLY, 0644)) < 0 ||
606  (fd[1] = open(chan->monitor->filename_base, O_CREAT | O_EXCL | O_WRONLY, 0644)) < 0) {
607  if (fd[0] < 0) {
608  ast_log(LOG_ERROR, "Unable to compare filenames: %s\n", strerror(errno));
609  } else {
610  ast_debug(2, "No need to rename monitor filename to itself\n");
611  }
612  doexit = 1;
613  }
614 
615  /* Cleanup temporary files */
616  for (i = 0; i < 2; i++) {
617  if (fd[i] >= 0) {
618  while (close(fd[i]) < 0 && errno == EINTR);
619  }
620  }
621  unlink(tmpstring);
622  /* if previous monitor file existed in a subdirectory, the directory will not be removed */
623  unlink(chan->monitor->filename_base);
624 
625  if (doexit) {
626  UNLOCK_IF_NEEDED(chan, need_lock);
627  return 0;
628  }
629 
630  ast_copy_string(chan->monitor->filename_base, tmpstring, sizeof(chan->monitor->filename_base));
631  chan->monitor->filename_changed = 1;
632  } else {
633  ast_log(LOG_WARNING, "Cannot change monitor filename of channel %s to %s, monitoring not started\n", chan->name, fname_base);
634  }
635 
636  UNLOCK_IF_NEEDED(chan, need_lock);
637 
638  return 0;
639 }
#define UNLOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:253
#define LOG_WARNING
Definition: logger.h:144
char filename_base[FILENAME_MAX]
Definition: monitor.h:45
#define LOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:248
#define ast_debug(level,...)
Log a DEBUG message.
Definition: logger.h:236
static force_inline int attribute_pure ast_strlen_zero(const char *s)
Definition: strings.h:63
static int doexit
Definition: db.c:113
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition: utils.h:663
#define LOG_ERROR
Definition: logger.h:155
const ast_string_field name
Definition: channel.h:787
void ast_log(int level, const char *file, int line, const char *function, const char *fmt,...)
Used for sending a log message This is the standard logger function. Probably the only way you will i...
Definition: logger.c:1207
int errno
static const char name[]
const char * ast_config_AST_MONITOR_DIR
Definition: asterisk.c:260
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
Definition: strings.h:223
struct ast_channel_monitor * monitor
Definition: channel.h:769
int ast_mkdir(const char *path, int mode)
Recursively create directory path.
Definition: utils.c:2151
int ast_monitor_pause ( struct ast_channel chan)

Pause monitoring of channel.

Definition at line 535 of file res_monitor.c.

References AST_MONITOR_PAUSED, and ast_monitor_set_state().

Referenced by do_pause_or_unpause(), and pause_monitor_exec().

536 {
538 }
static int ast_monitor_set_state(struct ast_channel *chan, int state)
Change state of monitored channel.
Definition: res_monitor.c:267
void ast_monitor_setjoinfiles ( struct ast_channel chan,
int  turnon 
)

Definition at line 867 of file res_monitor.c.

References ast_channel_monitor::joinfiles, and ast_channel::monitor.

Referenced by __agent_start_monitoring(), start_monitor_action(), start_monitor_exec(), and try_calling().

868 {
869  if (chan->monitor)
870  chan->monitor->joinfiles = turnon;
871 }
struct ast_channel_monitor * monitor
Definition: channel.h:769
int ast_monitor_start ( struct ast_channel chan,
const char *  format_spec,
const char *  fname_base,
int  need_lock,
int  stream_action 
)

Start monitoring a channel.

Parameters
chanast_channel struct to record
format_specfile format to use for recording
fname_basefilename base to record to
need_lockwhether to lock the channel mutex
stream_actionwhether to record the input and/or output streams. X_REC_IN | X_REC_OUT is most often used Creates the file to record, if no format is specified it assumes WAV It also sets channel variable __MONITORED=yes
Return values
0on success
-1on failure

Definition at line 290 of file res_monitor.c.

References ast_calloc, ast_closestream(), ast_config_AST_MONITOR_DIR, ast_debug, AST_FILE_MODE, ast_filedelete(), ast_fileexists(), ast_free, ast_log(), ast_manager_event, ast_mkdir(), AST_MONITOR_RUNNING, ast_monitor_set_state(), ast_monitor_stop(), ast_mutex_lock, ast_mutex_unlock, ast_strdup, ast_strdupa, ast_strlen_zero(), ast_writefile(), EVENT_FLAG_CALL, ast_channel_monitor::filename_base, ast_channel_monitor::filename_changed, FILENAME_MAX, ast_channel_monitor::format, LOCK_IF_NEEDED, LOG_WARNING, monitor, ast_channel::monitor, monitorlock, name, ast_channel::name, pbx_builtin_setvar_helper(), ast_channel_monitor::read_filename, ast_channel_monitor::read_stream, ast_channel_monitor::stop, ast_channel::uniqueid, UNLOCK_IF_NEEDED, ast_channel_monitor::write_filename, ast_channel_monitor::write_stream, X_REC_IN, and X_REC_OUT.

Referenced by __agent_start_monitoring(), start_monitor_action(), start_monitor_exec(), and try_calling().

292 {
293  int res = 0;
294 
295  LOCK_IF_NEEDED(chan, need_lock);
296 
297  if (!(chan->monitor)) {
299  char *channel_name, *p;
300 
301  /* Create monitoring directory if needed */
303 
304  if (!(monitor = ast_calloc(1, sizeof(*monitor)))) {
305  UNLOCK_IF_NEEDED(chan, need_lock);
306  return -1;
307  }
308 
309  /* Determine file names */
310  if (!ast_strlen_zero(fname_base)) {
311  int directory = strchr(fname_base, '/') ? 1 : 0;
312  const char *absolute = *fname_base == '/' ? "" : ast_config_AST_MONITOR_DIR;
313  const char *absolute_suffix = *fname_base == '/' ? "" : "/";
314 
315  snprintf(monitor->read_filename, FILENAME_MAX, "%s%s%s-in",
316  absolute, absolute_suffix, fname_base);
317  snprintf(monitor->write_filename, FILENAME_MAX, "%s%s%s-out",
318  absolute, absolute_suffix, fname_base);
319  snprintf(monitor->filename_base, FILENAME_MAX, "%s%s%s",
320  absolute, absolute_suffix, fname_base);
321 
322  /* try creating the directory just in case it doesn't exist */
323  if (directory) {
324  char *name = ast_strdupa(monitor->filename_base);
325  ast_mkdir(dirname(name), 0777);
326  }
327  } else {
329  snprintf(monitor->read_filename, FILENAME_MAX, "%s/audio-in-%lu",
331  snprintf(monitor->write_filename, FILENAME_MAX, "%s/audio-out-%lu",
333  seq++;
335 
336  /* Replace all '/' chars from the channel name with '-' chars. */
337  channel_name = ast_strdupa(chan->name);
338  for (p = channel_name; (p = strchr(p, '/')); ) {
339  *p = '-';
340  }
341 
342  snprintf(monitor->filename_base, FILENAME_MAX, "%s/%d-%s",
343  ast_config_AST_MONITOR_DIR, (int)time(NULL), channel_name);
344  monitor->filename_changed = 1;
345  }
346 
347  monitor->stop = ast_monitor_stop;
348 
349  /* Determine file format */
350  if (!ast_strlen_zero(format_spec)) {
351  monitor->format = ast_strdup(format_spec);
352  } else {
353  monitor->format = ast_strdup("wav");
354  }
355 
356  /* open files */
357  if (stream_action & X_REC_IN) {
358  if (ast_fileexists(monitor->read_filename, NULL, NULL) > 0)
359  ast_filedelete(monitor->read_filename, NULL);
360  if (!(monitor->read_stream = ast_writefile(monitor->read_filename,
361  monitor->format, NULL,
362  O_CREAT|O_TRUNC|O_WRONLY, 0, AST_FILE_MODE))) {
363  ast_log(LOG_WARNING, "Could not create file %s\n",
364  monitor->read_filename);
365  ast_free(monitor);
366  UNLOCK_IF_NEEDED(chan, need_lock);
367  return -1;
368  }
369  } else
370  monitor->read_stream = NULL;
371 
372  if (stream_action & X_REC_OUT) {
373  if (ast_fileexists(monitor->write_filename, NULL, NULL) > 0) {
374  ast_filedelete(monitor->write_filename, NULL);
375  }
376  if (!(monitor->write_stream = ast_writefile(monitor->write_filename,
377  monitor->format, NULL,
378  O_CREAT|O_TRUNC|O_WRONLY, 0, AST_FILE_MODE))) {
379  ast_log(LOG_WARNING, "Could not create file %s\n",
380  monitor->write_filename);
381  if (monitor->read_stream) {
382  ast_closestream(monitor->read_stream);
383  }
384  ast_free(monitor);
385  UNLOCK_IF_NEEDED(chan, need_lock);
386  return -1;
387  }
388  } else
389  monitor->write_stream = NULL;
390 
391  chan->monitor = monitor;
393  /* so we know this call has been monitored in case we need to bill for it or something */
394  pbx_builtin_setvar_helper(chan, "__MONITORED","true");
395 
396  ast_manager_event(chan, EVENT_FLAG_CALL, "MonitorStart",
397  "Channel: %s\r\n"
398  "Uniqueid: %s\r\n",
399  chan->name,
400  chan->uniqueid);
401  } else {
402  ast_debug(1,"Cannot start monitoring %s, already monitored\n", chan->name);
403  res = -1;
404  }
405 
406  UNLOCK_IF_NEEDED(chan, need_lock);
407 
408  return res;
409 }
#define X_REC_IN
Definition: monitor.h:35
char read_filename[FILENAME_MAX]
Definition: monitor.h:43
static int ast_monitor_set_state(struct ast_channel *chan, int state)
Change state of monitored channel.
Definition: res_monitor.c:267
const ast_string_field uniqueid
Definition: channel.h:787
#define ast_strdup(a)
Definition: astmm.h:109
#define UNLOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:253
#define LOG_WARNING
Definition: logger.h:144
static ast_mutex_t monitorlock
Definition: res_monitor.c:246
char filename_base[FILENAME_MAX]
Definition: monitor.h:45
#define EVENT_FLAG_CALL
Definition: manager.h:72
int(* stop)(struct ast_channel *chan, int need_lock)
Definition: monitor.h:50
#define LOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:248
#define ast_mutex_lock(a)
Definition: lock.h:155
int ast_filedelete(const char *filename, const char *fmt)
Deletes a file.
Definition: file.c:931
char write_filename[FILENAME_MAX]
Definition: monitor.h:44
#define AST_FILE_MODE
Definition: asterisk.h:36
#define X_REC_OUT
Definition: monitor.h:36
#define ast_manager_event(chan, category, event, contents,...)
Definition: manager.h:221
#define ast_debug(level,...)
Log a DEBUG message.
Definition: logger.h:236
static force_inline int attribute_pure ast_strlen_zero(const char *s)
Definition: strings.h:63
#define FILENAME_MAX
Definition: private.h:207
int ast_monitor_stop(struct ast_channel *chan, int need_lock)
Stop monitoring channel.
Definition: res_monitor.c:437
#define ast_strdupa(s)
duplicate a string in memory from the stack
Definition: utils.h:663
static unsigned int monitor
Definition: chan_phone.c:108
const ast_string_field name
Definition: channel.h:787
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:1049
void ast_log(int level, const char *file, int line, const char *function, const char *fmt,...)
Used for sending a log message This is the standard logger function. Probably the only way you will i...
Definition: logger.c:1207
struct ast_filestream * read_stream
Definition: monitor.h:41
static const char name[]
#define ast_free(a)
Definition: astmm.h:97
const char * ast_config_AST_MONITOR_DIR
Definition: asterisk.c:260
struct ast_filestream * write_stream
Definition: monitor.h:42
int ast_closestream(struct ast_filestream *f)
Closes a stream.
Definition: file.c:904
int pbx_builtin_setvar_helper(struct ast_channel *chan, const char *name, const char *value)
Add a variable to the channel variable stack, removing the most recently set value for the same name...
Definition: pbx.c:10546
#define ast_calloc(a, b)
Definition: astmm.h:82
int ast_fileexists(const char *filename, const char *fmt, const char *preflang)
Checks for the existence of a given file.
Definition: file.c:919
static unsigned long seq
Definition: res_monitor.c:258
struct ast_channel_monitor * monitor
Definition: channel.h:769
#define ast_mutex_unlock(a)
Definition: lock.h:156
int ast_mkdir(const char *path, int mode)
Recursively create directory path.
Definition: utils.c:2151
int ast_monitor_stop ( struct ast_channel chan,
int  need_lock 
)

Stop monitoring channel.

Parameters
chan
need_lockStop the recording, close any open streams, mix in/out channels if required
Returns
Always 0

Definition at line 437 of file res_monitor.c.

References ast_closestream(), ast_copy_string(), ast_debug, ast_filedelete(), ast_fileexists(), ast_filerename(), ast_free, ast_log(), ast_manager_event, ast_safe_system(), ast_strlen_zero(), EVENT_FLAG_CALL, ast_channel_monitor::filename_base, ast_channel_monitor::filename_changed, FILENAME_MAX, ast_channel_monitor::format, format, get_soxmix_format(), ast_channel_monitor::joinfiles, LOCK_IF_NEEDED, LOG_WARNING, ast_channel::monitor, ast_channel::name, pbx_builtin_getvar_helper(), pbx_builtin_setvar_helper(), ast_channel_monitor::read_filename, ast_channel_monitor::read_stream, ast_channel::uniqueid, UNLOCK_IF_NEEDED, ast_channel_monitor::write_filename, and ast_channel_monitor::write_stream.

Referenced by ast_monitor_start(), stop_monitor_action(), and stop_monitor_exec().

438 {
439  int delfiles = 0;
440 
441  LOCK_IF_NEEDED(chan, need_lock);
442 
443  if (chan->monitor) {
444  char filename[ FILENAME_MAX ];
445 
446  if (chan->monitor->read_stream) {
448  }
449  if (chan->monitor->write_stream) {
451  }
452 
454  if (chan->monitor->read_stream) {
455  if (ast_fileexists(chan->monitor->read_filename,NULL,NULL) > 0) {
456  snprintf(filename, FILENAME_MAX, "%s-in", chan->monitor->filename_base);
457  if (ast_fileexists(filename, NULL, NULL) > 0) {
458  ast_filedelete(filename, NULL);
459  }
460  ast_filerename(chan->monitor->read_filename, filename, chan->monitor->format);
461  } else {
462  ast_log(LOG_WARNING, "File %s not found\n", chan->monitor->read_filename);
463  }
464  }
465 
466  if (chan->monitor->write_stream) {
467  if (ast_fileexists(chan->monitor->write_filename,NULL,NULL) > 0) {
468  snprintf(filename, FILENAME_MAX, "%s-out", chan->monitor->filename_base);
469  if (ast_fileexists(filename, NULL, NULL) > 0) {
470  ast_filedelete(filename, NULL);
471  }
472  ast_filerename(chan->monitor->write_filename, filename, chan->monitor->format);
473  } else {
474  ast_log(LOG_WARNING, "File %s not found\n", chan->monitor->write_filename);
475  }
476  }
477  }
478 
479  if (chan->monitor->joinfiles && !ast_strlen_zero(chan->monitor->filename_base)) {
480  char tmp[1024];
481  char tmp2[1024];
482  const char *format = !strcasecmp(chan->monitor->format,"wav49") ? "WAV" : chan->monitor->format;
483  char *fname_base = chan->monitor->filename_base;
484  const char *execute, *execute_args;
485  /* at this point, fname_base really is the full path */
486 
487  /* Set the execute application */
488  execute = pbx_builtin_getvar_helper(chan, "MONITOR_EXEC");
489  if (ast_strlen_zero(execute)) {
490 #ifdef HAVE_SOXMIX
491  execute = "nice -n 19 soxmix";
492 #else
493  execute = "nice -n 19 sox -m";
494 #endif
495  format = get_soxmix_format(format);
496  delfiles = 1;
497  }
498  execute_args = pbx_builtin_getvar_helper(chan, "MONITOR_EXEC_ARGS");
499  if (ast_strlen_zero(execute_args)) {
500  execute_args = "";
501  }
502 
503  snprintf(tmp, sizeof(tmp), "%s \"%s-in.%s\" \"%s-out.%s\" \"%s.%s\" %s &",
504  execute, fname_base, format, fname_base, format, fname_base, format,execute_args);
505  if (delfiles) {
506  snprintf(tmp2,sizeof(tmp2), "( %s& rm -f \"%s-\"* ) &",tmp, fname_base); /* remove legs when done mixing */
507  ast_copy_string(tmp, tmp2, sizeof(tmp));
508  }
509  ast_debug(1,"monitor executing %s\n",tmp);
510  if (ast_safe_system(tmp) == -1)
511  ast_log(LOG_WARNING, "Execute of %s failed.\n",tmp);
512  }
513 
514  ast_free(chan->monitor->format);
515  ast_free(chan->monitor);
516  chan->monitor = NULL;
517 
518  ast_manager_event(chan, EVENT_FLAG_CALL, "MonitorStop",
519  "Channel: %s\r\n"
520  "Uniqueid: %s\r\n",
521  chan->name,
522  chan->uniqueid
523  );
524  pbx_builtin_setvar_helper(chan, "MONITORED", NULL);
525  }
526  pbx_builtin_setvar_helper(chan, "AUTO_MONITOR", NULL);
527 
528  UNLOCK_IF_NEEDED(chan, need_lock);
529 
530  return 0;
531 }
char read_filename[FILENAME_MAX]
Definition: monitor.h:43
int ast_safe_system(const char *s)
Safely spawn an external program while closing file descriptors.
Definition: asterisk.c:1077
const ast_string_field uniqueid
Definition: channel.h:787
#define UNLOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:253
#define LOG_WARNING
Definition: logger.h:144
char filename_base[FILENAME_MAX]
Definition: monitor.h:45
#define EVENT_FLAG_CALL
Definition: manager.h:72
#define LOCK_IF_NEEDED(lock, needed)
Definition: res_monitor.c:248
int ast_filedelete(const char *filename, const char *fmt)
Deletes a file.
Definition: file.c:931
char write_filename[FILENAME_MAX]
Definition: monitor.h:44
static const char * get_soxmix_format(const char *format)
Get audio format.
Definition: res_monitor.c:418
const char * pbx_builtin_getvar_helper(struct ast_channel *chan, const char *name)
Return a pointer to the value of the corresponding channel variable.
Definition: pbx.c:10475
#define ast_manager_event(chan, category, event, contents,...)
Definition: manager.h:221
#define ast_debug(level,...)
Log a DEBUG message.
Definition: logger.h:236
static force_inline int attribute_pure ast_strlen_zero(const char *s)
Definition: strings.h:63
#define FILENAME_MAX
Definition: private.h:207
const ast_string_field name
Definition: channel.h:787
void ast_log(int level, const char *file, int line, const char *function, const char *fmt,...)
Used for sending a log message This is the standard logger function. Probably the only way you will i...
Definition: logger.c:1207
struct ast_filestream * read_stream
Definition: monitor.h:41
#define ast_free(a)
Definition: astmm.h:97
struct ast_filestream * write_stream
Definition: monitor.h:42
int ast_closestream(struct ast_filestream *f)
Closes a stream.
Definition: file.c:904
int pbx_builtin_setvar_helper(struct ast_channel *chan, const char *name, const char *value)
Add a variable to the channel variable stack, removing the most recently set value for the same name...
Definition: pbx.c:10546
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
Definition: strings.h:223
int ast_fileexists(const char *filename, const char *fmt, const char *preflang)
Checks for the existence of a given file.
Definition: file.c:919
int ast_filerename(const char *oldname, const char *newname, const char *fmt)
Renames a file.
Definition: file.c:936
struct ast_channel_monitor * monitor
Definition: channel.h:769
static snd_pcm_format_t format
Definition: chan_alsa.c:93
int ast_monitor_unpause ( struct ast_channel chan)

Unpause monitoring of channel.

Definition at line 541 of file res_monitor.c.

References AST_MONITOR_RUNNING, and ast_monitor_set_state().

Referenced by do_pause_or_unpause(), and unpause_monitor_exec().

542 {
544 }
static int ast_monitor_set_state(struct ast_channel *chan, int state)
Change state of monitored channel.
Definition: res_monitor.c:267