Fri Jun 19 12:10:06 2009

Asterisk developer's documentation


asterisk.c File Reference

Top level source file for Asterisk - the Open Source PBX. Implementation of PBX core functions and CLI interface. More...

#include "asterisk.h"
#include "asterisk/_private.h"
#include <sys/time.h>
#include <fcntl.h>
#include <signal.h>
#include <sched.h>
#include <sys/un.h>
#include <sys/wait.h>
#include <ctype.h>
#include <sys/resource.h>
#include <grp.h>
#include <pwd.h>
#include <sys/stat.h>
#include <sys/sysinfo.h>
#include <regex.h>
#include "asterisk/paths.h"
#include "asterisk/network.h"
#include "asterisk/cli.h"
#include "asterisk/channel.h"
#include "asterisk/features.h"
#include "asterisk/ulaw.h"
#include "asterisk/alaw.h"
#include "asterisk/callerid.h"
#include "asterisk/image.h"
#include "asterisk/tdd.h"
#include "asterisk/term.h"
#include "asterisk/manager.h"
#include "asterisk/cdr.h"
#include "asterisk/pbx.h"
#include "asterisk/enum.h"
#include "asterisk/rtp.h"
#include "asterisk/http.h"
#include "asterisk/udptl.h"
#include "asterisk/app.h"
#include "asterisk/lock.h"
#include "asterisk/utils.h"
#include "asterisk/file.h"
#include "asterisk/io.h"
#include "editline/histedit.h"
#include "asterisk/config.h"
#include "asterisk/ast_version.h"
#include "asterisk/linkedlists.h"
#include "asterisk/devicestate.h"
#include "asterisk/module.h"
#include "asterisk/dsp.h"
#include "asterisk/poll-compat.h"
#include "asterisk/doxyref.h"
#include "../defaults.h"

Go to the source code of this file.

Data Structures

struct  _cfg_paths
struct  ast_atexit
struct  atexits
struct  console
struct  file_version
struct  file_versions
struct  profile_data
struct  profile_entry
struct  thread_list
struct  thread_list_t

Defines

#define AF_LOCAL   AF_UNIX
#define AST_MAX_CONNECTS   128
#define ASTERISK_PROMPT   "*CLI> "
#define ASTERISK_PROMPT2   "%s*CLI> "
#define DEFINE_PROFILE_MIN_MAX_VALUES
#define EL_BUF_SIZE   512
#define FORMAT   "%-25.25s %-40.40s\n"
#define NUM_MSGS   64
#define PF_LOCAL   PF_UNIX
#define WELCOME_MESSAGE
 Welcome message when starting a CLI interface.

Functions

static void __quit_handler (int num)
static void __remote_quit_handler (int num)
int ast_add_profile (const char *name, uint64_t scale)
 support for event profiling
static int ast_all_zeros (char *s)
static int ast_cli_display_match_list (char **matches, int len, int max)
void ast_console_puts (const char *string)
void ast_console_puts_mutable (const char *string, int level)
 log the string to the console, and all attached console clients
void ast_console_toggle_loglevel (int fd, int level, int state)
void ast_console_toggle_mute (int fd, int silent)
 mute or unmute a console from logging
static int ast_el_add_history (char *)
static int ast_el_initialize (void)
static int ast_el_read_char (EditLine *editline, char *cp)
static int ast_el_read_history (char *)
static int ast_el_sort_compare (const void *i1, const void *i2)
static char ** ast_el_strtoarr (char *buf)
static int ast_el_write_history (char *)
const char * ast_file_version_find (const char *file)
 Find version for given module name.
static int ast_makesocket (void)
int64_t ast_mark (int i, int startstop)
static void ast_network_puts (const char *string)
 write the string to all attached console clients
static void ast_network_puts_mutable (const char *string, int level)
 log the string to all attached console clients
int64_t ast_profile (int i, int64_t delta)
static void ast_readconfig (void)
int ast_register_atexit (void(*func)(void))
 Register a function to be executed before Asterisk exits.
void ast_register_file_version (const char *file, const char *version)
 Register the version of a source code file with the core.
void ast_register_thread (char *name)
static void ast_remotecontrol (char *data)
void ast_replace_sigchld (void)
 Replace the SIGCHLD handler.
static void ast_run_atexits (void)
int ast_safe_system (const char *s)
 Safely spawn an external program while closing file descriptors.
int ast_set_priority (int pri)
 We set ourselves to a high priority, that we might pre-empt everything else. If your PBX has heavy activity on it, this is a good thing.
static int ast_tryconnect (void)
void ast_unregister_atexit (void(*func)(void))
 Unregister a function registered with ast_register_atexit().
void ast_unregister_file_version (const char *file)
 Unregister a source code file from the core.
void ast_unregister_thread (void *id)
void ast_unreplace_sigchld (void)
 Restore the SIGCHLD handler.
static void canary_exit (void)
static void * canary_thread (void *unused)
static void child_handler (int sig)
static char * cli_complete (EditLine *editline, int ch)
static char * cli_prompt (EditLine *editline)
static void console_verboser (const char *s)
static void consolehandler (char *s)
static int fdprint (int fd, const char *s)
static int fdsend (int fd, const char *s)
static const char * fix_header (char *outbuf, int maxout, const char *s, char *cmp)
static char * handle_abort_shutdown (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_abort_shutdown_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_bang (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_clear_profile (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_gracefully (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_gracefully_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_now (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_now_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_when_convenient (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_restart_when_convenient_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_show_profile (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_show_settings (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
 Give an overview of core settings.
static char * handle_show_sysinfo (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
 Give an overview of system statistics.
static char * handle_show_threads (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_show_version_files (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
 CLI command to list module versions.
static char * handle_stop_gracefully (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_stop_gracefully_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_stop_now (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_stop_now_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_stop_when_convenient (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_stop_when_convenient_deprecated (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static char * handle_version (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static void hup_handler (int num)
static void * listener (void *unused)
int main (int argc, char *argv[])
static void * monitor_sig_flags (void *unused)
static void * netconsole (void *vconsole)
static void network_verboser (const char *s)
static void null_sig_handler (int sig)
 NULL handler so we can collect the child exit status.
static void quit_handler (int num, int niceness, int safeshutdown, int restart)
static __inline uint64_t rdtsc (void)
static int remoteconsolehandler (char *s)
static void run_startup_commands (void)
static void set_icon (char *text)
static void set_title (char *text)
 Set an X-term or screen title.
static void set_ulimit (int value)
 Set maximum open files.
static int show_cli_help (void)
static char * show_license (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static int show_version (void)
static char * show_warranty (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static void urg_handler (int num)
 Urgent handler.

Variables

static char * _argv [256]
const char * ast_build_date
const char * ast_build_hostname
const char * ast_build_kernel
const char * ast_build_machine
const char * ast_build_os
const char * ast_build_user
ast_flags ast_compat = { 7 }
const char * ast_config_AST_AGI_DIR = cfg_paths.agi_dir
const char * ast_config_AST_CONFIG_DIR = cfg_paths.config_dir
const char * ast_config_AST_CONFIG_FILE = cfg_paths.config_file
static char ast_config_AST_CTL [PATH_MAX] = "asterisk.ctl"
static char ast_config_AST_CTL_GROUP [PATH_MAX] = "\0"
static char ast_config_AST_CTL_OWNER [PATH_MAX] = "\0"
static char ast_config_AST_CTL_PERMISSIONS [PATH_MAX]
const char * ast_config_AST_DATA_DIR = cfg_paths.data_dir
const char * ast_config_AST_DB = cfg_paths.db_path
const char * ast_config_AST_KEY_DIR = cfg_paths.key_dir
const char * ast_config_AST_LOG_DIR = cfg_paths.log_dir
const char * ast_config_AST_MODULE_DIR = cfg_paths.module_dir
const char * ast_config_AST_MONITOR_DIR = cfg_paths.monitor_dir
const char * ast_config_AST_PID = cfg_paths.pid_path
const char * ast_config_AST_RUN_DIR = cfg_paths.run_dir
const char * ast_config_AST_RUN_GROUP = cfg_paths.run_group
const char * ast_config_AST_RUN_USER = cfg_paths.run_user
const char * ast_config_AST_SOCKET = cfg_paths.socket_path
const char * ast_config_AST_SPOOL_DIR = cfg_paths.spool_dir
const char * ast_config_AST_SYSTEM_NAME = cfg_paths.system_name
const char * ast_config_AST_VAR_DIR = cfg_paths.var_dir
static int ast_consock = -1
ast_eid ast_eid_default
 Global EID.
timeval ast_lastreloadtime
pid_t ast_mainpid
ast_flags ast_options = { AST_DEFAULT_OPTIONS }
static int ast_socket = -1
timeval ast_startuptime
static char canary_filename [128]
static int canary_pid = 0
static int canary_pipe = -1
static struct _cfg_paths cfg_paths
static struct ast_cli_entry cli_abort_shutdown_deprecated = { .handler = handle_abort_shutdown_deprecated , .summary = "Cancel a running shutdown." ,__VA_ARGS__ }
static struct ast_cli_entry cli_asterisk []
static struct ast_cli_entry cli_restart_gracefully_deprecated = { .handler = handle_restart_gracefully_deprecated , .summary = "Restart Asterisk gracefully." ,__VA_ARGS__ }
static struct ast_cli_entry cli_restart_now_deprecated = { .handler = handle_restart_now_deprecated , .summary = "Restart Asterisk immediately." ,__VA_ARGS__ }
static struct ast_cli_entry cli_restart_when_convenient_deprecated = { .handler = handle_restart_when_convenient_deprecated , .summary = "Restart Asterisk at empty call volume." ,__VA_ARGS__ }
static struct ast_cli_entry cli_stop_gracefully_deprecated = { .handler = handle_stop_gracefully_deprecated , .summary = "Gracefully shut down Asterisk." ,__VA_ARGS__ }
static struct ast_cli_entry cli_stop_now_deprecated = { .handler = handle_stop_now_deprecated , .summary = "Shut down Asterisk immediately." ,__VA_ARGS__ }
static struct ast_cli_entry cli_stop_when_convenient_deprecated = { .handler = handle_stop_when_convenient_deprecated , .summary = "Shut down Asterisk at empty call volume." ,__VA_ARGS__ }
console consoles [AST_MAX_CONNECTS]
static pthread_t consolethread = AST_PTHREADT_NULL
char defaultlanguage [MAX_LANGUAGE] = DEFAULT_LANGUAGE
static EditLine * el
static History * el_hist
static const char license_lines []
static pthread_t lthread
int option_debug
int option_maxcalls
int option_maxfiles
double option_maxload
long option_minmemfree
int option_verbose
static struct profile_dataprof_data
static struct ast_strprompt = NULL
static char randompool [256]
char record_cache_dir [AST_CACHE_DIR_LEN] = DEFAULT_TMP_DIR
static char * remotehostname
static int restartnow
static unsigned int safe_system_level = 0
 Keep track of how many threads are currently trying to wait*() on a child process.
static ast_mutex_t safe_system_lock = ((ast_mutex_t) PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP )
static void * safe_system_prev_handler
static int shuttingdown
static int sig_alert_pipe [2] = { -1, -1 }
struct {
   unsigned int   need_quit:1
   unsigned int   need_reload:1
sig_flags
static const char warranty_lines []


Detailed Description

Top level source file for Asterisk - the Open Source PBX. Implementation of PBX core functions and CLI interface.

Definition in file asterisk.c.


Define Documentation

#define AF_LOCAL   AF_UNIX

Definition at line 127 of file asterisk.c.

Referenced by ast_makesocket(), ast_tryconnect(), listener(), and NBScat_exec().

#define AST_MAX_CONNECTS   128

Definition at line 131 of file asterisk.c.

Referenced by ast_console_toggle_loglevel(), ast_console_toggle_mute(), ast_makesocket(), ast_network_puts(), ast_network_puts_mutable(), and listener().

#define ASTERISK_PROMPT   "*CLI> "

Definition at line 1886 of file asterisk.c.

Referenced by cli_prompt().

#define ASTERISK_PROMPT2   "%s*CLI> "

Definition at line 1888 of file asterisk.c.

Referenced by cli_prompt().

#define DEFINE_PROFILE_MIN_MAX_VALUES

Definition at line 613 of file asterisk.c.

Referenced by handle_clear_profile(), and handle_show_profile().

#define EL_BUF_SIZE   512

Referenced by ast_el_read_char().

#define FORMAT   "%-25.25s %-40.40s\n"

Referenced by __iax2_show_peers(), _sip_show_peers(), dahdi_show_channels(), dahdi_show_status(), dundi_show_mappings(), dundi_show_peers(), dundi_show_precache(), dundi_show_requests(), dundi_show_trans(), gtalk_show_channels(), handle_cli_core_show_channeltypes(), handle_cli_core_show_file_formats(), handle_cli_iax2_show_channels(), handle_cli_iax2_show_registry(), handle_cli_iax2_show_users(), handle_cli_keys_show(), handle_core_show_image_formats(), handle_show_routes(), handle_show_version_files(), jingle_show_channels(), show_channels_cb(), show_chanstats_cb(), sip_show_domains(), sip_show_inuse(), sip_show_registry(), sip_show_tcp(), and sip_show_users().

#define NUM_MSGS   64

Definition at line 132 of file asterisk.c.

#define PF_LOCAL   PF_UNIX

Definition at line 128 of file asterisk.c.

Referenced by ast_makesocket(), and ast_tryconnect().

#define WELCOME_MESSAGE

Welcome message when starting a CLI interface.

Definition at line 135 of file asterisk.c.

Referenced by ast_el_read_char(), and main().


Function Documentation

static void __quit_handler ( int  num  )  [static]

Definition at line 1452 of file asterisk.c.

References errno, sig_alert_pipe, and sig_flags.

Referenced by main().

01453 {
01454    int a = 0;
01455    sig_flags.need_quit = 1;
01456    if (sig_alert_pipe[1] != -1) {
01457       if (write(sig_alert_pipe[1], &a, sizeof(a)) < 0) {
01458          fprintf(stderr, "hup_handler: write() failed: %s\n", strerror(errno));
01459       }
01460    }
01461    /* There is no need to restore the signal handler here, since the app
01462     * is going to exit */
01463 }

static void __remote_quit_handler ( int  num  )  [static]

Definition at line 1465 of file asterisk.c.

References sig_flags.

Referenced by ast_remotecontrol().

01466 {
01467    sig_flags.need_quit = 1;
01468 }

int ast_add_profile ( const char *  name,
uint64_t  scale 
)

support for event profiling

Returns:
Returns the identifier of the counter.

Definition at line 532 of file asterisk.c.

References ast_calloc, ast_realloc, ast_strdup, profile_data::e, profile_data::entries, profile_entry::events, profile_entry::mark, profile_data::max_size, profile_entry::name, prof_data, profile_entry::scale, and profile_entry::value.

Referenced by extension_match_core().

00533 {
00534    int l = sizeof(struct profile_data);
00535    int n = 10; /* default entries */
00536 
00537    if (prof_data == NULL) {
00538       prof_data = ast_calloc(1, l + n*sizeof(struct profile_entry));
00539       if (prof_data == NULL)
00540          return -1;
00541       prof_data->entries = 0;
00542       prof_data->max_size = n;
00543    }
00544    if (prof_data->entries >= prof_data->max_size) {
00545       void *p;
00546       n = prof_data->max_size + 20;
00547       p = ast_realloc(prof_data, l + n*sizeof(struct profile_entry));
00548       if (p == NULL)
00549          return -1;
00550       prof_data = p;
00551       prof_data->max_size = n;
00552    }
00553    n = prof_data->entries++;
00554    prof_data->e[n].name = ast_strdup(name);
00555    prof_data->e[n].value = 0;
00556    prof_data->e[n].events = 0;
00557    prof_data->e[n].mark = 0;
00558    prof_data->e[n].scale = scale;
00559    return n;
00560 }

static int ast_all_zeros ( char *  s  )  [static]

Definition at line 1512 of file asterisk.c.

Referenced by ast_el_read_history(), consolehandler(), and remoteconsolehandler().

01513 {
01514    while (*s) {
01515       if (*s > 32)
01516          return 0;
01517       s++;  
01518    }
01519    return 1;
01520 }

static int ast_cli_display_match_list ( char **  matches,
int  len,
int  max 
) [static]

Definition at line 2208 of file asterisk.c.

References ast_el_sort_compare(), ast_free, and ast_get_termcols().

Referenced by cli_complete().

02209 {
02210    int i, idx, limit, count;
02211    int screenwidth = 0;
02212    int numoutput = 0, numoutputline = 0;
02213 
02214    screenwidth = ast_get_termcols(STDOUT_FILENO);
02215 
02216    /* find out how many entries can be put on one line, with two spaces between strings */
02217    limit = screenwidth / (max + 2);
02218    if (limit == 0)
02219       limit = 1;
02220 
02221    /* how many lines of output */
02222    count = len / limit;
02223    if (count * limit < len)
02224       count++;
02225 
02226    idx = 1;
02227 
02228    qsort(&matches[0], (size_t)(len), sizeof(char *), ast_el_sort_compare);
02229 
02230    for (; count > 0; count--) {
02231       numoutputline = 0;
02232       for (i = 0; i < limit && matches[idx]; i++, idx++) {
02233 
02234          /* Don't print dupes */
02235          if ( (matches[idx+1] != NULL && strcmp(matches[idx], matches[idx+1]) == 0 ) ) {
02236             i--;
02237             ast_free(matches[idx]);
02238             matches[idx] = NULL;
02239             continue;
02240          }
02241 
02242          numoutput++;
02243          numoutputline++;
02244          fprintf(stdout, "%-*s  ", max, matches[idx]);
02245          ast_free(matches[idx]);
02246          matches[idx] = NULL;
02247       }
02248       if (numoutputline > 0)
02249          fprintf(stdout, "\n");
02250    }
02251 
02252    return numoutput;
02253 }

void ast_console_puts ( const char *  string  ) 

write the string to the console, and all attached console clients

Definition at line 993 of file asterisk.c.

References ast_network_puts().

Referenced by chan_misdn_log().

00994 {
00995    fputs(string, stdout);
00996    fflush(stdout);
00997    ast_network_puts(string);
00998 }

void ast_console_puts_mutable ( const char *  string,
int  level 
)

log the string to the console, and all attached console clients

Version:
1.6.1 added level parameter

Definition at line 970 of file asterisk.c.

References ast_network_puts_mutable().

Referenced by logger_print_normal().

00971 {
00972    fputs(string, stdout);
00973    fflush(stdout);
00974    ast_network_puts_mutable(string, level);
00975 }

void ast_console_toggle_loglevel ( int  fd,
int  level,
int  state 
)

Since:
1.6.1

Definition at line 917 of file asterisk.c.

References AST_MAX_CONNECTS, consoles, and levels.

00918 {
00919    int x;
00920    for (x = 0;x < AST_MAX_CONNECTS; x++) {
00921       if (fd == consoles[x].fd) {
00922          consoles[x].levels[level] = state;
00923          return;
00924       }
00925    }
00926 }

void ast_console_toggle_mute ( int  fd,
int  silent 
)

mute or unmute a console from logging

Definition at line 931 of file asterisk.c.

References ast_cli(), AST_MAX_CONNECTS, consoles, and console::mute.

Referenced by handle_logger_mute().

00931                                                  {
00932    int x;
00933    for (x = 0;x < AST_MAX_CONNECTS; x++) {
00934       if (fd == consoles[x].fd) {
00935          if (consoles[x].mute) {
00936             consoles[x].mute = 0;
00937             if (!silent)
00938                ast_cli(fd, "Console is not muted anymore.\n");
00939          } else {
00940             consoles[x].mute = 1;
00941             if (!silent)
00942                ast_cli(fd, "Console is muted.\n");
00943          }
00944          return;
00945       }
00946    }
00947    ast_cli(fd, "Couldn't find remote console.\n");
00948 }

static int ast_el_add_history ( char *   )  [static]

Definition at line 2409 of file asterisk.c.

References ast_el_initialize(), el, and el_hist.

Referenced by ast_el_read_history(), consolehandler(), and remoteconsolehandler().

02410 {
02411    HistEvent ev;
02412 
02413    if (el_hist == NULL || el == NULL)
02414       ast_el_initialize();
02415    if (strlen(buf) > 256)
02416       return 0;
02417    return (history(el_hist, &ev, H_ENTER, buf));
02418 }

static int ast_el_initialize ( void   )  [static]

Definition at line 2374 of file asterisk.c.

References cli_complete(), cli_prompt(), el, and el_hist.

Referenced by ast_el_add_history(), ast_el_read_history(), ast_el_write_history(), ast_remotecontrol(), and main().

02375 {
02376    HistEvent ev;
02377    char *editor = getenv("AST_EDITOR");
02378 
02379    if (el != NULL)
02380       el_end(el);
02381    if (el_hist != NULL)
02382       history_end(el_hist);
02383 
02384    el = el_init("asterisk", stdin, stdout, stderr);
02385    el_set(el, EL_PROMPT, cli_prompt);
02386 
02387    el_set(el, EL_EDITMODE, 1);      
02388    el_set(el, EL_EDITOR, editor ? editor : "emacs");     
02389    el_hist = history_init();
02390    if (!el || !el_hist)
02391       return -1;
02392 
02393    /* setup history with 100 entries */
02394    history(el_hist, &ev, H_SETSIZE, 100);
02395 
02396    el_set(el, EL_HIST, history, el_hist);
02397 
02398    el_set(el, EL_ADDFN, "ed-complete", "Complete argument", cli_complete);
02399    /* Bind <tab> to command completion */
02400    el_set(el, EL_BIND, "^I", "ed-complete", NULL);
02401    /* Bind ? to command completion */
02402    el_set(el, EL_BIND, "?", "ed-complete", NULL);
02403    /* Bind ^D to redisplay */
02404    el_set(el, EL_BIND, "^D", "ed-redisplay", NULL);
02405 
02406    return 0;
02407 }

static int ast_el_read_char ( EditLine *  editline,
char *  cp 
) [static]

Definition at line 1924 of file asterisk.c.

References ast_log(), ast_opt_exec, ast_opt_mute, ast_opt_reconnect, ast_poll, ast_tryconnect(), buf, EL_BUF_SIZE, errno, fdsend(), LOG_ERROR, quit_handler(), sig_flags, term_quit(), and WELCOME_MESSAGE.

Referenced by ast_remotecontrol().

01925 {
01926    int num_read = 0;
01927    int lastpos = 0;
01928    struct pollfd fds[2];
01929    int res;
01930    int max;
01931 #define EL_BUF_SIZE 512
01932    char buf[EL_BUF_SIZE];
01933 
01934    for (;;) {
01935       max = 1;
01936       fds[0].fd = ast_consock;
01937       fds[0].events = POLLIN;
01938       if (!ast_opt_exec) {
01939          fds[1].fd = STDIN_FILENO;
01940          fds[1].events = POLLIN;
01941          max++;
01942       }
01943       res = ast_poll(fds, max, -1);
01944       if (res < 0) {
01945          if (sig_flags.need_quit)
01946             break;
01947          if (errno == EINTR)
01948             continue;
01949          ast_log(LOG_ERROR, "poll failed: %s\n", strerror(errno));
01950          break;
01951       }
01952 
01953       if (!ast_opt_exec && fds[1].revents) {
01954          num_read = read(STDIN_FILENO, cp, 1);
01955          if (num_read < 1) {
01956             break;
01957          } else 
01958             return (num_read);
01959       }
01960       if (fds[0].revents) {
01961          char *tmp;
01962          res = read(ast_consock, buf, sizeof(buf) - 1);
01963          /* if the remote side disappears exit */
01964          if (res < 1) {
01965             fprintf(stderr, "\nDisconnected from Asterisk server\n");
01966             if (!ast_opt_reconnect) {
01967                quit_handler(0, 0, 0, 0);
01968             } else {
01969                int tries;
01970                int reconnects_per_second = 20;
01971                fprintf(stderr, "Attempting to reconnect for 30 seconds\n");
01972                for (tries = 0; tries < 30 * reconnects_per_second; tries++) {
01973                   if (ast_tryconnect()) {
01974                      fprintf(stderr, "Reconnect succeeded after %.3f seconds\n", 1.0 / reconnects_per_second * tries);
01975                      printf("%s", term_quit());
01976                      WELCOME_MESSAGE;
01977                      if (!ast_opt_mute)
01978                         fdsend(ast_consock, "logger mute silent");
01979                      else 
01980                         printf("log and verbose output currently muted ('logger mute' to unmute)\n");
01981                      break;
01982                   } else
01983                      usleep(1000000 / reconnects_per_second);
01984                }
01985                if (tries >= 30 * reconnects_per_second) {
01986                   fprintf(stderr, "Failed to reconnect for 30 seconds.  Quitting.\n");
01987                   quit_handler(0, 0, 0, 0);
01988                }
01989             }
01990          }
01991 
01992          buf[res] = '\0';
01993 
01994          /* Strip preamble from asynchronous events, too */
01995          for (tmp = buf; *tmp; tmp++) {
01996             if (*tmp == 127) {
01997                memmove(tmp, tmp + 1, strlen(tmp));
01998                tmp--;
01999                res--;
02000             }
02001          }
02002 
02003          /* Write over the CLI prompt */
02004          if (!ast_opt_exec && !lastpos) {
02005             if (write(STDOUT_FILENO, "\r", 1) < 0) {
02006             }
02007          }
02008          if (write(STDOUT_FILENO, buf, res) < 0) {
02009          }
02010          if ((res < EL_BUF_SIZE - 1) && ((buf[res-1] == '\n') || (buf[res-2] == '\n'))) {
02011             *cp = CC_REFRESH;
02012             return(1);
02013          } else
02014             lastpos = 1;
02015       }
02016    }
02017 
02018    *cp = '\0';
02019    return (0);
02020 }

static int ast_el_read_history ( char *   )  [static]

Definition at line 2430 of file asterisk.c.

References ast_all_zeros(), ast_el_add_history(), ast_el_initialize(), el, el_hist, and f.

Referenced by ast_remotecontrol(), and main().

02431 {
02432    char buf[256];
02433    FILE *f;
02434    int ret = -1;
02435 
02436    if (el_hist == NULL || el == NULL)
02437       ast_el_initialize();
02438 
02439    if ((f = fopen(filename, "r")) == NULL)
02440       return ret;
02441 
02442    while (!feof(f)) {
02443       if (!fgets(buf, sizeof(buf), f)) {
02444          continue;
02445       }
02446       if (!strcmp(buf, "_HiStOrY_V2_\n"))
02447          continue;
02448       if (ast_all_zeros(buf))
02449          continue;
02450       if ((ret = ast_el_add_history(buf)) == -1)
02451          break;
02452    }
02453    fclose(f);
02454 
02455    return ret;
02456 }

static int ast_el_sort_compare ( const void *  i1,
const void *  i2 
) [static]

Definition at line 2198 of file asterisk.c.

Referenced by ast_cli_display_match_list().

02199 {
02200    char *s1, *s2;
02201 
02202    s1 = ((char **)i1)[0];
02203    s2 = ((char **)i2)[0];
02204 
02205    return strcasecmp(s1, s2);
02206 }

static char** ast_el_strtoarr ( char *  buf  )  [static]

Definition at line 2155 of file asterisk.c.

References AST_CLI_COMPLETE_EOF, ast_free, ast_realloc, ast_strdup, and strsep().

Referenced by cli_complete().

02156 {
02157    char **match_list = NULL, **match_list_tmp, *retstr;
02158    size_t match_list_len;
02159    int matches = 0;
02160 
02161    match_list_len = 1;
02162    while ( (retstr = strsep(&buf, " ")) != NULL) {
02163 
02164       if (!strcmp(retstr, AST_CLI_COMPLETE_EOF))
02165          break;
02166       if (matches + 1 >= match_list_len) {
02167          match_list_len <<= 1;
02168          if ((match_list_tmp = ast_realloc(match_list, match_list_len * sizeof(char *)))) {
02169             match_list = match_list_tmp;
02170          } else {
02171             if (match_list)
02172                ast_free(match_list);
02173             return (char **) NULL;
02174          }
02175       }
02176 
02177       match_list[matches++] = ast_strdup(retstr);
02178    }
02179 
02180    if (!match_list)
02181       return (char **) NULL;
02182 
02183    if (matches >= match_list_len) {
02184       if ((match_list_tmp = ast_realloc(match_list, (match_list_len + 1) * sizeof(char *)))) {
02185          match_list = match_list_tmp;
02186       } else {
02187          if (match_list)
02188             ast_free(match_list);
02189          return (char **) NULL;
02190       }
02191    }
02192 
02193    match_list[matches] = (char *) NULL;
02194 
02195    return match_list;
02196 }

static int ast_el_write_history ( char *   )  [static]

Definition at line 2420 of file asterisk.c.

References ast_el_initialize(), el, and el_hist.

Referenced by quit_handler().

02421 {
02422    HistEvent ev;
02423 
02424    if (el_hist == NULL || el == NULL)
02425       ast_el_initialize();
02426 
02427    return (history(el_hist, &ev, H_SAVE, filename));
02428 }

const char* ast_file_version_find ( const char *  file  ) 

Find version for given module name.

Parameters:
file Module name (i.e. chan_sip.so)
Returns:
version string or NULL if the module is not found

Definition at line 322 of file asterisk.c.

References AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, file_version::file, ast_atexit::list, and file_version::version.

Referenced by manager_modulecheck().

00323 {
00324    struct file_version *iterator;
00325 
00326    AST_RWLIST_WRLOCK(&file_versions);
00327    AST_RWLIST_TRAVERSE_SAFE_BEGIN(&file_versions, iterator, list) {
00328       if (!strcasecmp(iterator->file, file))
00329          break;
00330    }
00331    AST_RWLIST_TRAVERSE_SAFE_END;
00332    AST_RWLIST_UNLOCK(&file_versions);
00333    if (iterator)
00334       return iterator->version;
00335    return NULL;
00336 }      

static int ast_makesocket ( void   )  [static]

Definition at line 1126 of file asterisk.c.

References AF_LOCAL, ast_config_AST_CTL_GROUP, ast_config_AST_CTL_OWNER, ast_config_AST_CTL_PERMISSIONS, ast_config_AST_SOCKET, ast_copy_string(), ast_log(), AST_MAX_CONNECTS, ast_pthread_create_background, ast_register_verbose(), ast_strlen_zero(), consoles, errno, listener(), LOG_WARNING, lthread, network_verboser(), and PF_LOCAL.

Referenced by main().

01127 {
01128    struct sockaddr_un sunaddr;
01129    int res;
01130    int x;
01131    uid_t uid = -1;
01132    gid_t gid = -1;
01133 
01134    for (x = 0; x < AST_MAX_CONNECTS; x++) 
01135       consoles[x].fd = -1;
01136    unlink(ast_config_AST_SOCKET);
01137    ast_socket = socket(PF_LOCAL, SOCK_STREAM, 0);
01138    if (ast_socket < 0) {
01139       ast_log(LOG_WARNING, "Unable to create control socket: %s\n", strerror(errno));
01140       return -1;
01141    }     
01142    memset(&sunaddr, 0, sizeof(sunaddr));
01143    sunaddr.sun_family = AF_LOCAL;
01144    ast_copy_string(sunaddr.sun_path, ast_config_AST_SOCKET, sizeof(sunaddr.sun_path));
01145    res = bind(ast_socket, (struct sockaddr *)&sunaddr, sizeof(sunaddr));
01146    if (res) {
01147       ast_log(LOG_WARNING, "Unable to bind socket to %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
01148       close(ast_socket);
01149       ast_socket = -1;
01150       return -1;
01151    }
01152    res = listen(ast_socket, 2);
01153    if (res < 0) {
01154       ast_log(LOG_WARNING, "Unable to listen on socket %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
01155       close(ast_socket);
01156       ast_socket = -1;
01157       return -1;
01158    }
01159    if (ast_register_verbose(network_verboser)) {
01160       ast_log(LOG_WARNING, "Unable to register network verboser?\n");
01161    }
01162 
01163    ast_pthread_create_background(&lthread, NULL, listener, NULL);
01164 
01165    if (!ast_strlen_zero(ast_config_AST_CTL_OWNER)) {
01166       struct passwd *pw;
01167       if ((pw = getpwnam(ast_config_AST_CTL_OWNER)) == NULL)
01168          ast_log(LOG_WARNING, "Unable to find uid of user %s\n", ast_config_AST_CTL_OWNER);
01169       else
01170          uid = pw->pw_uid;
01171    }
01172       
01173    if (!ast_strlen_zero(ast_config_AST_CTL_GROUP)) {
01174       struct group *grp;
01175       if ((grp = getgrnam(ast_config_AST_CTL_GROUP)) == NULL)
01176          ast_log(LOG_WARNING, "Unable to find gid of group %s\n", ast_config_AST_CTL_GROUP);
01177       else
01178          gid = grp->gr_gid;
01179    }
01180 
01181    if (chown(ast_config_AST_SOCKET, uid, gid) < 0)
01182       ast_log(LOG_WARNING, "Unable to change ownership of %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
01183 
01184    if (!ast_strlen_zero(ast_config_AST_CTL_PERMISSIONS)) {
01185       int p1;
01186       mode_t p;
01187       sscanf(ast_config_AST_CTL_PERMISSIONS, "%o", &p1);
01188       p = p1;
01189       if ((chmod(ast_config_AST_SOCKET, p)) < 0)
01190          ast_log(LOG_WARNING, "Unable to change file permissions of %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
01191    }
01192 
01193    return 0;
01194 }

int64_t ast_mark ( int  i,
int  startstop 
)

Definition at line 597 of file asterisk.c.

References profile_data::e, profile_data::entries, profile_entry::events, profile_entry::mark, prof_data, rdtsc(), profile_entry::scale, and profile_entry::value.

Referenced by extension_match_core().

00598 {
00599    if (!prof_data || i < 0 || i > prof_data->entries) /* invalid index */
00600       return 0;
00601    if (startstop == 1)
00602       prof_data->e[i].mark = rdtsc();
00603    else {
00604       prof_data->e[i].mark = (rdtsc() - prof_data->e[i].mark);
00605       if (prof_data->e[i].scale > 1)
00606          prof_data->e[i].mark /= prof_data->e[i].scale;
00607       prof_data->e[i].value += prof_data->e[i].mark;
00608       prof_data->e[i].events++;
00609    }
00610    return prof_data->e[i].mark;
00611 }

static void ast_network_puts ( const char *  string  )  [static]

write the string to all attached console clients

Definition at line 980 of file asterisk.c.

References AST_MAX_CONNECTS, consoles, and fdprint().

Referenced by ast_console_puts().

00981 {
00982    int x;
00983    for (x = 0; x < AST_MAX_CONNECTS; x++) {
00984       if (consoles[x].fd > -1) 
00985          fdprint(consoles[x].p[1], string);
00986    }
00987 }

static void ast_network_puts_mutable ( const char *  string,
int  level 
) [static]

log the string to all attached console clients

Definition at line 953 of file asterisk.c.

References AST_MAX_CONNECTS, consoles, fdprint(), and levels.

Referenced by ast_console_puts_mutable(), and network_verboser().

00954 {
00955    int x;
00956    for (x = 0;x < AST_MAX_CONNECTS; x++) {
00957       if (consoles[x].mute)
00958          continue;
00959       if (consoles[x].fd > -1) {
00960          if (!consoles[x].levels[level]) 
00961             fdprint(consoles[x].p[1], string);
00962       }
00963    }
00964 }

int64_t ast_profile ( int  i,
int64_t  delta 
)

Definition at line 562 of file asterisk.c.

References profile_data::e, profile_data::entries, profile_entry::events, prof_data, profile_entry::scale, and profile_entry::value.

00563 {
00564    if (!prof_data || i < 0 || i > prof_data->entries) /* invalid index */
00565       return 0;
00566    if (prof_data->e[i].scale > 1)
00567       delta /= prof_data->e[i].scale;
00568    prof_data->e[i].value += delta;
00569    prof_data->e[i].events++;
00570    return prof_data->e[i].value;
00571 }

static void ast_readconfig ( void   )  [static]

Definition at line 2644 of file asterisk.c.

References _cfg_paths::agi_dir, ast_config_AST_CONFIG_FILE, ast_config_AST_CTL, ast_config_AST_CTL_GROUP, ast_config_AST_CTL_OWNER, ast_config_AST_CTL_PERMISSIONS, ast_config_load2(), ast_copy_string(), ast_eid_default, ast_log(), ast_opt_override_config, ast_set_default_eid(), ast_variable_browse(), cfg_paths, config, _cfg_paths::config_dir, config_flags, _cfg_paths::data_dir, _cfg_paths::db_path, DEFAULT_AGI_DIR, DEFAULT_CONFIG_DIR, DEFAULT_CONFIG_FILE, DEFAULT_DATA_DIR, DEFAULT_DB, DEFAULT_KEY_DIR, DEFAULT_LOG_DIR, DEFAULT_MODULE_DIR, DEFAULT_PID, DEFAULT_RUN_DIR, DEFAULT_SOCKET, DEFAULT_SPOOL_DIR, DEFAULT_VAR_DIR, hostname, _cfg_paths::key_dir, _cfg_paths::log_dir, LOG_WARNING, MAXHOSTNAMELEN, _cfg_paths::module_dir, _cfg_paths::monitor_dir, ast_variable::name, ast_variable::next, _cfg_paths::pid_path, _cfg_paths::run_dir, _cfg_paths::socket_path, _cfg_paths::spool_dir, ast_variable::value, and _cfg_paths::var_dir.

Referenced by main().

02645 {
02646    struct ast_config *cfg;
02647    struct ast_variable *v;
02648    char *config = DEFAULT_CONFIG_FILE;
02649    char hostname[MAXHOSTNAMELEN] = "";
02650    struct ast_flags config_flags = { 0 };
02651    struct {
02652       unsigned int dbdir:1;
02653       unsigned int keydir:1;
02654    } found = { 0, 0 };
02655 
02656    if (ast_opt_override_config) {
02657       cfg = ast_config_load2(ast_config_AST_CONFIG_FILE, "" /* core, can't reload */, config_flags);
02658       if (!cfg)
02659          ast_log(LOG_WARNING, "Unable to open specified master config file '%s', using built-in defaults\n", ast_config_AST_CONFIG_FILE);
02660    } else 
02661       cfg = ast_config_load2(config, "" /* core, can't reload */, config_flags);
02662 
02663    /* init with buildtime config */
02664    ast_copy_string(cfg_paths.config_dir, DEFAULT_CONFIG_DIR, sizeof(cfg_paths.config_dir));
02665    ast_copy_string(cfg_paths.spool_dir, DEFAULT_SPOOL_DIR, sizeof(cfg_paths.spool_dir));
02666    ast_copy_string(cfg_paths.module_dir, DEFAULT_MODULE_DIR, sizeof(cfg_paths.module_dir));
02667    snprintf(cfg_paths.monitor_dir, sizeof(cfg_paths.monitor_dir), "%s/monitor", cfg_paths.spool_dir);
02668    ast_copy_string(cfg_paths.var_dir, DEFAULT_VAR_DIR, sizeof(cfg_paths.var_dir));
02669    ast_copy_string(cfg_paths.data_dir, DEFAULT_DATA_DIR, sizeof(cfg_paths.data_dir));
02670    ast_copy_string(cfg_paths.log_dir, DEFAULT_LOG_DIR, sizeof(cfg_paths.log_dir));
02671    ast_copy_string(cfg_paths.agi_dir, DEFAULT_AGI_DIR, sizeof(cfg_paths.agi_dir));
02672    ast_copy_string(cfg_paths.db_path, DEFAULT_DB, sizeof(cfg_paths.db_path));
02673    ast_copy_string(cfg_paths.key_dir, DEFAULT_KEY_DIR, sizeof(cfg_paths.key_dir));
02674    ast_copy_string(cfg_paths.pid_path, DEFAULT_PID, sizeof(cfg_paths.pid_path));
02675    ast_copy_string(cfg_paths.socket_path, DEFAULT_SOCKET, sizeof(cfg_paths.socket_path));
02676    ast_copy_string(cfg_paths.run_dir, DEFAULT_RUN_DIR, sizeof(cfg_paths.run_dir));
02677 
02678    ast_set_default_eid(&ast_eid_default);
02679 
02680    /* no asterisk.conf? no problem, use buildtime config! */
02681    if (!cfg) {
02682       return;
02683    }
02684 
02685    for (v = ast_variable_browse(cfg, "files"); v; v = v->next) {
02686       if (!strcasecmp(v->name, "astctlpermissions"))
02687          ast_copy_string(ast_config_AST_CTL_PERMISSIONS, v->value, sizeof(ast_config_AST_CTL_PERMISSIONS));
02688       else if (!strcasecmp(v->name, "astctlowner"))
02689          ast_copy_string(ast_config_AST_CTL_OWNER, v->value, sizeof(ast_config_AST_CTL_OWNER));
02690       else if (!strcasecmp(v->name, "astctlgroup"))
02691          ast_copy_string(ast_config_AST_CTL_GROUP, v->value, sizeof(ast_config_AST_CTL_GROUP));
02692       else if (!strcasecmp(v->name, "astctl"))
02693          ast_copy_string(ast_config_AST_CTL, v->value, sizeof(ast_config_AST_CTL));
02694    }
02695 
02696    for (v = ast_variable_browse(cfg, "directories"); v; v = v->next) {
02697       if (!strcasecmp(v->name, "astetcdir")) {
02698          ast_copy_string(cfg_paths.config_dir, v->value, sizeof(cfg_paths.config_dir));
02699       } else if (!strcasecmp(v->name, "astspooldir")) {
02700          ast_copy_string(cfg_paths.spool_dir, v->value, sizeof(cfg_paths.spool_dir));
02701          snprintf(cfg_paths.monitor_dir, sizeof(cfg_paths.monitor_dir), "%s/monitor", v->value);
02702       } else if (!strcasecmp(v->name, "astvarlibdir")) {
02703          ast_copy_string(cfg_paths.var_dir, v->value, sizeof(cfg_paths.var_dir));
02704          if (!found.dbdir)
02705             snprintf(cfg_paths.db_path, sizeof(cfg_paths.db_path), "%s/astdb", v->value);
02706       } else if (!strcasecmp(v->name, "astdbdir")) {
02707          snprintf(cfg_paths.db_path, sizeof(cfg_paths.db_path), "%s/astdb", v->value);
02708          found.dbdir = 1;
02709       } else if (!strcasecmp(v->name, "astdatadir")) {
02710          ast_copy_string(cfg_paths.data_dir, v->value, sizeof(cfg_paths.data_dir));
02711          if (!found.keydir)
02712             snprintf(cfg_paths.key_dir, sizeof(cfg_paths.key_dir), "%s/keys", v->value);
02713       } else if (!strcasecmp(v->name, "astkeydir")) {
02714          snprintf(cfg_paths.key_dir, sizeof(cfg_paths.key_dir), "%s/keys", v->value);
02715          found.keydir = 1;
02716       } else if (!strcasecmp(v->name, "astlogdir")) {
02717          ast_copy_string(cfg_paths.log_dir, v->value, sizeof(cfg_paths.log_dir));
02718       } else if (!strcasecmp(v->name, "astagidir")) {
02719          ast_copy_string(cfg_paths.agi_dir, v->value, sizeof(cfg_paths.agi_dir));
02720       } else if (!strcasecmp(v->name, "astrundir")) {
02721          snprintf(cfg_paths.pid_path, sizeof(cfg_paths.pid_path), "%s/%s", v->value, "asterisk.pid");
02722          snprintf(cfg_paths.socket_path, sizeof(cfg_paths.socket_path), "%s/%s", v->value, ast_config_AST_CTL);
02723          ast_copy_string(cfg_paths.run_dir, v->value, sizeof(cfg_paths.run_dir));
02724       } else if (!strcasecmp(v->name, "astmoddir")) {
02725          ast_copy_string(cfg_paths.module_dir, v->value, sizeof(cfg_paths.module_dir));
02726       }
02727    }
02728 
02729    for (v = ast_variable_browse(cfg, "options"); v; v = v->next) {
02730       /* verbose level (-v at startup) */
02731       if (!strcasecmp(v->name, "verbose")) {
02732          option_verbose = atoi(v->value);
02733       /* whether or not to force timestamping in CLI verbose output. (-T at startup) */
02734       } else if (!strcasecmp(v->name, "timestamp")) {
02735          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TIMESTAMP);
02736       /* whether or not to support #exec in config files */
02737       } else if (!strcasecmp(v->name, "execincludes")) {
02738          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_EXEC_INCLUDES);
02739       /* debug level (-d at startup) */
02740       } else if (!strcasecmp(v->name, "debug")) {
02741          option_debug = 0;
02742          if (sscanf(v->value, "%d", &option_debug) != 1) {
02743             option_debug = ast_true(v->value);
02744          }
02745 #if HAVE_WORKING_FORK
02746       /* Disable forking (-f at startup) */
02747       } else if (!strcasecmp(v->name, "nofork")) {
02748          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_NO_FORK);
02749       /* Always fork, even if verbose or debug are enabled (-F at startup) */
02750       } else if (!strcasecmp(v->name, "alwaysfork")) {
02751          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_ALWAYS_FORK);
02752 #endif
02753       /* Run quietly (-q at startup ) */
02754       } else if (!strcasecmp(v->name, "quiet")) {
02755          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_QUIET);
02756       /* Run as console (-c at startup, implies nofork) */
02757       } else if (!strcasecmp(v->name, "console")) {
02758          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_CONSOLE);
02759       /* Run with high priority if the O/S permits (-p at startup) */
02760       } else if (!strcasecmp(v->name, "highpriority")) {
02761          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_HIGH_PRIORITY);
02762       /* Initialize RSA auth keys (IAX2) (-i at startup) */
02763       } else if (!strcasecmp(v->name, "initcrypto")) {
02764          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_INIT_KEYS);
02765       /* Disable ANSI colors for console (-c at startup) */
02766       } else if (!strcasecmp(v->name, "nocolor")) {
02767          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_NO_COLOR);
02768       /* Disable some usage warnings for picky people :p */
02769       } else if (!strcasecmp(v->name, "dontwarn")) {
02770          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_DONT_WARN);
02771       /* Dump core in case of crash (-g) */
02772       } else if (!strcasecmp(v->name, "dumpcore")) {
02773          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_DUMP_CORE);
02774       /* Cache recorded sound files to another directory during recording */
02775       } else if (!strcasecmp(v->name, "cache_record_files")) {
02776          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_CACHE_RECORD_FILES);
02777       /* Specify cache directory */
02778       }  else if (!strcasecmp(v->name, "record_cache_dir")) {
02779          ast_copy_string(record_cache_dir, v->value, AST_CACHE_DIR_LEN);
02780       /* Build transcode paths via SLINEAR, instead of directly */
02781       } else if (!strcasecmp(v->name, "transcode_via_sln")) {
02782          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TRANSCODE_VIA_SLIN);
02783       /* Transmit SLINEAR silence while a channel is being recorded or DTMF is being generated on a channel */
02784       } else if (!strcasecmp(v->name, "transmit_silence_during_record") || !strcasecmp(v->name, "transmit_silence")) {
02785          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TRANSMIT_SILENCE);
02786       /* Enable internal timing */
02787       } else if (!strcasecmp(v->name, "internal_timing")) {
02788          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_INTERNAL_TIMING);
02789       } else if (!strcasecmp(v->name, "maxcalls")) {
02790          if ((sscanf(v->value, "%d", &option_maxcalls) != 1) || (option_maxcalls < 0)) {
02791             option_maxcalls = 0;
02792          }
02793       } else if (!strcasecmp(v->name, "maxload")) {
02794          double test[1];
02795 
02796          if (getloadavg(test, 1) == -1) {
02797             ast_log(LOG_ERROR, "Cannot obtain load average on this system. 'maxload' option disabled.\n");
02798             option_maxload = 0.0;
02799          } else if ((sscanf(v->value, "%lf", &option_maxload) != 1) || (option_maxload < 0.0)) {
02800             option_maxload = 0.0;
02801          }
02802       /* Set the maximum amount of open files */
02803       } else if (!strcasecmp(v->name, "maxfiles")) {
02804          option_maxfiles = atoi(v->value);
02805          set_ulimit(option_maxfiles);
02806       /* What user to run as */
02807       } else if (!strcasecmp(v->name, "runuser")) {
02808          ast_copy_string(cfg_paths.run_user, v->value, sizeof(cfg_paths.run_user));
02809       /* What group to run as */
02810       } else if (!strcasecmp(v->name, "rungroup")) {
02811          ast_copy_string(cfg_paths.run_group, v->value, sizeof(cfg_paths.run_group));
02812       } else if (!strcasecmp(v->name, "systemname")) {
02813          ast_copy_string(cfg_paths.system_name, v->value, sizeof(cfg_paths.system_name));
02814       } else if (!strcasecmp(v->name, "autosystemname")) {
02815          if (ast_true(v->value)) {
02816             if (!gethostname(hostname, sizeof(hostname) - 1))
02817                ast_copy_string(cfg_paths.system_name, hostname, sizeof(cfg_paths.system_name));
02818             else {
02819                if (ast_strlen_zero(ast_config_AST_SYSTEM_NAME)){
02820                   ast_copy_string(cfg_paths.system_name, "localhost", sizeof(cfg_paths.system_name));
02821                }
02822                ast_log(LOG_ERROR, "Cannot obtain hostname for this system.  Using '%s' instead.\n", ast_config_AST_SYSTEM_NAME);
02823             }
02824          }
02825       } else if (!strcasecmp(v->name, "languageprefix")) {
02826          ast_language_is_prefix = ast_true(v->value);
02827       } else if (!strcasecmp(v->name, "lockmode")) {
02828          if (!strcasecmp(v->value, "lockfile")) {
02829             ast_set_lock_type(AST_LOCK_TYPE_LOCKFILE);
02830          } else if (!strcasecmp(v->value, "flock")) {
02831             ast_set_lock_type(AST_LOCK_TYPE_FLOCK);
02832          } else {
02833             ast_log(LOG_WARNING, "'%s' is not a valid setting for the lockmode option, "
02834                "defaulting to 'lockfile'\n", v->value);
02835             ast_set_lock_type(AST_LOCK_TYPE_LOCKFILE);
02836          }
02837 #if defined(HAVE_SYSINFO)
02838       } else if (!strcasecmp(v->name, "minmemfree")) {
02839          /* specify the minimum amount of free memory to retain.  Asterisk should stop accepting new calls
02840           * if the amount of free memory falls below this watermark */
02841          if ((sscanf(v->value, "%ld", &option_minmemfree) != 1) || (option_minmemfree < 0)) {
02842             option_minmemfree = 0;
02843          }
02844 #endif
02845       } else if (!strcasecmp(v->name, "entityid")) {
02846          struct ast_eid tmp_eid;
02847          if (!ast_str_to_eid(&tmp_eid, v->value)) {
02848             ast_verbose("Successfully set global EID to '%s'\n", v->value);
02849             ast_eid_default = tmp_eid;
02850          } else
02851             ast_verbose("Invalid Entity ID '%s' provided\n", v->value);
02852       }
02853    }
02854    for (v = ast_variable_browse(cfg, "compat"); v; v = v->next) {
02855       float version;
02856       if (sscanf(v->value, "%f", &version) != 1) {
02857          ast_log(LOG_WARNING, "Compatibility version for option '%s' is not a number: '%s'\n", v->name, v->value);
02858          continue;
02859       }
02860       if (!strcasecmp(v->name, "app_set")) {
02861          ast_set2_flag(&ast_compat, version < 1.5 ? 1 : 0, AST_COMPAT_APP_SET);
02862       } else if (!strcasecmp(v->name, "res_agi")) {
02863          ast_set2_flag(&ast_compat, version < 1.5 ? 1 : 0, AST_COMPAT_DELIM_RES_AGI);
02864       } else if (!strcasecmp(v->name, "pbx_realtime")) {
02865          ast_set2_flag(&ast_compat, version < 1.5 ? 1 : 0, AST_COMPAT_DELIM_PBX_REALTIME);
02866       }
02867    }
02868    ast_config_destroy(cfg);
02869 }

int ast_register_atexit ( void(*)(void)  func  ) 

Register a function to be executed before Asterisk exits.

Parameters:
func The callback function to use.
Return values:
0 on success.
-1 on error.

Definition at line 773 of file asterisk.c.

References ast_calloc, AST_RWLIST_INSERT_HEAD, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_unregister_atexit(), and ast_atexit::list.

Referenced by do_reload(), and load_module().

00774 {
00775    struct ast_atexit *ae;
00776 
00777    if (!(ae = ast_calloc(1, sizeof(*ae))))
00778       return -1;
00779 
00780    ae->func = func;
00781 
00782    ast_unregister_atexit(func);  
00783 
00784    AST_RWLIST_WRLOCK(&atexits);
00785    AST_RWLIST_INSERT_HEAD(&atexits, ae, list);
00786    AST_RWLIST_UNLOCK(&atexits);
00787 
00788    return 0;
00789 }

void ast_register_file_version ( const char *  file,
const char *  version 
)

Register the version of a source code file with the core.

Parameters:
file the source file name
version the version string (typically a CVS revision keyword string)
Returns:
nothing
This function should not be called directly, but instead the ASTERISK_FILE_VERSION macro should be used to register a file with the core.

Definition at line 282 of file asterisk.c.

References ast_calloc, AST_RWLIST_INSERT_HEAD, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_strdupa, ast_strip(), ast_strip_quoted(), and ast_atexit::list.

00283 {
00284    struct file_version *new;
00285    char *work;
00286    size_t version_length;
00287 
00288    work = ast_strdupa(version);
00289    work = ast_strip(ast_strip_quoted(work, "$", "$"));
00290    version_length = strlen(work) + 1;
00291    
00292    if (!(new = ast_calloc(1, sizeof(*new) + version_length)))
00293       return;
00294 
00295    new->file = file;
00296    new->version = (char *) new + sizeof(*new);
00297    memcpy(new->version, work, version_length);
00298    AST_RWLIST_WRLOCK(&file_versions);
00299    AST_RWLIST_INSERT_HEAD(&file_versions, new, list);
00300    AST_RWLIST_UNLOCK(&file_versions);
00301 }

void ast_register_thread ( char *  name  ) 

Definition at line 348 of file asterisk.c.

References ast_calloc, AST_RWLIST_INSERT_HEAD, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, and ast_atexit::list.

Referenced by dummy_start().

00349 { 
00350    struct thread_list_t *new = ast_calloc(1, sizeof(*new));
00351 
00352    if (!new)
00353       return;
00354    new->id = pthread_self();
00355    new->name = name; /* steal the allocated memory for the thread name */
00356    AST_RWLIST_WRLOCK(&thread_list);
00357    AST_RWLIST_INSERT_HEAD(&thread_list, new, list);
00358    AST_RWLIST_UNLOCK(&thread_list);
00359 }

static void ast_remotecontrol ( char *  data  )  [static]

Definition at line 2458 of file asterisk.c.

References __remote_quit_handler(), ast_el_initialize(), ast_el_read_char(), ast_el_read_history(), ast_log(), ast_opt_exec, ast_opt_mute, ast_poll, ast_strlen_zero(), ast_verbose, el, el_hist, errno, fdsend(), hostname, LOG_ERROR, LOG_WARNING, num, prefix, remoteconsolehandler(), remotehostname, sig_flags, strsep(), and version.

Referenced by main().

02459 {
02460    char buf[80];
02461    int res;
02462    char filename[80] = "";
02463    char *hostname;
02464    char *cpid;
02465    char *version;
02466    int pid;
02467    char *stringp = NULL;
02468 
02469    char *ebuf;
02470    int num = 0;
02471 
02472    memset(&sig_flags, 0, sizeof(sig_flags));
02473    signal(SIGINT, __remote_quit_handler);
02474    signal(SIGTERM, __remote_quit_handler);
02475    signal(SIGHUP, __remote_quit_handler);
02476 
02477    if (read(ast_consock, buf, sizeof(buf)) < 0) {
02478       ast_log(LOG_ERROR, "read() failed: %s\n", strerror(errno));
02479       return;
02480    }
02481    if (data) {
02482       char prefix[] = "cli quit after ";
02483       char *tmp = alloca(strlen(data) + strlen(prefix) + 1);
02484       sprintf(tmp, "%s%s", prefix, data);
02485       if (write(ast_consock, tmp, strlen(tmp) + 1) < 0) {
02486          ast_log(LOG_ERROR, "write() failed: %s\n", strerror(errno));
02487          if (sig_flags.need_quit == 1) {
02488             return;
02489          }
02490       }
02491    }
02492    stringp = buf;
02493    hostname = strsep(&stringp, "/");
02494    cpid = strsep(&stringp, "/");
02495    version = strsep(&stringp, "\n");
02496    if (!version)
02497       version = "<Version Unknown>";
02498    stringp = hostname;
02499    strsep(&stringp, ".");
02500    if (cpid)
02501       pid = atoi(cpid);
02502    else
02503       pid = -1;
02504    if (!data) {
02505       char tmp[80];
02506       snprintf(tmp, sizeof(tmp), "core set verbose atleast %d", option_verbose);
02507       fdsend(ast_consock, tmp);
02508       snprintf(tmp, sizeof(tmp), "core set debug atleast %d", option_debug);
02509       fdsend(ast_consock, tmp);
02510       if (!ast_opt_mute)
02511          fdsend(ast_consock, "logger mute silent");
02512       else 
02513          printf("log and verbose output currently muted ('logger mute' to unmute)\n");
02514    }
02515    ast_verbose("Connected to Asterisk %s currently running on %s (pid = %d)\n", version, hostname, pid);
02516    remotehostname = hostname;
02517    if (getenv("HOME")) 
02518       snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
02519    if (el_hist == NULL || el == NULL)
02520       ast_el_initialize();
02521 
02522    el_set(el, EL_GETCFN, ast_el_read_char);
02523 
02524    if (!ast_strlen_zero(filename))
02525       ast_el_read_history(filename);
02526 
02527    if (ast_opt_exec && data) {  /* hack to print output then exit if asterisk -rx is used */
02528       struct pollfd fds;
02529       fds.fd = ast_consock;
02530       fds.events = POLLIN;
02531       fds.revents = 0;
02532       while (ast_poll(&fds, 1, 500) > 0) {
02533          char buffer[512] = "", *curline = buffer, *nextline;
02534          int not_written = 1;
02535 
02536          if (sig_flags.need_quit == 1) {
02537             break;
02538          }
02539 
02540          if (read(ast_consock, buffer, sizeof(buffer) - 1) <= 0) {
02541             break;
02542          }
02543 
02544          do {
02545             if ((nextline = strchr(curline, '\n'))) {
02546                nextline++;
02547             } else {
02548                nextline = strchr(curline, '\0');
02549             }
02550 
02551             /* Skip verbose lines */
02552             if (*curline != 127) {
02553                not_written = 0;
02554                if (write(STDOUT_FILENO, curline, nextline - curline) < 0) {
02555                   ast_log(LOG_WARNING, "write() failed: %s\n", strerror(errno));
02556                }
02557             }
02558             curline = nextline;
02559          } while (!ast_strlen_zero(curline));
02560 
02561          /* No non-verbose output in 500ms */
02562          if (not_written) {
02563             break;
02564          }
02565       }
02566       return;
02567    }
02568    for (;;) {
02569       ebuf = (char *)el_gets(el, &num);
02570 
02571       if (sig_flags.need_quit == 1) {
02572          break;
02573       }
02574 
02575       if (!ebuf && write(1, "", 1) < 0)
02576          break;
02577 
02578       if (!ast_strlen_zero(ebuf)) {
02579          if (ebuf[strlen(ebuf)-1] == '\n')
02580             ebuf[strlen(ebuf)-1] = '\0';
02581          if (!remoteconsolehandler(ebuf)) {
02582             /* Strip preamble from output */
02583             char *temp;
02584             for (temp = ebuf; *temp; temp++) {
02585                if (*temp == 127) {
02586                   memmove(temp, temp + 1, strlen(temp));
02587                   temp--;
02588                }
02589             }
02590             res = write(ast_consock, ebuf, strlen(ebuf) + 1);
02591             if (res < 1) {
02592                ast_log(LOG_WARNING, "Unable to write: %s\n", strerror(errno));
02593                break;
02594             }
02595          }
02596       }
02597    }
02598    printf("\nDisconnected from Asterisk server\n");
02599 }

void ast_replace_sigchld ( void   ) 

Replace the SIGCHLD handler.

Normally, Asterisk has a SIGCHLD handler that is cleaning up all zombie processes from forking elsewhere in Asterisk. However, if you want to wait*() on the process to retrieve information about it's exit status, then this signal handler needs to be temporarily replaced.

Code that executes this function *must* call ast_unreplace_sigchld() after it is finished doing the wait*().

Definition at line 833 of file asterisk.c.

References ast_mutex_lock(), ast_mutex_unlock(), null_sig_handler(), safe_system_level, safe_system_lock, and safe_system_prev_handler.

Referenced by ast_safe_fork(), and ast_safe_system().

00834 {
00835    unsigned int level;
00836 
00837    ast_mutex_lock(&safe_system_lock);
00838    level = safe_system_level++;
00839 
00840    /* only replace the handler if it has not already been done */
00841    if (level == 0)
00842       safe_system_prev_handler = signal(SIGCHLD, null_sig_handler);
00843 
00844    ast_mutex_unlock(&safe_system_lock);
00845 }

static void ast_run_atexits ( void   )  [static]

Definition at line 1332 of file asterisk.c.

References AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_atexit::func, and ast_atexit::list.

Referenced by quit_handler().

01333 {
01334    struct ast_atexit *ae;
01335    AST_RWLIST_RDLOCK(&atexits);
01336    AST_RWLIST_TRAVERSE(&atexits, ae, list) {
01337       if (ae->func) 
01338          ae->func();
01339    }
01340    AST_RWLIST_UNLOCK(&atexits);
01341 }

int ast_safe_system ( const char *  s  ) 

Safely spawn an external program while closing file descriptors.

Note:
This replaces the system call in all Asterisk modules

Definition at line 861 of file asterisk.c.

References ast_close_fds_above_n(), ast_log(), ast_opt_high_priority, ast_replace_sigchld(), ast_set_priority(), ast_unreplace_sigchld(), errno, LOG_WARNING, status, WEXITSTATUS, and WIFEXITED.

Referenced by add_email_attachment(), alarmreceiver_exec(), ast_monitor_stop(), consolehandler(), filestream_destructor(), mixmonitor_thread(), notify_message(), process_text_line(), remoteconsolehandler(), rotate_file(), run_externnotify(), sendmail(), sendpage(), system_exec_helper(), and vm_change_password_shell().

00862 {
00863    pid_t pid;
00864    int res;
00865    struct rusage rusage;
00866    int status;
00867 
00868 #if defined(HAVE_WORKING_FORK) || defined(HAVE_WORKING_VFORK)
00869    ast_replace_sigchld();
00870 
00871 #ifdef HAVE_WORKING_FORK
00872    pid = fork();
00873 #else
00874    pid = vfork();
00875 #endif   
00876 
00877    if (pid == 0) {
00878 #ifdef HAVE_CAP
00879       cap_t cap = cap_from_text("cap_net_admin-eip");
00880 
00881       if (cap_set_proc(cap)) {
00882          /* Careful with order! Logging cannot happen after we close FDs */
00883          ast_log(LOG_WARNING, "Unable to remove capabilities.\n");
00884       }
00885       cap_free(cap);
00886 #endif
00887 #ifdef HAVE_WORKING_FORK
00888       if (ast_opt_high_priority)
00889          ast_set_priority(0);
00890       /* Close file descriptors and launch system command */
00891       ast_close_fds_above_n(STDERR_FILENO);
00892 #endif
00893       execl("/bin/sh", "/bin/sh", "-c", s, (char *) NULL);
00894       _exit(1);
00895    } else if (pid > 0) {
00896       for (;;) {
00897          res = wait4(pid, &status, 0, &rusage);
00898          if (res > -1) {
00899             res = WIFEXITED(status) ? WEXITSTATUS(status) : -1;
00900             break;
00901          } else if (errno != EINTR) 
00902             break;
00903       }
00904    } else {
00905       ast_log(LOG_WARNING, "Fork failed: %s\n", strerror(errno));
00906       res = -1;
00907    }
00908 
00909    ast_unreplace_sigchld();
00910 #else /* !defined(HAVE_WORKING_FORK) && !defined(HAVE_WORKING_VFORK) */
00911    res = -1;
00912 #endif
00913 
00914    return res;
00915 }

int ast_set_priority ( int   ) 

We set ourselves to a high priority, that we might pre-empt everything else. If your PBX has heavy activity on it, this is a good thing.

Provided by asterisk.c

Definition at line 1298 of file asterisk.c.

References ast_log(), ast_verbose, LOG_WARNING, sched_setscheduler, and setpriority.

Referenced by ast_safe_system(), canary_thread(), icesencode(), launch_script(), main(), mp3play(), NBScatplay(), send_waveform_to_fd(), spawn_mp3(), and spawn_ras().

01299 {
01300    struct sched_param sched;
01301    memset(&sched, 0, sizeof(sched));
01302 #ifdef __linux__
01303    if (pri) {  
01304       sched.sched_priority = 10;
01305       if (sched_setscheduler(0, SCHED_RR, &sched)) {
01306          ast_log(LOG_WARNING, "Unable to set high priority\n");
01307          return -1;
01308       } else
01309          if (option_verbose)
01310             ast_verbose("Set to realtime thread\n");
01311    } else {
01312       sched.sched_priority = 0;
01313       /* According to the manpage, these parameters can never fail. */
01314       sched_setscheduler(0, SCHED_OTHER, &sched);
01315    }
01316 #else
01317    if (pri) {
01318       if (setpriority(PRIO_PROCESS, 0, -10) == -1) {
01319          ast_log(LOG_WARNING, "Unable to set high priority\n");
01320          return -1;
01321       } else
01322          if (option_verbose)
01323             ast_verbose("Set to high priority\n");
01324    } else {
01325       /* According to the manpage, these parameters can never fail. */
01326       setpriority(PRIO_PROCESS, 0, 0);
01327    }
01328 #endif
01329    return 0;
01330 }

static int ast_tryconnect ( void   )  [static]

Definition at line 1196 of file asterisk.c.

References AF_LOCAL, ast_config_AST_SOCKET, ast_copy_string(), ast_log(), errno, LOG_WARNING, and PF_LOCAL.

Referenced by ast_el_read_char(), and main().

01197 {
01198    struct sockaddr_un sunaddr;
01199    int res;
01200    ast_consock = socket(PF_LOCAL, SOCK_STREAM, 0);
01201    if (ast_consock < 0) {
01202       ast_log(LOG_WARNING, "Unable to create socket: %s\n", strerror(errno));
01203       return 0;
01204    }
01205    memset(&sunaddr, 0, sizeof(sunaddr));
01206    sunaddr.sun_family = AF_LOCAL;
01207    ast_copy_string(sunaddr.sun_path, ast_config_AST_SOCKET, sizeof(sunaddr.sun_path));
01208    res = connect(ast_consock, (struct sockaddr *)&sunaddr, sizeof(sunaddr));
01209    if (res) {
01210       close(ast_consock);
01211       ast_consock = -1;
01212       return 0;
01213    } else
01214       return 1;
01215 }

void ast_unregister_atexit ( void(*)(void)  func  ) 

Unregister a function registered with ast_register_atexit().

Parameters:
func The callback function to unregister.

Definition at line 791 of file asterisk.c.

References AST_RWLIST_REMOVE_CURRENT, AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, free, ast_atexit::func, and ast_atexit::list.

Referenced by ast_register_atexit(), do_reload(), and unload_module().

00792 {
00793    struct ast_atexit *ae = NULL;
00794 
00795    AST_RWLIST_WRLOCK(&atexits);
00796    AST_RWLIST_TRAVERSE_SAFE_BEGIN(&atexits, ae, list) {
00797       if (ae->func == func) {
00798          AST_RWLIST_REMOVE_CURRENT(list);
00799          break;
00800       }
00801    }
00802    AST_RWLIST_TRAVERSE_SAFE_END;
00803    AST_RWLIST_UNLOCK(&atexits);
00804 
00805    if (ae)
00806       free(ae);
00807 }

void ast_unregister_file_version ( const char *  file  ) 

Unregister a source code file from the core.

Parameters:
file the source file name
Returns:
nothing
This function should not be called directly, but instead the ASTERISK_FILE_VERSION macro should be used to automatically unregister the file when the module is unloaded.

Definition at line 303 of file asterisk.c.

References ast_free, AST_RWLIST_REMOVE_CURRENT, AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, file_version::file, and ast_atexit::list.

00304 {
00305    struct file_version *find;
00306 
00307    AST_RWLIST_WRLOCK(&file_versions);
00308    AST_RWLIST_TRAVERSE_SAFE_BEGIN(&file_versions, find, list) {
00309       if (!strcasecmp(find->file, file)) {
00310          AST_RWLIST_REMOVE_CURRENT(list);
00311          break;
00312       }
00313    }
00314    AST_RWLIST_TRAVERSE_SAFE_END;
00315    AST_RWLIST_UNLOCK(&file_versions);
00316 
00317    if (find)
00318       ast_free(find);
00319 }

void ast_unregister_thread ( void *  id  ) 

Definition at line 361 of file asterisk.c.

References ast_free, AST_RWLIST_REMOVE_CURRENT, AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, thread_list_t::id, ast_atexit::list, and thread_list_t::name.

Referenced by dummy_start().

00362 {
00363    struct thread_list_t *x;
00364 
00365    AST_RWLIST_WRLOCK(&thread_list);
00366    AST_RWLIST_TRAVERSE_SAFE_BEGIN(&thread_list, x, list) {
00367       if ((void *) x->id == id) {
00368          AST_RWLIST_REMOVE_CURRENT(list);
00369          break;
00370       }
00371    }
00372    AST_RWLIST_TRAVERSE_SAFE_END;
00373    AST_RWLIST_UNLOCK(&thread_list);
00374    if (x) {
00375       ast_free(x->name);
00376       ast_free(x);
00377    }
00378 }

void ast_unreplace_sigchld ( void   ) 

Restore the SIGCHLD handler.

This function is called after a call to ast_replace_sigchld. It restores the SIGCHLD handler that cleans up any zombie processes.

Definition at line 847 of file asterisk.c.

References ast_mutex_lock(), ast_mutex_unlock(), safe_system_level, safe_system_lock, and safe_system_prev_handler.

Referenced by ast_safe_fork_cleanup(), and ast_safe_system().

00848 {
00849    unsigned int level;
00850 
00851    ast_mutex_lock(&safe_system_lock);
00852    level = --safe_system_level;
00853 
00854    /* only restore the handler if we are the last one */
00855    if (level == 0)
00856       signal(SIGCHLD, safe_system_prev_handler);
00857 
00858    ast_mutex_unlock(&safe_system_lock);
00859 }

static void canary_exit ( void   )  [static]

Definition at line 2915 of file asterisk.c.

References canary_pid.

Referenced by main().

02916 {
02917    if (canary_pid > 0)
02918       kill(canary_pid, SIGKILL);
02919 }

static void* canary_thread ( void *  unused  )  [static]

Definition at line 2892 of file asterisk.c.

References ast_log(), ast_set_priority(), ast_tvnow(), canary_filename, and LOG_WARNING.

Referenced by main().

02893 {
02894    struct stat canary_stat;
02895    struct timeval now;
02896 
02897    /* Give the canary time to sing */
02898    sleep(120);
02899 
02900    for (;;) {
02901       stat(canary_filename, &canary_stat);
02902       now = ast_tvnow();
02903       if (now.tv_sec > canary_stat.st_mtime + 60) {
02904          ast_log(LOG_WARNING, "The canary is no more.  He has ceased to be!  He's expired and gone to meet his maker!  He's a stiff!  Bereft of life, he rests in peace.  His metabolic processes are now history!  He's off the twig!  He's kicked the bucket.  He's shuffled off his mortal coil, run down the curtain, and joined the bleeding choir invisible!!  THIS is an EX-CANARY.  (Reducing priority)\n");
02905          ast_set_priority(0);
02906          pthread_exit(NULL);
02907       }
02908 
02909       /* Check the canary once a minute */
02910       sleep(60);
02911    }
02912 }

static void child_handler ( int  sig  )  [static]

Definition at line 1245 of file asterisk.c.

References status.

Referenced by main().

01246 {
01247    /* Must not ever ast_log or ast_verbose within signal handler */
01248    int n, status;
01249 
01250    /*
01251     * Reap all dead children -- not just one
01252     */
01253    for (n = 0; wait4(-1, &status, WNOHANG, NULL) > 0; n++)
01254       ;
01255    if (n == 0 && option_debug)   
01256       printf("Huh?  Child handler, but nobody there?\n");
01257    signal(sig, child_handler);
01258 }

static char* cli_complete ( EditLine *  editline,
int  ch 
) [static]

Definition at line 2256 of file asterisk.c.

References AST_CLI_COMPLETE_EOF, ast_cli_completion_matches(), ast_cli_display_match_list(), ast_el_strtoarr(), ast_free, ast_malloc, ast_opt_remote, ast_realloc, fdsend(), and len().

Referenced by ast_el_initialize().

02257 {
02258    int len = 0;
02259    char *ptr;
02260    int nummatches = 0;
02261    char **matches;
02262    int retval = CC_ERROR;
02263    char buf[2048], savechr;
02264    int res;
02265 
02266    LineInfo *lf = (LineInfo *)el_line(editline);
02267 
02268    savechr = *(char *)lf->cursor;
02269    *(char *)lf->cursor = '\0';
02270    ptr = (char *)lf->cursor;
02271    if (ptr) {
02272       while (ptr > lf->buffer) {
02273          if (isspace(*ptr)) {
02274             ptr++;
02275             break;
02276          }
02277          ptr--;
02278       }
02279    }
02280 
02281    len = lf->cursor - ptr;
02282 
02283    if (ast_opt_remote) {
02284       snprintf(buf, sizeof(buf), "_COMMAND NUMMATCHES \"%s\" \"%s\"", lf->buffer, ptr); 
02285       fdsend(ast_consock, buf);
02286       res = read(ast_consock, buf, sizeof(buf));
02287       buf[res] = '\0';
02288       nummatches = atoi(buf);
02289 
02290       if (nummatches > 0) {
02291          char *mbuf;
02292          int mlen = 0, maxmbuf = 2048;
02293          /* Start with a 2048 byte buffer */       
02294          if (!(mbuf = ast_malloc(maxmbuf))) {
02295             lf->cursor[0] = savechr;
02296             return (char *)(CC_ERROR);
02297          }
02298          snprintf(buf, sizeof(buf), "_COMMAND MATCHESARRAY \"%s\" \"%s\"", lf->buffer, ptr); 
02299          fdsend(ast_consock, buf);
02300          res = 0;
02301          mbuf[0] = '\0';
02302          while (!strstr(mbuf, AST_CLI_COMPLETE_EOF) && res != -1) {
02303             if (mlen + 1024 > maxmbuf) {
02304                /* Every step increment buffer 1024 bytes */
02305                maxmbuf += 1024;              
02306                if (!(mbuf = ast_realloc(mbuf, maxmbuf))) {
02307                   lf->cursor[0] = savechr;
02308                   return (char *)(CC_ERROR);
02309                }
02310             }
02311             /* Only read 1024 bytes at a time */
02312             res = read(ast_consock, mbuf + mlen, 1024);
02313             if (res > 0)
02314                mlen += res;
02315          }
02316          mbuf[mlen] = '\0';
02317 
02318          matches = ast_el_strtoarr(mbuf);
02319          ast_free(mbuf);
02320       } else
02321          matches = (char **) NULL;
02322    } else {
02323       char **p, *oldbuf=NULL;
02324       nummatches = 0;
02325       matches = ast_cli_completion_matches((char *)lf->buffer,ptr);
02326       for (p = matches; p && *p; p++) {
02327          if (!oldbuf || strcmp(*p,oldbuf))
02328             nummatches++;
02329          oldbuf = *p;
02330       }
02331    }
02332 
02333    if (matches) {
02334       int i;
02335       int matches_num, maxlen, match_len;
02336 
02337       if (matches[0][0] != '\0') {
02338          el_deletestr(editline, (int) len);
02339          el_insertstr(editline, matches[0]);
02340          retval = CC_REFRESH;
02341       }
02342 
02343       if (nummatches == 1) {
02344          /* Found an exact match */
02345          el_insertstr(editline, " ");
02346          retval = CC_REFRESH;
02347       } else {
02348          /* Must be more than one match */
02349          for (i = 1, maxlen = 0; matches[i]; i++) {
02350             match_len = strlen(matches[i]);
02351             if (match_len > maxlen)
02352                maxlen = match_len;
02353          }
02354          matches_num = i - 1;
02355          if (matches_num >1) {
02356             fprintf(stdout, "\n");
02357             ast_cli_display_match_list(matches, nummatches, maxlen);
02358             retval = CC_REDISPLAY;
02359          } else { 
02360             el_insertstr(editline," ");
02361             retval = CC_REFRESH;
02362          }
02363       }
02364       for (i = 0; matches[i]; i++)
02365          ast_free(matches[i]);
02366       ast_free(matches);
02367    }
02368 
02369    lf->cursor[0] = savechr;
02370 
02371    return (char *)(long)retval;
02372 }

static char* cli_prompt ( EditLine *  editline  )  [static]

Definition at line 2024 of file asterisk.c.

References ast_config_AST_SYSTEM_NAME, ast_localtime(), ast_opt_remote, ast_str_append(), ast_str_create(), ast_str_make_space(), ast_str_reset(), ast_str_set(), ast_strftime(), ast_tvnow(), ASTERISK_PROMPT, ASTERISK_PROMPT2, COLOR_BLACK, COLOR_WHITE, getloadavg(), hostname, ast_str::len, ast_atexit::list, MAXHOSTNAMELEN, prompt, remotehostname, ast_str::str, term_color_code(), and ast_str::used.

Referenced by ast_el_initialize().

02025 {
02026    char tmp[100];
02027    char *pfmt;
02028    int color_used = 0;
02029    static int cli_prompt_changes = 0;
02030    char term_code[20];
02031    struct passwd *pw;
02032    struct group *gr;
02033 
02034    if (prompt == NULL) {
02035       prompt = ast_str_create(100);
02036    } else if (!cli_prompt_changes) {
02037       return prompt->str;
02038    } else {
02039       ast_str_reset(prompt);
02040    }
02041 
02042    if ((pfmt = getenv("ASTERISK_PROMPT"))) {
02043       char *t = pfmt;
02044       struct timeval ts = ast_tvnow();
02045       while (*t != '\0') {
02046          if (*t == '%') {
02047             char hostname[MAXHOSTNAMELEN] = "";
02048             int i, which;
02049             struct ast_tm tm = { 0, };
02050             int fgcolor = COLOR_WHITE, bgcolor = COLOR_BLACK;
02051 
02052             t++;
02053             switch (*t) {
02054             case 'C': /* color */
02055                t++;
02056                if (sscanf(t, "%d;%d%n", &fgcolor, &bgcolor, &i) == 2) {
02057                   ast_str_append(&prompt, 0, "%s", term_color_code(term_code, fgcolor, bgcolor, sizeof(term_code)));
02058                   t += i - 1;
02059                } else if (sscanf(t, "%d%n", &fgcolor, &i) == 1) {
02060                   ast_str_append(&prompt, 0, "%s", term_color_code(term_code, fgcolor, 0, sizeof(term_code)));
02061                   t += i - 1;
02062                }
02063 
02064                /* If the color has been reset correctly, then there's no need to reset it later */
02065                color_used = ((fgcolor == COLOR_WHITE) && (bgcolor == COLOR_BLACK)) ? 0 : 1;
02066                break;
02067             case 'd': /* date */
02068                if (ast_localtime(&ts, &tm, NULL)) {
02069                   ast_strftime(tmp, sizeof(tmp), "%Y-%m-%d", &tm);
02070                   ast_str_append(&prompt, 0, "%s", tmp);
02071                   cli_prompt_changes++;
02072                }
02073                break;
02074             case 'g': /* group */
02075                if ((gr = getgrgid(getgid()))) {
02076                   ast_str_append(&prompt, 0, "%s", gr->gr_name);
02077                }
02078                break;
02079             case 'h': /* hostname */
02080                if (!gethostname(hostname, sizeof(hostname) - 1)) {
02081                   ast_str_append(&prompt, 0, "%s", hostname);
02082                } else {
02083                   ast_str_append(&prompt, 0, "%s", "localhost");
02084                }
02085                break;
02086             case 'H': /* short hostname */
02087                if (!gethostname(hostname, sizeof(hostname) - 1)) {
02088                   char *dotptr;
02089                   if ((dotptr = strchr(hostname, '.'))) {
02090                      *dotptr = '\0';
02091                   }
02092                   ast_str_append(&prompt, 0, "%s", hostname);
02093                } else {
02094                   ast_str_append(&prompt, 0, "%s", "localhost");
02095                }
02096                break;
02097 #ifdef HAVE_GETLOADAVG
02098             case 'l': /* load avg */
02099                t++;
02100                if (sscanf(t, "%d", &which) == 1 && which > 0 && which <= 3) {
02101                   double list[3];
02102                   getloadavg(list, 3);
02103                   ast_str_append(&prompt, 0, "%.2f", list[which - 1]);
02104                   cli_prompt_changes++;
02105                }
02106                break;
02107 #endif
02108             case 's': /* Asterisk system name (from asterisk.conf) */
02109                ast_str_append(&prompt, 0, "%s", ast_config_AST_SYSTEM_NAME);
02110                break;
02111             case 't': /* time */
02112                if (ast_localtime(&ts, &tm, NULL)) {
02113                   ast_strftime(tmp, sizeof(tmp), "%H:%M:%S", &tm);
02114                   ast_str_append(&prompt, 0, "%s", tmp);
02115                   cli_prompt_changes++;
02116                }
02117                break;
02118             case 'u': /* username */
02119                if ((pw = getpwuid(getuid()))) {
02120                   ast_str_append(&prompt, 0, "%s", pw->pw_name);
02121                }
02122                break;
02123             case '#': /* process console or remote? */
02124                ast_str_append(&prompt, 0, "%c", ast_opt_remote ? '>' : '#');
02125                break;
02126             case '%': /* literal % */
02127                ast_str_append(&prompt, 0, "%c", '%');
02128                break;
02129             case '\0': /* % is last character - prevent bug */
02130                t--;
02131                break;
02132             }
02133             t++;
02134          } else {
02135             if (prompt->used + 5 > prompt->len) {
02136                ast_str_make_space(&prompt, prompt->len + 5);
02137             }
02138             prompt->str[prompt->used++] = *t++;
02139             prompt->str[prompt->used] = '\0';
02140          }
02141       }
02142       if (color_used) {
02143          /* Force colors back to normal at end */
02144          ast_str_append(&prompt, 0, "%s", term_color_code(term_code, COLOR_WHITE, COLOR_BLACK, sizeof(term_code)));
02145       }
02146    } else if (remotehostname) {
02147       ast_str_set(&prompt, 0, ASTERISK_PROMPT2, remotehostname);
02148    } else {
02149       ast_str_set(&prompt, 0, "%s", ASTERISK_PROMPT);
02150    }
02151 
02152    return(prompt->str); 
02153 }

static void console_verboser ( const char *  s  )  [static]

Definition at line 1487 of file asterisk.c.

References ast_opt_console, AST_PTHREADT_NULL, consolethread, fix_header(), VERBOSE_PREFIX_1, VERBOSE_PREFIX_2, VERBOSE_PREFIX_3, and VERBOSE_PREFIX_4.

Referenced by main().

01488 {
01489    char tmp[80];
01490    const char *c = NULL;
01491 
01492    if ((c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_4)) ||
01493        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_3)) ||
01494        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_2)) ||
01495        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_1))) {
01496       fputs(tmp, stdout);
01497       fputs(c, stdout);
01498    } else {
01499       if (*s == 127) {
01500          s++;
01501       }
01502       fputs(s, stdout);
01503    }
01504 
01505    fflush(stdout);
01506    
01507    /* Wake up a poll()ing console */
01508    if (ast_opt_console && consolethread != AST_PTHREADT_NULL)
01509       pthread_kill(consolethread, SIGURG);
01510 }

static void consolehandler ( char *  s  )  [static]

Definition at line 1522 of file asterisk.c.

References ast_all_zeros(), ast_cli_command(), ast_el_add_history(), ast_safe_system(), and term_end().

Referenced by main().

01523 {
01524    printf("%s", term_end());
01525    fflush(stdout);
01526 
01527    /* Called when readline data is available */
01528    if (!ast_all_zeros(s))
01529       ast_el_add_history(s);
01530    /* The real handler for bang */
01531    if (s[0] == '!') {
01532       if (s[1])
01533          ast_safe_system(s+1);
01534       else
01535          ast_safe_system(getenv("SHELL") ? getenv("SHELL") : "/bin/sh");
01536    } else 
01537       ast_cli_command(STDOUT_FILENO, s);
01538 }

static int fdprint ( int  fd,
const char *  s 
) [static]

Definition at line 816 of file asterisk.c.

Referenced by ast_network_puts(), ast_network_puts_mutable(), listener(), and netconsole().

00817 {
00818    return write(fd, s, strlen(s));
00819 }

static int fdsend ( int  fd,
const char *  s 
) [static]

Definition at line 810 of file asterisk.c.

Referenced by ast_el_read_char(), ast_remotecontrol(), and cli_complete().

00811 {
00812    return write(fd, s, strlen(s) + 1);
00813 }

static const char* fix_header ( char *  outbuf,
int  maxout,
const char *  s,
char *  cmp 
) [static]

Definition at line 1470 of file asterisk.c.

References COLOR_GRAY, and term_color().

Referenced by console_verboser().

01471 {
01472    const char *c;
01473 
01474    /* Check for verboser preamble */
01475    if (*s == 127) {
01476       s++;
01477    }
01478 
01479    if (!strncmp(s, cmp, strlen(cmp))) {
01480       c = s + strlen(cmp);
01481       term_color(outbuf, cmp, COLOR_GRAY, 0, maxout);
01482       return c;
01483    }
01484    return NULL;
01485 }

static char* handle_abort_shutdown ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1762 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, ast_cancel_shutdown(), CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, shuttingdown, and ast_cli_entry::usage.

Referenced by handle_abort_shutdown_deprecated().

01763 {
01764    switch (cmd) {
01765    case CLI_INIT:
01766       e->command = "core abort shutdown";
01767       e->usage = 
01768          "Usage: core abort shutdown\n"
01769          "       Causes Asterisk to abort an executing shutdown or restart, and resume normal\n"
01770          "       call operations.\n";
01771       return NULL;
01772    case CLI_GENERATE:
01773       return NULL;
01774    }
01775 
01776    if (a->argc != e->args)
01777       return CLI_SHOWUSAGE;
01778    ast_cancel_shutdown();
01779    shuttingdown = 0;
01780    return CLI_SUCCESS;
01781 }

static char* handle_abort_shutdown_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1783 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_abort_shutdown().

01784 {
01785    char *res = handle_abort_shutdown(e, cmd, a);
01786    if (cmd == CLI_INIT)
01787       e->command = "abort shutdown";
01788    return res;
01789 }

static char* handle_bang ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1791 of file asterisk.c.

References CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, and ast_cli_entry::usage.

01792 {
01793    switch (cmd) {
01794    case CLI_INIT:
01795       e->command = "!";
01796       e->usage = 
01797          "Usage: !<command>\n"
01798          "       Executes a given shell command\n";
01799       return NULL;
01800    case CLI_GENERATE:
01801       return NULL;
01802    }
01803 
01804    return CLI_SUCCESS;
01805 }

static char* handle_clear_profile ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 661 of file asterisk.c.

References CLI_GENERATE, CLI_INIT, DEFINE_PROFILE_MIN_MAX_VALUES, profile_data::e, profile_entry::events, profile_entry::name, prof_data, and profile_entry::value.

00662 {
00663    int i, min, max;
00664    char *search = NULL;
00665    switch (cmd) {
00666    case CLI_INIT:
00667       e->command = "core clear profile";
00668       e->usage = "Usage: core clear profile\n"
00669             "       clear profile information";
00670       return NULL;
00671    case CLI_GENERATE:
00672       return NULL;
00673    }
00674 
00675    if (prof_data == NULL)
00676       return 0;
00677 
00678    DEFINE_PROFILE_MIN_MAX_VALUES;
00679    for (i= min; i < max; i++) {
00680       if (!search || strstr(prof_data->e[i].name, search)) {
00681          prof_data->e[i].value = 0;
00682          prof_data->e[i].events = 0;
00683       }
00684    }
00685    return CLI_SUCCESS;
00686 }

static char* handle_restart_gracefully ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1706 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_restart_gracefully_deprecated().

01707 {
01708    switch (cmd) {
01709    case CLI_INIT:
01710       e->command = "core restart gracefully";
01711       e->usage = 
01712          "Usage: core restart gracefully\n"
01713          "       Causes Asterisk to stop accepting new calls and exec() itself performing a cold\n"
01714          "       restart when all active calls have ended.\n";
01715       return NULL;
01716    case CLI_GENERATE:
01717       return NULL;
01718    }
01719 
01720    if (a->argc != e->args)
01721       return CLI_SHOWUSAGE;
01722    quit_handler(0, 1 /* nicely */, 1 /* safely */, 1 /* restart */);
01723    return CLI_SUCCESS;
01724 }

static char* handle_restart_gracefully_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1726 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_restart_gracefully().

01727 {
01728    char *res = handle_restart_gracefully(e, cmd, a);
01729    if (cmd == CLI_INIT)
01730       e->command = "restart gracefully";
01731    return res;
01732 }

static char* handle_restart_now ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1678 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_restart_now_deprecated().

01679 {
01680    switch (cmd) {
01681    case CLI_INIT:
01682       e->command = "core restart now";
01683       e->usage = 
01684          "Usage: core restart now\n"
01685          "       Causes Asterisk to hangup all calls and exec() itself performing a cold\n"
01686          "       restart.\n";
01687       return NULL;
01688    case CLI_GENERATE:
01689       return NULL;
01690    }
01691 
01692    if (a->argc != e->args)
01693       return CLI_SHOWUSAGE;
01694    quit_handler(0, 0 /* not nicely */, 1 /* safely */, 1 /* restart */);
01695    return CLI_SUCCESS;
01696 }

static char* handle_restart_now_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1698 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_restart_now().

01699 {
01700    char *res = handle_restart_now(e, cmd, a);
01701    if (cmd == CLI_INIT)
01702       e->command = "restart now";
01703    return res;
01704 }

static char* handle_restart_when_convenient ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1734 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_restart_when_convenient_deprecated().

01735 {
01736    switch (cmd) {
01737    case CLI_INIT:
01738       e->command = "core restart when convenient";
01739       e->usage = 
01740          "Usage: core restart when convenient\n"
01741          "       Causes Asterisk to perform a cold restart when all active calls have ended.\n";
01742       return NULL;
01743    case CLI_GENERATE:
01744       return NULL;
01745    }
01746 
01747    if (a->argc != e->args)
01748       return CLI_SHOWUSAGE;
01749    ast_cli(a->fd, "Waiting for inactivity to perform restart\n");
01750    quit_handler(0, 2 /* really nicely */, 1 /* safely */, 1 /* restart */);
01751    return CLI_SUCCESS;
01752 }

static char* handle_restart_when_convenient_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1754 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_restart_when_convenient().

01755 {
01756    char *res = handle_restart_when_convenient(e, cmd, a);
01757    if (cmd == CLI_INIT)
01758       e->command = "restart when convenient";
01759    return res;
01760 }

static char* handle_show_profile ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 626 of file asterisk.c.

References ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SUCCESS, DEFINE_PROFILE_MIN_MAX_VALUES, profile_data::e, profile_data::entries, ast_cli_args::fd, profile_data::max_size, and prof_data.

00627 {
00628    int i, min, max;
00629    char *search = NULL;
00630    switch (cmd) {
00631    case CLI_INIT:
00632       e->command = "core show profile";
00633       e->usage = "Usage: core show profile\n"
00634             "       show profile information";
00635       return NULL;
00636    case CLI_GENERATE:
00637       return NULL;
00638    }
00639 
00640    if (prof_data == NULL)
00641       return 0;
00642 
00643    DEFINE_PROFILE_MIN_MAX_VALUES;
00644    ast_cli(a->fd, "profile values (%d, allocated %d)\n-------------------\n",
00645       prof_data->entries, prof_data->max_size);
00646    ast_cli(a->fd, "%6s   %8s  %10s %12s %12s  %s\n", "ID", "Scale", "Events",
00647          "Value", "Average", "Name");
00648    for (i = min; i < max; i++) {
00649       struct profile_entry *entry = &prof_data->e[i];
00650       if (!search || strstr(entry->name, search))
00651           ast_cli(a->fd, "%6d: [%8ld] %10ld %12lld %12lld  %s\n",
00652          i,
00653          (long)entry->scale,
00654          (long)entry->events, (long long)entry->value,
00655          (long long)(entry->events ? entry->value / entry->events : entry->value),
00656          entry->name);
00657    }
00658    return CLI_SUCCESS;
00659 }

static char* handle_show_settings ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Give an overview of core settings.

Todo:
we could check musiconhold, voicemail, smdi, adsi, queues

Definition at line 381 of file asterisk.c.

References ast_active_channels(), ast_build_date, ast_build_kernel, ast_build_machine, ast_build_os, ast_build_user, AST_BUILDOPTS, ast_cli(), ast_config_AST_CONFIG_DIR, ast_config_AST_CONFIG_FILE, ast_config_AST_LOG_DIR, ast_config_AST_MODULE_DIR, ast_config_AST_RUN_GROUP, ast_config_AST_RUN_USER, ast_config_AST_SPOOL_DIR, ast_config_AST_SYSTEM_NAME, ast_eid_default, ast_eid_to_str(), ast_get_version(), ast_language_is_prefix, ast_lastreloadtime, ast_localtime(), AST_OPT_FLAG_EXEC_INCLUDES, AST_OPT_FLAG_INTERNAL_TIMING, AST_OPT_FLAG_TRANSCODE_VIA_SLIN, AST_OPT_FLAG_TRANSMIT_SILENCE, ast_options, ast_realtime_enabled(), ast_startuptime, ast_strftime(), ast_test_flag, buf, check_cdr_enabled(), check_manager_enabled(), check_webmanager_enabled(), CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, defaultlanguage, ast_cli_args::fd, S_OR, and ast_cli_entry::usage.

00382 {
00383    char buf[BUFSIZ];
00384    struct ast_tm tm;
00385    char eid_str[128];
00386 
00387    switch (cmd) {
00388    case CLI_INIT:
00389       e->command = "core show settings";
00390       e->usage = "Usage: core show settings\n"
00391             "       Show core misc settings";
00392       return NULL;
00393    case CLI_GENERATE:
00394       return NULL;
00395    }
00396 
00397    ast_eid_to_str(eid_str, sizeof(eid_str), &ast_eid_default);
00398 
00399    ast_cli(a->fd, "\nPBX Core settings\n");
00400    ast_cli(a->fd, "-----------------\n");
00401    ast_cli(a->fd, "  Version:                     %s\n", ast_get_version());
00402    ast_cli(a->fd, "  Build Options:               %s\n", S_OR(AST_BUILDOPTS, "(none)"));
00403    if (option_maxcalls)
00404       ast_cli(a->fd, "  Maximum calls:               %d (Current %d)\n", option_maxcalls, ast_active_channels());
00405    else
00406       ast_cli(a->fd, "  Maximum calls:               Not set\n");
00407    if (option_maxfiles)
00408       ast_cli(a->fd, "  Maximum open file handles:   %d\n", option_maxfiles); 
00409    else
00410       ast_cli(a->fd, "  Maximum open file handles:   Not set\n");
00411    ast_cli(a->fd, "  Verbosity:                   %d\n", option_verbose);
00412    ast_cli(a->fd, "  Debug level:                 %d\n", option_debug);
00413    ast_cli(a->fd, "  Maximum load average:        %lf\n", option_maxload);
00414 #if defined(HAVE_SYSINFO)
00415    ast_cli(a->fd, "  Minimum free memory:         %ld MB\n", option_minmemfree);
00416 #endif
00417    if (ast_localtime(&ast_startuptime, &tm, NULL)) {
00418       ast_strftime(buf, sizeof(buf), "%H:%M:%S", &tm);
00419       ast_cli(a->fd, "  Startup time:                %s\n", buf);
00420    }
00421    if (ast_localtime(&ast_lastreloadtime, &tm, NULL)) {
00422       ast_strftime(buf, sizeof(buf), "%H:%M:%S", &tm);
00423       ast_cli(a->fd, "  Last reload time:            %s\n", buf);
00424    }
00425    ast_cli(a->fd, "  System:                      %s/%s built by %s on %s %s\n", ast_build_os, ast_build_kernel, ast_build_user, ast_build_machine, ast_build_date);
00426    ast_cli(a->fd, "  System name:                 %s\n", ast_config_AST_SYSTEM_NAME);
00427    ast_cli(a->fd, "  Entity ID:                   %s\n", eid_str);
00428    ast_cli(a->fd, "  Default language:            %s\n", defaultlanguage);
00429    ast_cli(a->fd, "  Language prefix:             %s\n", ast_language_is_prefix ? "Enabled" : "Disabled");
00430    ast_cli(a->fd, "  User name and group:         %s/%s\n", ast_config_AST_RUN_USER, ast_config_AST_RUN_GROUP);
00431    ast_cli(a->fd, "  Executable includes:         %s\n", ast_test_flag(&ast_options, AST_OPT_FLAG_EXEC_INCLUDES) ? "Enabled" : "Disabled");
00432    ast_cli(a->fd, "  Transcode via SLIN:          %s\n", ast_test_flag(&ast_options, AST_OPT_FLAG_TRANSCODE_VIA_SLIN) ? "Enabled" : "Disabled");
00433    ast_cli(a->fd, "  Internal timing:             %s\n", ast_test_flag(&ast_options, AST_OPT_FLAG_INTERNAL_TIMING) ? "Enabled" : "Disabled");
00434    ast_cli(a->fd, "  Transmit silence during rec: %s\n", ast_test_flag(&ast_options, AST_OPT_FLAG_TRANSMIT_SILENCE) ? "Enabled" : "Disabled");
00435 
00436    ast_cli(a->fd, "\n* Subsystems\n");
00437    ast_cli(a->fd, "  -------------\n");
00438    ast_cli(a->fd, "  Manager (AMI):               %s\n", check_manager_enabled() ? "Enabled" : "Disabled");
00439    ast_cli(a->fd, "  Web Manager (AMI/HTTP):      %s\n", check_webmanager_enabled() ? "Enabled" : "Disabled");
00440    ast_cli(a->fd, "  Call data records:           %s\n", check_cdr_enabled() ? "Enabled" : "Disabled");
00441    ast_cli(a->fd, "  Realtime Architecture (ARA): %s\n", ast_realtime_enabled() ? "Enabled" : "Disabled");
00442 
00443    /*! \todo we could check musiconhold, voicemail, smdi, adsi, queues  */
00444 
00445    ast_cli(a->fd, "\n* Directories\n");
00446    ast_cli(a->fd, "  -------------\n");
00447    ast_cli(a->fd, "  Configuration file:          %s\n", ast_config_AST_CONFIG_FILE);
00448    ast_cli(a->fd, "  Configuration directory:     %s\n", ast_config_AST_CONFIG_DIR);
00449    ast_cli(a->fd, "  Module directory:            %s\n", ast_config_AST_MODULE_DIR);
00450    ast_cli(a->fd, "  Spool directory:             %s\n", ast_config_AST_SPOOL_DIR);
00451    ast_cli(a->fd, "  Log directory:               %s\n", ast_config_AST_LOG_DIR);
00452    ast_cli(a->fd, "\n\n");
00453    return CLI_SUCCESS;
00454 }

static char* handle_show_sysinfo ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Give an overview of system statistics.

Definition at line 483 of file asterisk.c.

References ast_cli(), CLI_FAILURE, CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, and ast_cli_entry::usage.

00484 {
00485    struct sysinfo sys_info;
00486    switch (cmd) {
00487    case CLI_INIT:
00488       e->command = "core show sysinfo";
00489       e->usage =
00490          "Usage: core show sysinfo\n"
00491          "       List current system information.\n";
00492       return NULL;
00493    case CLI_GENERATE:
00494       return NULL;
00495    }
00496    if (sysinfo(&sys_info)) {
00497       ast_cli(a->fd, "FAILED to retrieve system information\n\n");
00498       return CLI_FAILURE;
00499    }
00500    ast_cli(a->fd, "\nSystem Statistics\n");
00501    ast_cli(a->fd, "-----------------\n");
00502    ast_cli(a->fd, "  System Uptime:             %ld hours\n", sys_info.uptime/3600);
00503    ast_cli(a->fd, "  Total RAM:                 %ld KiB\n", (sys_info.totalram * sys_info.mem_unit)/1024);
00504    ast_cli(a->fd, "  Free RAM:                  %ld KiB\n", (sys_info.freeram * sys_info.mem_unit)/1024);
00505    ast_cli(a->fd, "  Buffer RAM:                %ld KiB\n", (sys_info.bufferram * sys_info.mem_unit)/1024);
00506    ast_cli(a->fd, "  Total Swap Space:          %ld KiB\n", (sys_info.totalswap * sys_info.mem_unit)/1024);
00507    ast_cli(a->fd, "  Free Swap Space:           %ld KiB\n\n", (sys_info.freeswap * sys_info.mem_unit)/1024);
00508    ast_cli(a->fd, "  Number of Processes:       %d \n\n", sys_info.procs);
00509    return CLI_SUCCESS;
00510 }

static char* handle_show_threads ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 456 of file asterisk.c.

References ast_cli(), AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, thread_list_t::id, ast_atexit::list, thread_list_t::name, and ast_cli_entry::usage.

00457 {
00458    int count = 0;
00459    struct thread_list_t *cur;
00460    switch (cmd) {
00461    case CLI_INIT:
00462       e->command = "core show threads";
00463       e->usage = 
00464          "Usage: core show threads\n"
00465          "       List threads currently active in the system.\n";
00466       return NULL;
00467    case CLI_GENERATE:
00468       return NULL;
00469    }
00470 
00471    AST_RWLIST_RDLOCK(&thread_list);
00472    AST_RWLIST_TRAVERSE(&thread_list, cur, list) {
00473       ast_cli(a->fd, "%p %s\n", (void *)cur->id, cur->name);
00474       count++;
00475    }
00476         AST_RWLIST_UNLOCK(&thread_list);
00477    ast_cli(a->fd, "%d threads listed.\n", count);
00478    return CLI_SUCCESS;
00479 }

static char* handle_show_version_files ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

CLI command to list module versions.

Definition at line 690 of file asterisk.c.

References ast_cli_args::argc, ast_cli_args::argv, ast_cli(), AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_strdup, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, file_version::file, FORMAT, ast_atexit::list, ast_cli_args::n, ast_cli_args::pos, ast_cli_entry::usage, file_version::version, and ast_cli_args::word.

00691 {
00692 #define FORMAT "%-25.25s %-40.40s\n"
00693    struct file_version *iterator;
00694    regex_t regexbuf;
00695    int havepattern = 0;
00696    int havename = 0;
00697    int count_files = 0;
00698    char *ret = NULL;
00699    int matchlen, which = 0;
00700    struct file_version *find;
00701 
00702    switch (cmd) {
00703    case CLI_INIT:
00704       e->command = "core show file version [like]";
00705       e->usage = 
00706          "Usage: core show file version [like <pattern>]\n"
00707          "       Lists the revision numbers of the files used to build this copy of Asterisk.\n"
00708          "       Optional regular expression pattern is used to filter the file list.\n";
00709       return NULL;
00710    case CLI_GENERATE:
00711       matchlen = strlen(a->word);
00712       if (a->pos != 3)
00713          return NULL;
00714       AST_RWLIST_RDLOCK(&file_versions);
00715       AST_RWLIST_TRAVERSE(&file_versions, find, list) {
00716          if (!strncasecmp(a->word, find->file, matchlen) && ++which > a->n) {
00717             ret = ast_strdup(find->file);
00718             break;
00719          }
00720       }
00721       AST_RWLIST_UNLOCK(&file_versions);
00722       return ret;
00723    }
00724 
00725 
00726    switch (a->argc) {
00727    case 6:
00728       if (!strcasecmp(a->argv[4], "like")) {
00729          if (regcomp(&regexbuf, a->argv[5], REG_EXTENDED | REG_NOSUB))
00730             return CLI_SHOWUSAGE;
00731          havepattern = 1;
00732       } else
00733          return CLI_SHOWUSAGE;
00734       break;
00735    case 5:
00736       havename = 1;
00737       break;
00738    case 4:
00739       break;
00740    default:
00741       return CLI_SHOWUSAGE;
00742    }
00743 
00744    ast_cli(a->fd, FORMAT, "File", "Revision");
00745    ast_cli(a->fd, FORMAT, "----", "--------");
00746    AST_RWLIST_RDLOCK(&file_versions);
00747    AST_RWLIST_TRAVERSE(&file_versions, iterator, list) {
00748       if (havename && strcasecmp(iterator->file, a->argv[4]))
00749          continue;
00750 
00751       if (havepattern && regexec(&regexbuf, iterator->file, 0, NULL, 0))
00752          continue;
00753 
00754       ast_cli(a->fd, FORMAT, iterator->file, iterator->version);
00755       count_files++;
00756       if (havename)
00757          break;
00758    }
00759    AST_RWLIST_UNLOCK(&file_versions);
00760    if (!havename) {
00761       ast_cli(a->fd, "%d files listed.\n", count_files);
00762    }
00763 
00764    if (havepattern)
00765       regfree(&regexbuf);
00766 
00767    return CLI_SUCCESS;
00768 #undef FORMAT
00769 }

static char* handle_stop_gracefully ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1622 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_stop_gracefully_deprecated().

01623 {
01624    switch (cmd) {
01625    case CLI_INIT:
01626       e->command = "core stop gracefully";
01627       e->usage = 
01628          "Usage: core stop gracefully\n"
01629          "       Causes Asterisk to not accept new calls, and exit when all\n"
01630          "       active calls have terminated normally.\n";
01631       return NULL;
01632    case CLI_GENERATE:
01633       return NULL;
01634    }
01635 
01636    if (a->argc != e->args)
01637       return CLI_SHOWUSAGE;
01638    quit_handler(0, 1 /* nicely */, 1 /* safely */, 0 /* no restart */);
01639    return CLI_SUCCESS;
01640 }

static char* handle_stop_gracefully_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1642 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_stop_gracefully().

01643 {
01644    char *res = handle_stop_gracefully(e, cmd, a);
01645    if (cmd == CLI_INIT)
01646       e->command = "stop gracefully";
01647    return res;
01648 }

static char* handle_stop_now ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1595 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_stop_now_deprecated().

01596 {
01597    switch (cmd) {
01598    case CLI_INIT:
01599       e->command = "core stop now";
01600       e->usage = 
01601          "Usage: core stop now\n"
01602          "       Shuts down a running Asterisk immediately, hanging up all active calls .\n";
01603       return NULL;
01604    case CLI_GENERATE:
01605       return NULL;
01606    }
01607 
01608    if (a->argc != e->args)
01609       return CLI_SHOWUSAGE;
01610    quit_handler(0, 0 /* Not nice */, 1 /* safely */, 0 /* not restart */);
01611    return CLI_SUCCESS;
01612 }

static char* handle_stop_now_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1614 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_stop_now().

01615 {
01616    char *res = handle_stop_now(e, cmd, a);
01617    if (cmd == CLI_INIT)
01618       e->command = "stop now";
01619    return res;
01620 }

static char* handle_stop_when_convenient ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1650 of file asterisk.c.

References ast_cli_args::argc, ast_cli_entry::args, ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, quit_handler(), and ast_cli_entry::usage.

Referenced by handle_stop_when_convenient_deprecated().

01651 {
01652    switch (cmd) {
01653    case CLI_INIT:
01654       e->command = "core stop when convenient";
01655       e->usage = 
01656          "Usage: core stop when convenient\n"
01657          "       Causes Asterisk to perform a shutdown when all active calls have ended.\n";
01658       return NULL;
01659    case CLI_GENERATE:
01660       return NULL;
01661    }
01662 
01663    if (a->argc != e->args)
01664       return CLI_SHOWUSAGE;
01665    ast_cli(a->fd, "Waiting for inactivity to perform halt\n");
01666    quit_handler(0, 2 /* really nicely */, 1 /* safely */, 0 /* don't restart */);
01667    return CLI_SUCCESS;
01668 }

static char* handle_stop_when_convenient_deprecated ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1670 of file asterisk.c.

References CLI_INIT, ast_cli_entry::command, and handle_stop_when_convenient().

01671 {
01672    char *res = handle_stop_when_convenient(e, cmd, a);
01673    if (cmd == CLI_INIT)
01674       e->command = "stop when convenient";
01675    return res;
01676 }

static char* handle_version ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1564 of file asterisk.c.

References ast_cli_args::argc, ast_build_date, ast_build_hostname, ast_build_machine, ast_build_os, ast_build_user, ast_cli(), ast_get_version(), CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, and ast_cli_entry::usage.

01565 {
01566    switch (cmd) {
01567    case CLI_INIT:
01568       e->command = "core show version";
01569       e->usage = 
01570          "Usage: core show version\n"
01571          "       Shows Asterisk version information.\n";
01572       return NULL;
01573    case CLI_GENERATE:
01574       return NULL;
01575    }
01576 
01577    if (a->argc != 3)
01578       return CLI_SHOWUSAGE;
01579    ast_cli(a->fd, "Asterisk %s built by %s @ %s on a %s running %s on %s\n",
01580       ast_get_version(), ast_build_user, ast_build_hostname,
01581       ast_build_machine, ast_build_os, ast_build_date);
01582    return CLI_SUCCESS;
01583 }

static void hup_handler ( int  num  )  [static]

Definition at line 1229 of file asterisk.c.

References _argv, errno, restartnow, sig_alert_pipe, and sig_flags.

Referenced by main().

01230 {
01231    int a = 0;
01232    if (option_verbose > 1) 
01233       printf("Received HUP signal -- Reloading configs\n");
01234    if (restartnow)
01235       execvp(_argv[0], _argv);
01236    sig_flags.need_reload = 1;
01237    if (sig_alert_pipe[1] != -1) {
01238       if (write(sig_alert_pipe[1], &a, sizeof(a)) < 0) {
01239          fprintf(stderr, "hup_handler: write() failed: %s\n", strerror(errno));
01240       }
01241    }
01242    signal(num, hup_handler);
01243 }

static void* listener ( void *  unused  )  [static]

Definition at line 1065 of file asterisk.c.

References AF_LOCAL, ast_log(), AST_MAX_CONNECTS, ast_poll, ast_pthread_create_detached_background, ast_verb, consoles, errno, console::fd, fdprint(), len(), LOG_ERROR, LOG_WARNING, console::mute, netconsole(), and s.

Referenced by ast_makesocket().

01066 {
01067    struct sockaddr_un sunaddr;
01068    int s;
01069    socklen_t len;
01070    int x;
01071    int flags;
01072    struct pollfd fds[1];
01073    for (;;) {
01074       if (ast_socket < 0)
01075          return NULL;
01076       fds[0].fd = ast_socket;
01077       fds[0].events = POLLIN;
01078       s = ast_poll(fds, 1, -1);
01079       pthread_testcancel();
01080       if (s < 0) {
01081          if (errno != EINTR)
01082             ast_log(LOG_WARNING, "poll returned error: %s\n", strerror(errno));
01083          continue;
01084       }
01085       len = sizeof(sunaddr);
01086       s = accept(ast_socket, (struct sockaddr *)&sunaddr, &len);
01087       if (s < 0) {
01088          if (errno != EINTR)
01089             ast_log(LOG_WARNING, "Accept returned %d: %s\n", s, strerror(errno));
01090       } else {
01091          for (x = 0; x < AST_MAX_CONNECTS; x++) {
01092             if (consoles[x].fd < 0) {
01093                if (socketpair(AF_LOCAL, SOCK_STREAM, 0, consoles[x].p)) {
01094                   ast_log(LOG_ERROR, "Unable to create pipe: %s\n", strerror(errno));
01095                   consoles[x].fd = -1;
01096                   fdprint(s, "Server failed to create pipe\n");
01097                   close(s);
01098                   break;
01099                }
01100                flags = fcntl(consoles[x].p[1], F_GETFL);
01101                fcntl(consoles[x].p[1], F_SETFL, flags | O_NONBLOCK);
01102                consoles[x].fd = s;
01103                consoles[x].mute = 1; /* Default is muted, we will un-mute if necessary */
01104                if (ast_pthread_create_detached_background(&consoles[x].t, NULL, netconsole, &consoles[x])) {
01105                   ast_log(LOG_ERROR, "Unable to spawn thread to handle connection: %s\n", strerror(errno));
01106                   close(consoles[x].p[0]);
01107                   close(consoles[x].p[1]);
01108                   consoles[x].fd = -1;
01109                   fdprint(s, "Server failed to spawn thread\n");
01110                   close(s);
01111                }
01112                break;
01113             }
01114          }
01115          if (x >= AST_MAX_CONNECTS) {
01116             fdprint(s, "No more connections allowed\n");
01117             ast_log(LOG_WARNING, "No more connections allowed\n");
01118             close(s);
01119          } else if (consoles[x].fd > -1) 
01120             ast_verb(3, "Remote UNIX connection\n");
01121       }
01122    }
01123    return NULL;
01124 }

int main ( int  argc,
char *  argv[] 
)

Definition at line 2946 of file asterisk.c.

References __ast_mm_init(), __quit_handler(), _argv, ARRAY_LEN, ast_alaw_init(), ast_autoservice_init(), ast_builtins_init(), ast_cdr_engine_init(), ast_channels_init(), ast_clear_flag, ast_cli_register_multiple(), ast_config_AST_PID, ast_config_AST_RUN_DIR, ast_config_AST_RUN_GROUP, ast_config_AST_RUN_USER, ast_config_AST_SOCKET, ast_copy_string(), ast_device_state_engine_init(), ast_dsp_init(), ast_el_initialize(), ast_el_read_history(), ast_enum_init(), ast_event_init(), ast_fd_init(), ast_features_init(), ast_file_init(), ast_http_init(), ast_image_init(), ast_language_is_prefix, ast_lastreloadtime, ast_log(), ast_makesocket(), ast_opt_always_fork, ast_opt_console, ast_opt_dump_core, ast_opt_exec, AST_OPT_FLAG_ALWAYS_FORK, AST_OPT_FLAG_CACHE_RECORD_FILES, AST_OPT_FLAG_CONSOLE, AST_OPT_FLAG_DUMP_CORE, AST_OPT_FLAG_EXEC, AST_OPT_FLAG_FULLY_BOOTED, AST_OPT_FLAG_HIGH_PRIORITY, AST_OPT_FLAG_INIT_KEYS, AST_OPT_FLAG_INTERNAL_TIMING, AST_OPT_FLAG_MUTE, AST_OPT_FLAG_NO_COLOR, AST_OPT_FLAG_NO_FORK, AST_OPT_FLAG_OVERRIDE_CONFIG, AST_OPT_FLAG_QUIET, AST_OPT_FLAG_RECONNECT, AST_OPT_FLAG_REMOTE, AST_OPT_FLAG_TIMESTAMP, ast_opt_high_priority, ast_opt_no_fork, ast_opt_remote, ast_options, ast_pthread_create_detached, ast_readconfig(), ast_register_verbose(), ast_remotecontrol(), ast_rtp_init(), ast_set_flag, ast_set_priority(), ast_startuptime, ast_strdupa, ast_strlen_zero(), ast_term_init(), ast_test_flag, ast_timing_init(), ast_tps_init(), ast_tryconnect(), ast_tvnow(), ast_udptl_init(), ast_ulaw_init(), ast_utils_init(), ast_verbose, astdb_init(), astobj2_init(), callerid_init(), canary_exit(), canary_filename, canary_pid, canary_pipe, canary_thread(), cfg_paths, child_handler(), cli_asterisk, COLOR_BLACK, COLOR_BRWHITE, _cfg_paths::config_file, console_verboser(), consolehandler(), consolethread, dnsmgr_init(), dnsmgr_start_refresh(), el, el_hist, errno, f, hup_handler(), init_framer(), init_logger(), init_manager(), load_modules(), load_pbx(), LOG_ERROR, LOG_WARNING, MAXHOSTNAMELEN, monitor_sig_flags(), num, quit_handler(), randompool, read_config_maps(), register_config_cli(), run_startup_commands(), set_icon(), set_title(), show_cli_help(), show_version(), sig_alert_pipe, _cfg_paths::socket_path, tdd_init(), term_color(), term_end(), term_quit(), threadstorage_init(), urg_handler(), and WELCOME_MESSAGE.

02947 {
02948    int c;
02949    char filename[80] = "";
02950    char hostname[MAXHOSTNAMELEN] = "";
02951    char tmp[80];
02952    char * xarg = NULL;
02953    int x;
02954    FILE *f;
02955    sigset_t sigs;
02956    int num;
02957    int isroot = 1;
02958    char *buf;
02959    const char *runuser = NULL, *rungroup = NULL;
02960    char *remotesock = NULL;
02961 
02962    /* Remember original args for restart */
02963    if (argc > ARRAY_LEN(_argv) - 1) {
02964       fprintf(stderr, "Truncating argument size to %d\n", (int)ARRAY_LEN(_argv) - 1);
02965       argc = ARRAY_LEN(_argv) - 1;
02966    }
02967    for (x = 0; x < argc; x++)
02968       _argv[x] = argv[x];
02969    _argv[x] = NULL;
02970 
02971    if (geteuid() != 0)
02972       isroot = 0;
02973 
02974    /* if the progname is rasterisk consider it a remote console */
02975    if (argv[0] && (strstr(argv[0], "rasterisk")) != NULL) {
02976       ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE);
02977    }
02978    if (gethostname(hostname, sizeof(hostname)-1))
02979       ast_copy_string(hostname, "<Unknown>", sizeof(hostname));
02980    ast_mainpid = getpid();
02981    ast_ulaw_init();
02982    ast_alaw_init();
02983    callerid_init();
02984    ast_builtins_init();
02985    ast_utils_init();
02986    tdd_init();
02987    ast_tps_init();
02988    ast_fd_init();
02989 
02990    if (getenv("HOME")) 
02991       snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
02992    /* Check for options */
02993    while ((c = getopt(argc, argv, "mtThfFdvVqprRgciInx:U:G:C:L:M:e:s:")) != -1) {
02994       switch (c) {
02995 #if defined(HAVE_SYSINFO)
02996       case 'e':
02997          if ((sscanf(&optarg[1], "%ld", &option_minmemfree) != 1) || (option_minmemfree < 0)) {
02998             option_minmemfree = 0;
02999          }
03000          break;
03001 #endif
03002 #if HAVE_WORKING_FORK
03003       case 'F':
03004          ast_set_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK);
03005          break;
03006       case 'f':
03007          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
03008          break;
03009 #endif
03010       case 'd':
03011          option_debug++;
03012          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
03013          break;
03014       case 'c':
03015          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_CONSOLE);
03016          break;
03017       case 'n':
03018          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_COLOR);
03019          break;
03020       case 'r':
03021          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE);
03022          break;
03023       case 'R':
03024          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE | AST_OPT_FLAG_RECONNECT);
03025          break;
03026       case 'p':
03027          ast_set_flag(&ast_options, AST_OPT_FLAG_HIGH_PRIORITY);
03028          break;
03029       case 'v':
03030          option_verbose++;
03031          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
03032          break;
03033       case 'm':
03034          ast_set_flag(&ast_options, AST_OPT_FLAG_MUTE);
03035          break;
03036       case 'M':
03037          if ((sscanf(optarg, "%d", &option_maxcalls) != 1) || (option_maxcalls < 0))
03038             option_maxcalls = 0;
03039          break;
03040       case 'L':
03041          if ((sscanf(optarg, "%lf", &option_maxload) != 1) || (option_maxload < 0.0))
03042             option_maxload = 0.0;
03043          break;
03044       case 'q':
03045          ast_set_flag(&ast_options, AST_OPT_FLAG_QUIET);
03046          break;
03047       case 't':
03048          ast_set_flag(&ast_options, AST_OPT_FLAG_CACHE_RECORD_FILES);
03049          break;
03050       case 'T':
03051          ast_set_flag(&ast_options, AST_OPT_FLAG_TIMESTAMP);
03052          break;
03053       case 'x':
03054          ast_set_flag(&ast_options, AST_OPT_FLAG_EXEC);
03055          xarg = ast_strdupa(optarg);
03056          break;
03057       case 'C':
03058          ast_copy_string(cfg_paths.config_file, optarg, sizeof(cfg_paths.config_file));
03059          ast_set_flag(&ast_options, AST_OPT_FLAG_OVERRIDE_CONFIG);
03060          break;
03061       case 'I':
03062          ast_set_flag(&ast_options, AST_OPT_FLAG_INTERNAL_TIMING);
03063          break;
03064       case 'i':
03065          ast_set_flag(&ast_options, AST_OPT_FLAG_INIT_KEYS);
03066          break;
03067       case 'g':
03068          ast_set_flag(&ast_options, AST_OPT_FLAG_DUMP_CORE);
03069          break;
03070       case 'h':
03071          show_cli_help();
03072          exit(0);
03073       case 'V':
03074          show_version();
03075          exit(0);
03076       case 'U':
03077          runuser = ast_strdupa(optarg);
03078          break;
03079       case 'G':
03080          rungroup = ast_strdupa(optarg);
03081          break;
03082       case 's':
03083          remotesock = ast_strdupa(optarg);
03084          break;
03085       case '?':
03086          exit(1);
03087       }
03088    }
03089 
03090    if (ast_opt_console || option_verbose || (ast_opt_remote && !ast_opt_exec)) {
03091       if (ast_register_verbose(console_verboser)) {
03092          ast_log(LOG_WARNING, "Unable to register console verboser?\n");
03093       }
03094       WELCOME_MESSAGE;
03095    }
03096 
03097    if (ast_opt_console && !option_verbose) 
03098       ast_verbose("[ Booting...\n");
03099 
03100    /* For remote connections, change the name of the remote connection.
03101     * We do this for the benefit of init scripts (which need to know if/when
03102     * the main asterisk process has died yet). */
03103    if (ast_opt_remote) {
03104       strcpy(argv[0], "rasterisk");
03105       for (x = 1; x < argc; x++) {
03106          argv[x] = argv[0] + 10;
03107       }
03108    }
03109 
03110    if (ast_opt_console && !option_verbose) {
03111       ast_verbose("[ Reading Master Configuration ]\n");
03112    }
03113 
03114    ast_readconfig();
03115 
03116    if (ast_opt_remote && remotesock != NULL)
03117       ast_copy_string((char *) cfg_paths.socket_path, remotesock, sizeof(cfg_paths.socket_path));
03118 
03119    if (!ast_language_is_prefix && !ast_opt_remote)
03120       ast_log(LOG_WARNING, "The 'languageprefix' option in asterisk.conf is deprecated; in a future release it will be removed, and your sound files will need to be organized in the 'new style' language layout.\n");
03121 
03122    if (ast_opt_always_fork && (ast_opt_remote || ast_opt_console)) {
03123       ast_log(LOG_WARNING, "'alwaysfork' is not compatible with console or remote console mode; ignored\n");
03124       ast_clear_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK);
03125    }
03126 
03127    if (ast_opt_dump_core) {
03128       struct rlimit l;
03129       memset(&l, 0, sizeof(l));
03130       l.rlim_cur = RLIM_INFINITY;
03131       l.rlim_max = RLIM_INFINITY;
03132       if (setrlimit(RLIMIT_CORE, &l)) {
03133          ast_log(LOG_WARNING, "Unable to disable core size resource limit: %s\n", strerror(errno));
03134       }
03135    }
03136 
03137    if ((!rungroup) && !ast_strlen_zero(ast_config_AST_RUN_GROUP))
03138       rungroup = ast_config_AST_RUN_GROUP;
03139    if ((!runuser) && !ast_strlen_zero(ast_config_AST_RUN_USER))
03140       runuser = ast_config_AST_RUN_USER;
03141 
03142    /* Must install this signal handler up here to ensure that if the canary
03143     * fails to execute that it doesn't kill the Asterisk process.
03144     */
03145    signal(SIGCHLD, child_handler);
03146 
03147 #ifndef __CYGWIN__
03148 
03149    if (isroot) {
03150       ast_set_priority(ast_opt_high_priority);
03151       if (ast_opt_high_priority) {
03152          int cpipe[2];
03153 
03154          /* PIPE signal ensures that astcanary dies when Asterisk dies */
03155          if (pipe(cpipe)) {
03156             fprintf(stderr, "Unable to open pipe for canary process: %s\n", strerror(errno));
03157             exit(1);
03158          }
03159          canary_pipe = cpipe[0];
03160 
03161          snprintf(canary_filename, sizeof(canary_filename), "%s/alt.asterisk.canary.tweet.tweet.tweet", ast_config_AST_RUN_DIR);
03162 
03163          /* Don't let the canary child kill Asterisk, if it dies immediately */
03164          signal(SIGPIPE, SIG_IGN);
03165 
03166          canary_pid = fork();
03167          if (canary_pid == 0) {
03168             char canary_binary[128], *lastslash;
03169             int fd;
03170 
03171             /* Reset signal handler */
03172             signal(SIGCHLD, SIG_DFL);
03173             signal(SIGPIPE, SIG_DFL);
03174 
03175             dup2(cpipe[1], 100);
03176             close(cpipe[1]);
03177 
03178             for (fd = 0; fd < 100; fd++) {
03179                close(fd);
03180             }
03181 
03182             execlp("astcanary", "astcanary", canary_filename, (char *)NULL);
03183 
03184             /* If not found, try the same path as used to execute asterisk */
03185             ast_copy_string(canary_binary, argv[0], sizeof(canary_binary));
03186             if ((lastslash = strrchr(canary_binary, '/'))) {
03187                ast_copy_string(lastslash + 1, "astcanary", sizeof(canary_binary) + canary_binary - (lastslash + 1));
03188                execl(canary_binary, "astcanary", canary_filename, (char *)NULL);
03189             }
03190 
03191             /* Should never happen */
03192             _exit(1);
03193          } else if (canary_pid > 0) {
03194             pthread_t dont_care;
03195             close(cpipe[1]);
03196             ast_pthread_create_detached(&dont_care, NULL, canary_thread, NULL);
03197          }
03198 
03199          /* Kill the canary when we exit */
03200          atexit(canary_exit);
03201       }
03202    }
03203 
03204    if (isroot && rungroup) {
03205       struct group *gr;
03206       gr = getgrnam(rungroup);
03207       if (!gr) {
03208          ast_log(LOG_WARNING, "No such group '%s'!\n", rungroup);
03209          exit(1);
03210       }
03211       if (setgid(gr->gr_gid)) {
03212          ast_log(LOG_WARNING, "Unable to setgid to %d (%s)\n", (int)gr->gr_gid, rungroup);
03213          exit(1);
03214       }
03215       if (setgroups(0, NULL)) {
03216          ast_log(LOG_WARNING, "Unable to drop unneeded groups\n");
03217          exit(1);
03218       }
03219       if (option_verbose)
03220          ast_verbose("Running as group '%s'\n", rungroup);
03221    }
03222 
03223    if (runuser && !ast_test_flag(&ast_options, AST_OPT_FLAG_REMOTE)) {
03224 #ifdef HAVE_CAP
03225       int has_cap = 1;
03226 #endif /* HAVE_CAP */
03227       struct passwd *pw;
03228       pw = getpwnam(runuser);
03229       if (!pw) {
03230          ast_log(LOG_WARNING, "No such user '%s'!\n", runuser);
03231          exit(1);
03232       }
03233 #ifdef HAVE_CAP
03234       if (prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0)) {
03235          ast_log(LOG_WARNING, "Unable to keep capabilities.\n");
03236          has_cap = 0;
03237       }
03238 #endif /* HAVE_CAP */
03239       if (!isroot && pw->pw_uid != geteuid()) {
03240          ast_log(LOG_ERROR, "Asterisk started as nonroot, but runuser '%s' requested.\n", runuser);
03241          exit(1);
03242       }
03243       if (!rungroup) {
03244          if (setgid(pw->pw_gid)) {
03245             ast_log(LOG_WARNING, "Unable to setgid to %d!\n", (int)pw->pw_gid);
03246             exit(1);
03247          }
03248          if (isroot && initgroups(pw->pw_name, pw->pw_gid)) {
03249             ast_log(LOG_WARNING, "Unable to init groups for '%s'\n", runuser);
03250             exit(1);
03251          }
03252       }
03253       if (setuid(pw->pw_uid)) {
03254          ast_log(LOG_WARNING, "Unable to setuid to %d (%s)\n", (int)pw->pw_uid, runuser);
03255          exit(1);
03256       }
03257       if (option_verbose)
03258          ast_verbose("Running as user '%s'\n", runuser);
03259 #ifdef HAVE_CAP
03260       if (has_cap) {
03261          cap_t cap;
03262 
03263          cap = cap_from_text("cap_net_admin=eip");
03264 
03265          if (cap_set_proc(cap))
03266             ast_log(LOG_WARNING, "Unable to install capabilities.\n");
03267 
03268          if (cap_free(cap))
03269             ast_log(LOG_WARNING, "Unable to drop capabilities.\n");
03270       }
03271 #endif /* HAVE_CAP */
03272    }
03273 
03274 #endif /* __CYGWIN__ */
03275 
03276 #ifdef linux
03277    if (geteuid() && ast_opt_dump_core) {
03278       if (prctl(PR_SET_DUMPABLE, 1, 0, 0, 0) < 0) {
03279          ast_log(LOG_WARNING, "Unable to set the process for core dumps after changing to a non-root user. %s\n", strerror(errno));
03280       }  
03281    }
03282 #endif
03283 
03284    ast_term_init();
03285    printf("%s", term_end());
03286    fflush(stdout);
03287 
03288    if (ast_opt_console && !option_verbose) 
03289       ast_verbose("[ Initializing Custom Configuration Options ]\n");
03290    /* custom config setup */
03291    register_config_cli();
03292    read_config_maps();
03293    
03294    if (ast_opt_console) {
03295       if (el_hist == NULL || el == NULL)
03296          ast_el_initialize();
03297 
03298       if (!ast_strlen_zero(filename))
03299          ast_el_read_history(filename);
03300    }
03301 
03302    if (ast_tryconnect()) {
03303       /* One is already running */
03304       if (ast_opt_remote) {
03305          if (ast_opt_exec) {
03306             ast_remotecontrol(xarg);
03307             quit_handler(0, 0, 0, 0);
03308             exit(0);
03309          }
03310          printf("%s", term_quit());
03311          ast_remotecontrol(NULL);
03312          quit_handler(0, 0, 0, 0);
03313          exit(0);
03314       } else {
03315          ast_log(LOG_ERROR, "Asterisk already running on %s.  Use 'asterisk -r' to connect.\n", ast_config_AST_SOCKET);
03316          printf("%s", term_quit());
03317          exit(1);
03318       }
03319    } else if (ast_opt_remote || ast_opt_exec) {
03320       ast_log(LOG_ERROR, "Unable to connect to remote asterisk (does %s exist?)\n", ast_config_AST_SOCKET);
03321       printf("%s", term_quit());
03322       exit(1);
03323    }
03324    /* Blindly write pid file since we couldn't connect */
03325    unlink(ast_config_AST_PID);
03326    f = fopen(ast_config_AST_PID, "w");
03327    if (f) {
03328       fprintf(f, "%ld\n", (long)getpid());
03329       fclose(f);
03330    } else
03331       ast_log(LOG_WARNING, "Unable to open pid file '%s': %s\n", ast_config_AST_PID, strerror(errno));
03332 
03333 #if HAVE_WORKING_FORK
03334    if (ast_opt_always_fork || !ast_opt_no_fork) {
03335 #ifndef HAVE_SBIN_LAUNCHD
03336       if (daemon(1, 0) < 0) {
03337          ast_log(LOG_ERROR, "daemon() failed: %s\n", strerror(errno));
03338       }
03339       ast_mainpid = getpid();
03340       /* Blindly re-write pid file since we are forking */
03341       unlink(ast_config_AST_PID);
03342       f = fopen(ast_config_AST_PID, "w");
03343       if (f) {
03344          fprintf(f, "%ld\n", (long)ast_mainpid);
03345          fclose(f);
03346       } else
03347          ast_log(LOG_WARNING, "Unable to open pid file '%s': %s\n", ast_config_AST_PID, strerror(errno));
03348 #else
03349       ast_log(LOG_WARNING, "Mac OS X detected.  Use '/sbin/launchd -d' to launch with the nofork option.\n");
03350 #endif
03351    }
03352 #endif
03353 
03354    if (ast_event_init()) {
03355       printf("%s", term_quit());
03356       exit(1);
03357    }
03358 
03359    ast_makesocket();
03360    sigemptyset(&sigs);
03361    sigaddset(&sigs, SIGHUP);
03362    sigaddset(&sigs, SIGTERM);
03363    sigaddset(&sigs, SIGINT);
03364    sigaddset(&sigs, SIGPIPE);
03365    sigaddset(&sigs, SIGWINCH);
03366    pthread_sigmask(SIG_BLOCK, &sigs, NULL);
03367    signal(SIGURG, urg_handler);
03368    signal(SIGINT, __quit_handler);
03369    signal(SIGTERM, __quit_handler);
03370    signal(SIGHUP, hup_handler);
03371    signal(SIGPIPE, SIG_IGN);
03372 
03373    /* ensure that the random number generators are seeded with a different value every time
03374       Asterisk is started
03375    */
03376    srand((unsigned int) getpid() + (unsigned int) time(NULL));
03377    initstate((unsigned int) getpid() * 65536 + (unsigned int) time(NULL), randompool, sizeof(randompool));
03378 
03379    if (init_logger()) {    /* Start logging subsystem */
03380       printf("%s", term_quit());
03381       exit(1);
03382    }
03383 
03384    threadstorage_init();
03385 
03386    astobj2_init();
03387 
03388    ast_autoservice_init();
03389 
03390    if (ast_timing_init()) {
03391       printf("%s", term_quit());
03392       exit(1);
03393    }
03394 
03395    if (load_modules(1)) {     /* Load modules, pre-load only */
03396       printf("%s", term_quit());
03397       exit(1);
03398    }
03399 
03400    if (dnsmgr_init()) {    /* Initialize the DNS manager */
03401       printf("%s", term_quit());
03402       exit(1);
03403    }
03404 
03405    ast_http_init();     /* Start the HTTP server, if needed */
03406 
03407    ast_channels_init();
03408 
03409    if (ast_cdr_engine_init()) {
03410       printf("%s", term_quit());
03411       exit(1);
03412    }
03413 
03414    if (ast_device_state_engine_init()) {
03415       printf("%s", term_quit());
03416       exit(1);
03417    }
03418 
03419    ast_rtp_init();
03420    ast_dsp_init();
03421    ast_udptl_init();
03422 
03423    if (ast_image_init()) {
03424       printf("%s", term_quit());
03425       exit(1);
03426    }
03427 
03428    if (ast_file_init()) {
03429       printf("%s", term_quit());
03430       exit(1);
03431    }
03432 
03433    if (load_pbx()) {
03434       printf("%s", term_quit());
03435       exit(1);
03436    }
03437 
03438    ast_features_init();
03439 
03440    if (init_framer()) {
03441       printf("%s", term_quit());
03442       exit(1);
03443    }
03444 
03445    if (astdb_init()) {
03446       printf("%s", term_quit());
03447       exit(1);
03448    }
03449 
03450    if (ast_enum_init()) {
03451       printf("%s", term_quit());
03452       exit(1);
03453    }
03454 
03455    if (load_modules(0)) {
03456       printf("%s", term_quit());
03457       exit(1);
03458    }
03459 
03460    /* AMI is initialized after loading modules because of a potential
03461     * conflict between issuing a module reload from manager and
03462     * registering manager actions.  This will cause reversed locking
03463     * order between the module list and manager actions list. */
03464    if (init_manager()) {
03465       printf("%s", term_quit());
03466       exit(1);
03467    }
03468 
03469    dnsmgr_start_refresh();
03470 
03471    /* We might have the option of showing a console, but for now just
03472       do nothing... */
03473    if (ast_opt_console && !option_verbose)
03474       ast_verbose(" ]\n");
03475    if (option_verbose || ast_opt_console)
03476       ast_verbose("%s", term_color(tmp, "Asterisk Ready.\n", COLOR_BRWHITE, COLOR_BLACK, sizeof(tmp)));
03477    if (ast_opt_no_fork)
03478       consolethread = pthread_self();
03479 
03480    if (pipe(sig_alert_pipe))
03481       sig_alert_pipe[0] = sig_alert_pipe[1] = -1;
03482 
03483    ast_set_flag(&ast_options, AST_OPT_FLAG_FULLY_BOOTED);
03484    pthread_sigmask(SIG_UNBLOCK, &sigs, NULL);
03485 
03486 #ifdef __AST_DEBUG_MALLOC
03487    __ast_mm_init();
03488 #endif   
03489 
03490    ast_lastreloadtime = ast_startuptime = ast_tvnow();
03491    ast_cli_register_multiple(cli_asterisk, sizeof(cli_asterisk) / sizeof(struct ast_cli_entry));
03492 
03493    run_startup_commands();
03494 
03495    if (ast_opt_console) {
03496       /* Console stuff now... */
03497       /* Register our quit function */
03498       char title[256];
03499       pthread_t dont_care;
03500 
03501       ast_pthread_create_detached(&dont_care, NULL, monitor_sig_flags, NULL);
03502 
03503       set_icon("Asterisk");
03504       snprintf(title, sizeof(title), "Asterisk Console on '%s' (pid %ld)", hostname, (long)ast_mainpid);
03505       set_title(title);
03506 
03507       for (;;) {
03508          buf = (char *) el_gets(el, &num);
03509 
03510          if (!buf && write(1, "", 1) < 0)
03511             goto lostterm;
03512 
03513          if (buf) {
03514             if (buf[strlen(buf)-1] == '\n')
03515                buf[strlen(buf)-1] = '\0';
03516 
03517             consolehandler((char *)buf);
03518          } else if (ast_opt_remote && (write(STDOUT_FILENO, "\nUse EXIT or QUIT to exit the asterisk console\n",
03519                strlen("\nUse EXIT or QUIT to exit the asterisk console\n")) < 0)) {
03520             /* Whoa, stdout disappeared from under us... Make /dev/null's */
03521             int fd;
03522             fd = open("/dev/null", O_RDWR);
03523             if (fd > -1) {
03524                dup2(fd, STDOUT_FILENO);
03525                dup2(fd, STDIN_FILENO);
03526             } else
03527                ast_log(LOG_WARNING, "Failed to open /dev/null to recover from dead console. Bad things will happen!\n");
03528             break;
03529          }
03530       }
03531    }
03532 
03533    monitor_sig_flags(NULL);
03534 
03535 lostterm:
03536    return 0;
03537 }

static void* monitor_sig_flags ( void *  unused  )  [static]

Definition at line 2871 of file asterisk.c.

References ast_module_reload(), ast_poll, quit_handler(), sig_alert_pipe, and sig_flags.

Referenced by main().

02872 {
02873    for (;;) {
02874       struct pollfd p = { sig_alert_pipe[0], POLLIN, 0 };
02875       int a;
02876       ast_poll(&p, 1, -1);
02877       if (sig_flags.need_reload) {
02878          sig_flags.need_reload = 0;
02879          ast_module_reload(NULL);
02880       }
02881       if (sig_flags.need_quit) {
02882          sig_flags.need_quit = 0;
02883          quit_handler(0, 0, 1, 0);
02884       }
02885       if (read(sig_alert_pipe[0], &a, sizeof(a)) != sizeof(a)) {
02886       }
02887    }
02888 
02889    return NULL;
02890 }

static void* netconsole ( void *  vconsole  )  [static]

Definition at line 1007 of file asterisk.c.

References ast_cli_command_multiple(), ast_copy_string(), ast_get_version(), ast_log(), ast_poll, ast_verb, errno, console::fd, fdprint(), hostname, LOG_ERROR, LOG_WARNING, MAXHOSTNAMELEN, and console::p.

Referenced by listener().

01008 {
01009    struct console *con = vconsole;
01010    char hostname[MAXHOSTNAMELEN] = "";
01011    char tmp[512];
01012    int res;
01013    struct pollfd fds[2];
01014    
01015    if (gethostname(hostname, sizeof(hostname)-1))
01016       ast_copy_string(hostname, "<Unknown>", sizeof(hostname));
01017    snprintf(tmp, sizeof(tmp), "%s/%ld/%s\n", hostname, (long)ast_mainpid, ast_get_version());
01018    fdprint(con->fd, tmp);
01019    for (;;) {
01020       fds[0].fd = con->fd;
01021       fds[0].events = POLLIN;
01022       fds[0].revents = 0;
01023       fds[1].fd = con->p[0];
01024       fds[1].events = POLLIN;
01025       fds[1].revents = 0;
01026 
01027       res = ast_poll(fds, 2, -1);
01028       if (res < 0) {
01029          if (errno != EINTR)
01030             ast_log(LOG_WARNING, "poll returned < 0: %s\n", strerror(errno));
01031          continue;
01032       }
01033       if (fds[0].revents) {
01034          res = read(con->fd, tmp, sizeof(tmp));
01035          if (res < 1) {
01036             break;
01037          }
01038          tmp[res] = 0;
01039          if (strncmp(tmp, "cli quit after ", 15) == 0) {
01040             ast_cli_command_multiple(con->fd, res - 15, tmp + 15);
01041             break;
01042          }
01043          ast_cli_command_multiple(con->fd, res, tmp);
01044       }
01045       if (fds[1].revents) {
01046          res = read(con->p[0], tmp, sizeof(tmp));
01047          if (res < 1) {
01048             ast_log(LOG_ERROR, "read returned %d\n", res);
01049             break;
01050          }
01051          res = write(con->fd, tmp, res);
01052          if (res < 1)
01053             break;
01054       }
01055    }
01056    ast_verb(3, "Remote UNIX connection disconnected\n");
01057    close(con->fd);
01058    close(con->p[0]);
01059    close(con->p[1]);
01060    con->fd = -1;
01061    
01062    return NULL;
01063 }

static void network_verboser ( const char *  s  )  [static]

Definition at line 1000 of file asterisk.c.

References __LOG_VERBOSE, and ast_network_puts_mutable().

Referenced by ast_makesocket().

01001 {
01002    ast_network_puts_mutable(s, __LOG_VERBOSE);
01003 }

static void null_sig_handler ( int  sig  )  [static]

NULL handler so we can collect the child exit status.

Definition at line 822 of file asterisk.c.

Referenced by ast_replace_sigchld().

00823 {
00824 
00825 }

static void quit_handler ( int  num,
int  niceness,
int  safeshutdown,
int  restart 
) [static]

Definition at line 1343 of file asterisk.c.

References _argv, ast_active_channels(), ast_begin_shutdown(), ast_cdr_engine_term(), ast_config_AST_PID, ast_config_AST_SOCKET, ast_debug, ast_el_write_history(), ast_module_shutdown(), ast_opt_console, ast_opt_remote, AST_PTHREADT_NULL, ast_run_atexits(), ast_strlen_zero(), ast_verbose, close_logger(), consolethread, el, el_hist, EVENT_FLAG_SYSTEM, lthread, manager_event, restartnow, s, shuttingdown, and term_quit().

Referenced by ast_el_read_char(), handle_restart_gracefully(), handle_restart_now(), handle_restart_when_convenient(), handle_stop_gracefully(), handle_stop_now(), handle_stop_when_convenient(), main(), monitor_sig_flags(), and remoteconsolehandler().

01344 {
01345    char filename[80] = "";
01346    time_t s,e;
01347    int x;
01348    /* Try to get as many CDRs as possible submitted to the backend engines (if in batch mode) */
01349    ast_cdr_engine_term();
01350    if (safeshutdown) {
01351       shuttingdown = 1;
01352       if (!niceness) {
01353          /* Begin shutdown routine, hanging up active channels */
01354          ast_begin_shutdown(1);
01355          if (option_verbose && ast_opt_console)
01356             ast_verbose("Beginning asterisk %s....\n", restart ? "restart" : "shutdown");
01357          time(&s);
01358          for (;;) {
01359             time(&e);
01360             /* Wait up to 15 seconds for all channels to go away */
01361             if ((e - s) > 15)
01362                break;
01363             if (!ast_active_channels())
01364                break;
01365             if (!shuttingdown)
01366                break;
01367             /* Sleep 1/10 of a second */
01368             usleep(100000);
01369          }
01370       } else {
01371          if (niceness < 2)
01372             ast_begin_shutdown(0);
01373          if (option_verbose && ast_opt_console)
01374             ast_verbose("Waiting for inactivity to perform %s...\n", restart ? "restart" : "halt");
01375          for (;;) {
01376             if (!ast_active_channels())
01377                break;
01378             if (!shuttingdown)
01379                break;
01380             sleep(1);
01381          }
01382       }
01383 
01384       if (!shuttingdown) {
01385          if (option_verbose && ast_opt_console)
01386             ast_verbose("Asterisk %s cancelled.\n", restart ? "restart" : "shutdown");
01387          return;
01388       }
01389 
01390       if (niceness)
01391          ast_module_shutdown();
01392    }
01393    if (ast_opt_console || ast_opt_remote) {
01394       if (getenv("HOME")) 
01395          snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
01396       if (!ast_strlen_zero(filename))
01397          ast_el_write_history(filename);
01398       if (el != NULL)
01399          el_end(el);
01400       if (el_hist != NULL)
01401          history_end(el_hist);
01402    }
01403    if (option_verbose)
01404       ast_verbose("Executing last minute cleanups\n");
01405    ast_run_atexits();
01406    /* Called on exit */
01407    if (option_verbose && ast_opt_console)
01408       ast_verbose("Asterisk %s ending (%d).\n", ast_active_channels() ? "uncleanly" : "cleanly", num);
01409    ast_debug(1, "Asterisk ending (%d).\n", num);
01410    manager_event(EVENT_FLAG_SYSTEM, "Shutdown", "Shutdown: %s\r\nRestart: %s\r\n", ast_active_channels() ? "Uncleanly" : "Cleanly", restart ? "True" : "False");
01411    if (ast_socket > -1) {
01412       pthread_cancel(lthread);
01413       close(ast_socket);
01414       ast_socket = -1;
01415       unlink(ast_config_AST_SOCKET);
01416    }
01417    if (ast_consock > -1)
01418       close(ast_consock);
01419    if (!ast_opt_remote)
01420       unlink(ast_config_AST_PID);
01421    printf("%s", term_quit());
01422    if (restart) {
01423       if (option_verbose || ast_opt_console)
01424          ast_verbose("Preparing for Asterisk restart...\n");
01425       /* Mark all FD's for closing on exec */
01426       for (x=3; x < 32768; x++) {
01427          fcntl(x, F_SETFD, FD_CLOEXEC);
01428       }
01429       if (option_verbose || ast_opt_console)
01430          ast_verbose("Asterisk is now restarting...\n");
01431       restartnow = 1;
01432 
01433       /* close logger */
01434       close_logger();
01435 
01436       /* If there is a consolethread running send it a SIGHUP 
01437          so it can execvp, otherwise we can do it ourselves */
01438       if ((consolethread != AST_PTHREADT_NULL) && (consolethread != pthread_self())) {
01439          pthread_kill(consolethread, SIGHUP);
01440          /* Give the signal handler some time to complete */
01441          sleep(2);
01442       } else
01443          execvp(_argv[0], _argv);
01444    
01445    } else {
01446       /* close logger */
01447       close_logger();
01448    }
01449    exit(0);
01450 }

static __inline uint64_t rdtsc ( void   )  [static]

Definition at line 591 of file asterisk.c.

Referenced by ast_mark().

00592 {
00593    return 0;
00594 }

static int remoteconsolehandler ( char *  s  )  [static]

Definition at line 1540 of file asterisk.c.

References ast_all_zeros(), ast_el_add_history(), ast_safe_system(), and quit_handler().

Referenced by ast_remotecontrol().

01541 {
01542    int ret = 0;
01543 
01544    /* Called when readline data is available */
01545    if (!ast_all_zeros(s))
01546       ast_el_add_history(s);
01547    /* The real handler for bang */
01548    if (s[0] == '!') {
01549       if (s[1])
01550          ast_safe_system(s+1);
01551       else
01552          ast_safe_system(getenv("SHELL") ? getenv("SHELL") : "/bin/sh");
01553       ret = 1;
01554    }
01555    if ((strncasecmp(s, "quit", 4) == 0 || strncasecmp(s, "exit", 4) == 0) &&
01556        (s[4] == '\0' || isspace(s[4]))) {
01557       quit_handler(0, 0, 0, 0);
01558       ret = 1;
01559    }
01560 
01561    return ret;
01562 }

static void run_startup_commands ( void   )  [static]

Definition at line 2921 of file asterisk.c.

References ast_cli_command(), ast_config_destroy(), ast_config_load2(), ast_true(), ast_variable_browse(), ast_variable::name, ast_variable::next, and ast_variable::value.

Referenced by main().

02922 {
02923    int fd;
02924    struct ast_config *cfg;
02925    struct ast_flags cfg_flags = { 0 };
02926    struct ast_variable *v;
02927 
02928    if (!(cfg = ast_config_load2("cli.conf", "" /* core, can't reload */, cfg_flags)))
02929       return;
02930 
02931    fd = open("/dev/null", O_RDWR);
02932    if (fd < 0) {
02933       ast_config_destroy(cfg);
02934       return;
02935    }
02936 
02937    for (v = ast_variable_browse(cfg, "startup_commands"); v; v = v->next) {
02938       if (ast_true(v->value))
02939          ast_cli_command(fd, v->name);
02940    }
02941 
02942    close(fd);
02943    ast_config_destroy(cfg);
02944 }

static void set_icon ( char *  text  )  [static]

Definition at line 1290 of file asterisk.c.

Referenced by main().

01291 {
01292    if (getenv("TERM") && strstr(getenv("TERM"), "xterm"))
01293       fprintf(stdout, "\033]1;%s\007", text);
01294 }

static void set_title ( char *  text  )  [static]

Set an X-term or screen title.

Definition at line 1284 of file asterisk.c.

Referenced by main().

01285 {
01286    if (getenv("TERM") && strstr(getenv("TERM"), "xterm"))
01287       fprintf(stdout, "\033]2;%s\007", text);
01288 }

static void set_ulimit ( int  value  )  [static]

Set maximum open files.

Definition at line 1261 of file asterisk.c.

References ast_log(), errno, LOG_NOTICE, and LOG_WARNING.

01262 {
01263    struct rlimit l = {0, 0};
01264    
01265    if (value <= 0) {
01266       ast_log(LOG_WARNING, "Unable to change max files open to invalid value %i\n",value);
01267       return;
01268    }
01269    
01270    l.rlim_cur = value;
01271    l.rlim_max = value;
01272    
01273    if (setrlimit(RLIMIT_NOFILE, &l)) {
01274       ast_log(LOG_WARNING, "Unable to disable core size resource limit: %s\n",strerror(errno));
01275       return;
01276    }
01277    
01278    ast_log(LOG_NOTICE, "Setting max files open to %d\n",value);
01279    
01280    return;
01281 }

static int show_cli_help ( void   )  [static]

Definition at line 2607 of file asterisk.c.

References ast_get_version().

Referenced by main().

02607                                {
02608    printf("Asterisk %s, Copyright (C) 1999 - 2008, Digium, Inc. and others.\n", ast_get_version());
02609    printf("Usage: asterisk [OPTIONS]\n");
02610    printf("Valid Options:\n");
02611    printf("   -V              Display version number and exit\n");
02612    printf("   -C <configfile> Use an alternate configuration file\n");
02613    printf("   -G <group>      Run as a group other than the caller\n");
02614    printf("   -U <user>       Run as a user other than the caller\n");
02615    printf("   -c              Provide console CLI\n");
02616    printf("   -d              Enable extra debugging\n");
02617 #if HAVE_WORKING_FORK
02618    printf("   -f              Do not fork\n");
02619    printf("   -F              Always fork\n");
02620 #endif
02621    printf("   -g              Dump core in case of a crash\n");
02622    printf("   -h              This help screen\n");
02623    printf("   -i              Initialize crypto keys at startup\n");
02624    printf("   -I              Enable internal timing if DAHDI timer is available\n");
02625    printf("   -L <load>       Limit the maximum load average before rejecting new calls\n");
02626    printf("   -M <value>      Limit the maximum number of calls to the specified value\n");
02627    printf("   -m              Mute debugging and console output on the console\n");
02628    printf("   -n              Disable console colorization\n");
02629    printf("   -p              Run as pseudo-realtime thread\n");
02630    printf("   -q              Quiet mode (suppress output)\n");
02631    printf("   -r              Connect to Asterisk on this machine\n");
02632    printf("   -R              Same as -r, except attempt to reconnect if disconnected\n");
02633    printf("   -t              Record soundfiles in /var/tmp and move them where they\n");
02634    printf("                   belong after they are done\n");
02635    printf("   -T              Display the time in [Mmm dd hh:mm:ss] format for each line\n");
02636    printf("                   of output to the CLI\n");
02637    printf("   -v              Increase verbosity (multiple v's = more verbose)\n");
02638    printf("   -x <cmd>        Execute command <cmd> (only valid with -r)\n");
02639    printf("   -s <socket>     Connect to Asterisk via socket <socket> (only valid with -r)\n");
02640    printf("\n");
02641    return 0;
02642 }

static char* show_license ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1868 of file asterisk.c.

References ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, license_lines, and ast_cli_entry::usage.

01869 {
01870    switch (cmd) {
01871    case CLI_INIT:
01872       e->command = "core show license";
01873       e->usage = 
01874          "Usage: core show license\n"
01875          "       Shows the license(s) for this copy of Asterisk.\n";
01876       return NULL;
01877    case CLI_GENERATE:
01878       return NULL;
01879    }
01880 
01881    ast_cli(a->fd, "%s", license_lines);
01882 
01883    return CLI_SUCCESS;
01884 }

static int show_version ( void   )  [static]

Definition at line 2601 of file asterisk.c.

References ast_get_version().

Referenced by main().

02602 {
02603    printf("Asterisk %s\n", ast_get_version());
02604    return 0;
02605 }

static char* show_warranty ( struct ast_cli_entry e,
int  cmd,
struct ast_cli_args a 
) [static]

Definition at line 1831 of file asterisk.c.

References ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, ast_cli_entry::usage, and warranty_lines.

01832 {
01833    switch (cmd) {
01834    case CLI_INIT:
01835       e->command = "core show warranty";
01836       e->usage = 
01837          "Usage: core show warranty\n"
01838          "       Shows the warranty (if any) for this copy of Asterisk.\n";
01839       return NULL;
01840    case CLI_GENERATE:
01841       return NULL;
01842    }
01843 
01844    ast_cli(a->fd, "%s", warranty_lines);
01845 
01846    return CLI_SUCCESS;
01847 }

static void urg_handler ( int  num  )  [static]

Urgent handler.

Called by soft_hangup to interrupt the poll, read, or other system call. We don't actually need to do anything though. Remember: Cannot EVER ast_log from within a signal handler

Definition at line 1223 of file asterisk.c.

Referenced by main().

01224 {
01225    signal(num, urg_handler);
01226    return;
01227 }


Variable Documentation

char* _argv[256] [static]

Definition at line 257 of file asterisk.c.

Referenced by hup_handler(), main(), and quit_handler().

const char* ast_build_date

Definition at line 32 of file buildinfo.c.

Referenced by handle_show_settings(), and handle_version().

const char* ast_build_hostname

Definition at line 28 of file buildinfo.c.

Referenced by handle_version().

const char* ast_build_kernel

Definition at line 29 of file buildinfo.c.

Referenced by handle_show_settings().

const char* ast_build_machine

Definition at line 30 of file buildinfo.c.

Referenced by handle_show_settings(), and handle_version().

const char* ast_build_os

Definition at line 31 of file buildinfo.c.

Referenced by handle_show_settings(), and handle_version().

const char* ast_build_user

Definition at line 33 of file buildinfo.c.

Referenced by handle_show_settings(), and handle_version().

const char* ast_config_AST_AGI_DIR = cfg_paths.agi_dir

Definition at line 234 of file asterisk.c.

Referenced by launch_script().

const char* ast_config_AST_CONFIG_DIR = cfg_paths.config_dir

Definition at line 226 of file asterisk.c.

Referenced by action_createconfig(), compile_script(), config_text_file_load(), handle_cli_dialplan_save(), handle_show_settings(), ices_exec(), launch_script(), lua_read_extensions_file(), message_template_parse_filebody(), pbx_load_module(), and set_fn().

const char* ast_config_AST_CONFIG_FILE = cfg_paths.config_file

Definition at line 227 of file asterisk.c.

Referenced by ast_readconfig(), handle_show_settings(), and launch_script().

char ast_config_AST_CTL[PATH_MAX] = "asterisk.ctl" [static]

Definition at line 248 of file asterisk.c.

Referenced by ast_readconfig().

char ast_config_AST_CTL_GROUP[PATH_MAX] = "\0" [static]

Definition at line 247 of file asterisk.c.

Referenced by ast_makesocket(), and ast_readconfig().

char ast_config_AST_CTL_OWNER[PATH_MAX] = "\0" [static]

Definition at line 246 of file asterisk.c.

Referenced by ast_makesocket(), and ast_readconfig().

char ast_config_AST_CTL_PERMISSIONS[PATH_MAX] [static]

Definition at line 245 of file asterisk.c.

Referenced by ast_makesocket(), and ast_readconfig().

const char* ast_config_AST_DATA_DIR = cfg_paths.data_dir

Definition at line 232 of file asterisk.c.

Referenced by ast_linear_stream(), build_filename(), launch_script(), make_filename(), phoneprov_callback(), pp_each_extension_exec(), reload_firmware(), setup_privacy_args(), and static_callback().

const char* ast_config_AST_DB = cfg_paths.db_path

Definition at line 238 of file asterisk.c.

Referenced by dbinit().

const char* ast_config_AST_KEY_DIR = cfg_paths.key_dir

Definition at line 235 of file asterisk.c.

Referenced by crypto_load(), handle_cli_keys_init(), launch_script(), and osp_create_provider().

const char* ast_config_AST_LOG_DIR = cfg_paths.log_dir

Definition at line 233 of file asterisk.c.

Referenced by apply_general_options(), csv_log(), handle_show_settings(), init_logger(), launch_script(), load_config(), load_module(), make_logchannel(), OpenHistory(), reload_logger(), testclient_exec(), testserver_exec(), write_history(), and writefile().

const char* ast_config_AST_MODULE_DIR = cfg_paths.module_dir

Definition at line 228 of file asterisk.c.

Referenced by add_module(), complete_fn(), file_ok_sel(), handle_show_settings(), launch_script(), and load_dynamic_module().

const char* ast_config_AST_MONITOR_DIR = cfg_paths.monitor_dir

Definition at line 230 of file asterisk.c.

Referenced by ast_monitor_change_fname(), ast_monitor_start(), ast_monitor_stop(), chanspy_exec(), extenspy_exec(), launch_script(), and mixmonitor_exec().

const char* ast_config_AST_PID = cfg_paths.pid_path

Definition at line 239 of file asterisk.c.

Referenced by main(), and quit_handler().

const char* ast_config_AST_RUN_DIR = cfg_paths.run_dir

Definition at line 236 of file asterisk.c.

Referenced by launch_script(), and main().

const char* ast_config_AST_RUN_GROUP = cfg_paths.run_group

Definition at line 242 of file asterisk.c.

Referenced by action_coresettings(), handle_show_settings(), and main().

const char* ast_config_AST_RUN_USER = cfg_paths.run_user

Definition at line 241 of file asterisk.c.

Referenced by action_coresettings(), handle_show_settings(), and main().

const char* ast_config_AST_SOCKET = cfg_paths.socket_path

Definition at line 240 of file asterisk.c.

Referenced by ast_makesocket(), ast_tryconnect(), main(), and quit_handler().

const char* ast_config_AST_SPOOL_DIR = cfg_paths.spool_dir

Definition at line 229 of file asterisk.c.

Referenced by app_exec(), conf_run(), dictate_exec(), handle_show_settings(), launch_script(), load_module(), sms_nextoutgoing(), and sms_writefile().

const char* ast_config_AST_SYSTEM_NAME = cfg_paths.system_name

Definition at line 243 of file asterisk.c.

Referenced by action_coresettings(), ast_channel_alloc(), cli_prompt(), handle_show_settings(), pbx_retrieve_variable(), and realtime_update_peer().

const char* ast_config_AST_VAR_DIR = cfg_paths.var_dir

Definition at line 231 of file asterisk.c.

Referenced by launch_script().

int ast_consock = -1 [static]

UNIX Socket for controlling another asterisk

Definition at line 171 of file asterisk.c.

struct ast_eid ast_eid_default

Global EID.

This is set in asterisk.conf, or determined automatically by taking the mac address of an Ethernet interface on the system.

Definition at line 165 of file asterisk.c.

Referenced by ast_event_new(), ast_readconfig(), handle_show_settings(), pbx_retrieve_variable(), and set_config().

struct timeval ast_lastreloadtime

Definition at line 189 of file asterisk.c.

Referenced by action_corestatus(), ast_module_reload(), handle_show_settings(), handle_showuptime(), and main().

pid_t ast_mainpid

Definition at line 172 of file asterisk.c.

Referenced by safe_append(), and scan_service().

int ast_socket = -1 [static]

UNIX Socket for allowing remote control

Definition at line 170 of file asterisk.c.

struct timeval ast_startuptime

Definition at line 188 of file asterisk.c.

Referenced by action_corestatus(), handle_show_settings(), handle_showcalls(), handle_showuptime(), and main().

char canary_filename[128] [static]

Definition at line 262 of file asterisk.c.

Referenced by canary_thread(), and main().

int canary_pid = 0 [static]

Definition at line 261 of file asterisk.c.

Referenced by canary_exit(), and main().

int canary_pipe = -1 [static]

Definition at line 263 of file asterisk.c.

Referenced by main().

struct _cfg_paths cfg_paths [static]

Definition at line 224 of file asterisk.c.

Referenced by ast_readconfig(), and main().

struct ast_cli_entry cli_abort_shutdown_deprecated = { .handler = handle_abort_shutdown_deprecated , .summary = "Cancel a running shutdown." ,__VA_ARGS__ } [static]

Definition at line 1891 of file asterisk.c.

struct ast_cli_entry cli_asterisk[] [static]

Definition at line 1900 of file asterisk.c.

Referenced by main().

struct ast_cli_entry cli_restart_gracefully_deprecated = { .handler = handle_restart_gracefully_deprecated , .summary = "Restart Asterisk gracefully." ,__VA_ARGS__ } [static]

Definition at line 1896 of file asterisk.c.

struct ast_cli_entry cli_restart_now_deprecated = { .handler = handle_restart_now_deprecated , .summary = "Restart Asterisk immediately." ,__VA_ARGS__ } [static]

Definition at line 1895 of file asterisk.c.

struct ast_cli_entry cli_restart_when_convenient_deprecated = { .handler = handle_restart_when_convenient_deprecated , .summary = "Restart Asterisk at empty call volume." ,__VA_ARGS__ } [static]

Definition at line 1897 of file asterisk.c.

struct ast_cli_entry cli_stop_gracefully_deprecated = { .handler = handle_stop_gracefully_deprecated , .summary = "Gracefully shut down Asterisk." ,__VA_ARGS__ } [static]

Definition at line 1893 of file asterisk.c.

struct ast_cli_entry cli_stop_now_deprecated = { .handler = handle_stop_now_deprecated , .summary = "Shut down Asterisk immediately." ,__VA_ARGS__ } [static]

Definition at line 1892 of file asterisk.c.

struct ast_cli_entry cli_stop_when_convenient_deprecated = { .handler = handle_stop_when_convenient_deprecated , .summary = "Shut down Asterisk at empty call volume." ,__VA_ARGS__ } [static]

Definition at line 1894 of file asterisk.c.

struct console consoles[AST_MAX_CONNECTS]

Definition at line 195 of file asterisk.c.

Referenced by ast_console_toggle_loglevel(), ast_console_toggle_mute(), ast_makesocket(), ast_network_puts(), ast_network_puts_mutable(), and listener().

pthread_t consolethread = AST_PTHREADT_NULL [static]

Definition at line 260 of file asterisk.c.

Referenced by console_verboser(), main(), quit_handler(), and show_console().

char defaultlanguage[MAX_LANGUAGE] = DEFAULT_LANGUAGE

Definition at line 197 of file asterisk.c.

Referenced by ast_channel_alloc(), and handle_show_settings().

EditLine* el [static]

Definition at line 192 of file asterisk.c.

Referenced by __ast_internal_context_destroy(), add_pri(), ast_add_extension2_lockopt(), ast_el_add_history(), ast_el_initialize(), ast_el_read_history(), ast_el_write_history(), ast_remotecontrol(), handle_cli_dialplan_save(), main(), quit_handler(), and show_dialplan_helper().

History* el_hist [static]

Definition at line 191 of file asterisk.c.

Referenced by ast_el_add_history(), ast_el_initialize(), ast_el_read_history(), ast_el_write_history(), ast_remotecontrol(), main(), and quit_handler().

const char license_lines[] [static]

Definition at line 1849 of file asterisk.c.

Referenced by show_license().

pthread_t lthread [static]

Definition at line 1005 of file asterisk.c.

Referenced by ast_makesocket(), and quit_handler().

unsigned int need_quit

Definition at line 270 of file asterisk.c.

unsigned int need_reload

Definition at line 269 of file asterisk.c.

struct profile_data* prof_data [static]

Definition at line 527 of file asterisk.c.

Referenced by ast_add_profile(), ast_mark(), ast_profile(), handle_clear_profile(), and handle_show_profile().

struct ast_str* prompt = NULL [static]

Definition at line 2022 of file asterisk.c.

Referenced by auth_exec(), cli_prompt(), handle_speechrecognize(), minivm_accmess_exec(), and pw_cb().

char randompool[256] [static]

Definition at line 265 of file asterisk.c.

Referenced by main().

char record_cache_dir[AST_CACHE_DIR_LEN] = DEFAULT_TMP_DIR

Definition at line 168 of file asterisk.c.

Referenced by ast_writefile().

char* remotehostname [static]

Definition at line 193 of file asterisk.c.

Referenced by ast_remotecontrol(), and cli_prompt().

int restartnow [static]

Definition at line 259 of file asterisk.c.

Referenced by hup_handler(), and quit_handler().

unsigned int safe_system_level = 0 [static]

Keep track of how many threads are currently trying to wait*() on a child process.

Definition at line 830 of file asterisk.c.

Referenced by ast_replace_sigchld(), and ast_unreplace_sigchld().

ast_mutex_t safe_system_lock = ((ast_mutex_t) PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP ) [static]

Definition at line 827 of file asterisk.c.

Referenced by ast_replace_sigchld(), and ast_unreplace_sigchld().

void* safe_system_prev_handler [static]

Definition at line 831 of file asterisk.c.

Referenced by ast_replace_sigchld(), and ast_unreplace_sigchld().

int shuttingdown [static]

Definition at line 258 of file asterisk.c.

Referenced by handle_abort_shutdown(), and quit_handler().

int sig_alert_pipe[2] = { -1, -1 } [static]

Definition at line 267 of file asterisk.c.

Referenced by __quit_handler(), hup_handler(), main(), and monitor_sig_flags().

struct { ... } sig_flags [static]

Referenced by __quit_handler(), __remote_quit_handler(), ast_el_read_char(), ast_remotecontrol(), hup_handler(), and monitor_sig_flags().

const char warranty_lines[] [static]

Definition at line 1806 of file asterisk.c.

Referenced by show_warranty().


Generated on Fri Jun 19 12:10:07 2009 for Asterisk - the Open Source PBX by  doxygen 1.4.7