Codename Pineapple

Home page | Mailing list | Docs

Last updated: Sat Feb 3 05:01:01 2007

Asterisk developer's documentation :: Codename Pineapple


asterisk.c File Reference


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.

#include "asterisk.h"
#include <unistd.h>
#include <stdlib.h>
#include <sys/time.h>
#include <fcntl.h>
#include <stdio.h>
#include <signal.h>
#include <sched.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <sys/wait.h>
#include <string.h>
#include <errno.h>
#include <ctype.h>
#include <sys/resource.h>
#include <grp.h>
#include <pwd.h>
#include <sys/stat.h>
#include <regex.h>
#include "asterisk/logger.h"
#include "asterisk/options.h"
#include "asterisk/cli.h"
#include "asterisk/channel.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/version.h"
#include "asterisk/linkedlists.h"
#include "asterisk/devicestate.h"
#include "asterisk/doxyref.h"
#include "../defaults.h"

Include dependency graph for asterisk.c:

Go to the source code of this file.

Data Structures

struct  ast_atexit
struct  console
struct  file_version
struct  profile_data
struct  profile_entry
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 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)
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)
 log the string to the console, and all attached console clients
void ast_console_toggle_mute (int fd)
 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 *el, 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 *)
static AST_LIST_HEAD_STATIC (thread_list, thread_list_t)
static AST_LIST_HEAD_STATIC (file_versions, file_version)
static AST_LIST_HEAD_STATIC (atexits, ast_atexit)
static int ast_makesocket (void)
int64_t ast_mark (int i, int startstop)
 AST_MUTEX_DEFINE_STATIC (safe_system_lock)
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)
 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)
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 child_handler (int sig)
static char * cli_complete (EditLine *el, int ch)
static char * cli_prompt (EditLine *el)
static char * complete_show_version_files (const char *line, const char *word, int pos, int state)
static void console_verboser (const char *s)
static void consolehandler (char *s)
static int fdprint (int fd, const char *s)
static const char * fix_header (char *outbuf, int maxout, const char *s, char *cmp)
static int handle_abort_halt (int fd, int argc, char *argv[])
static int handle_bang (int fd, int argc, char *argv[])
static int handle_restart_gracefully (int fd, int argc, char *argv[])
static int handle_restart_now (int fd, int argc, char *argv[])
static int handle_restart_when_convenient (int fd, int argc, char *argv[])
static int handle_show_profile (int fd, int argc, char *argv[])
static int handle_show_threads (int fd, int argc, char *argv[])
static int handle_show_version_files (int fd, int argc, char *argv[])
 CLI command to list module versions.
static int handle_shutdown_gracefully (int fd, int argc, char *argv[])
static int handle_shutdown_now (int fd, int argc, char *argv[])
static int handle_shutdown_when_convenient (int fd, int argc, char *argv[])
static int handle_version (int fd, int argc, char *argv[])
static void hup_handler (int num)
static void * listener (void *unused)
int main (int argc, char *argv[])
static void * netconsole (void *vconsole)
static void network_verboser (const char *s)
static void null_sig_handler (int signal)
 NULL handler so we can collect the child exit status.
static void quit_handler (int num, int nice, int safeshutdown, int restart)
static __inline uint64_t rdtsc (void)
static int remoteconsolehandler (char *s)
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 int show_license (int fd, int argc, char *argv[])
static int show_version (void)
static int show_warranty (int fd, int argc, char *argv[])
static void urg_handler (int num)
 Urgent handler.

Variables

static char * _argv [256]
static const char abort_halt_help []
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
char ast_config_AST_AGI_DIR [PATH_MAX]
char ast_config_AST_CONFIG_DIR [PATH_MAX]
char ast_config_AST_CONFIG_FILE [PATH_MAX]
char ast_config_AST_CTL [PATH_MAX] = "asterisk.ctl"
char ast_config_AST_CTL_GROUP [PATH_MAX] = "\0"
char ast_config_AST_CTL_OWNER [PATH_MAX] = "\0"
char ast_config_AST_CTL_PERMISSIONS [PATH_MAX]
char ast_config_AST_DATA_DIR [PATH_MAX]
char ast_config_AST_DB [PATH_MAX]
char ast_config_AST_KEY_DIR [PATH_MAX]
char ast_config_AST_LOG_DIR [PATH_MAX]
char ast_config_AST_MODULE_DIR [PATH_MAX]
char ast_config_AST_MONITOR_DIR [PATH_MAX]
char ast_config_AST_PID [PATH_MAX]
char ast_config_AST_RUN_DIR [PATH_MAX]
char ast_config_AST_RUN_GROUP [PATH_MAX]
char ast_config_AST_RUN_USER [PATH_MAX]
char ast_config_AST_SOCKET [PATH_MAX]
char ast_config_AST_SPOOL_DIR [PATH_MAX]
char ast_config_AST_SYSTEM_NAME [20] = ""
char ast_config_AST_VAR_DIR [PATH_MAX]
static int ast_consock = -1
time_t ast_lastreloadtime
pid_t ast_mainpid
ast_flags ast_options = { AST_DEFAULT_OPTIONS }
static int ast_socket = -1
time_t ast_startuptime
static const char bang_help []
static struct ast_cli_entry cli_asterisk []
console consoles [AST_MAX_CONNECTS]
static pthread_t consolethread = AST_PTHREADT_NULL
char debug_filename [AST_FILENAME_MAX] = ""
char defaultlanguage [MAX_LANGUAGE] = DEFAULT_LANGUAGE
static EditLine * el
static History * el_hist
static const char * license_lines []
static pthread_t lthread
static unsigned int need_reload
int option_debug
int option_maxcalls
double option_maxload
int option_verbose
static struct profile_dataprof_data
static char randompool [256]
char record_cache_dir [AST_CACHE_DIR_LEN] = AST_TMP_DIR
static char * remotehostname
static const char restart_gracefully_help []
static const char restart_now_help []
static const char restart_when_convenient_help []
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 void * safe_system_prev_handler
static const char show_license_help []
static const char show_threads_help []
static const char show_version_files_help []
static const char show_warranty_help []
static const char shutdown_gracefully_help []
static const char shutdown_now_help []
static const char shutdown_when_convenient_help []
static int shuttingdown
static const char version_help []
static const char * warranty_lines []


Define Documentation

#define AF_LOCAL   AF_UNIX
 

Definition at line 130 of file asterisk.c.

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

#define AST_MAX_CONNECTS   128
 

Definition at line 134 of file asterisk.c.

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

#define ASTERISK_PROMPT   "*CLI> "
 

Definition at line 1495 of file asterisk.c.

#define ASTERISK_PROMPT2   "%s*CLI> "
 

Definition at line 1497 of file asterisk.c.

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

Referenced by __iax2_show_peers(), __sip_show_channels(), _sip_show_devices(), _sip_show_peers(), dundi_show_mappings(), dundi_show_peers(), dundi_show_precache(), dundi_show_requests(), dundi_show_trans(), handle_show_version_files(), iax2_show_registry(), iax2_show_users(), show_channeltypes(), show_file_formats(), show_image_formats(), sip_show_domains(), sip_show_inuse(), sip_show_registry(), and sip_show_users().

#define NUM_MSGS   64
 

Definition at line 135 of file asterisk.c.

#define PF_LOCAL   PF_UNIX
 

Definition at line 131 of file asterisk.c.

Referenced by ast_makesocket(), and ast_tryconnect().

#define WELCOME_MESSAGE
 

Welcome message when starting a CLI interface.

Definition at line 138 of file asterisk.c.


Function Documentation

static void __quit_handler int  num  )  [static]
 

Definition at line 1211 of file asterisk.c.

References quit_handler().

01212 {
01213    quit_handler(num, 0, 1, 0);
01214 }

int ast_add_profile const char *  name,
uint64_t  scale
 

support for event profiling

Returns:
Returns the identifier of the counter.

Definition at line 364 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().

00365 {
00366    int l = sizeof(struct profile_data);
00367    int n = 10; /* default entries */
00368 
00369    if (prof_data == NULL) {
00370       prof_data = ast_calloc(1, l + n*sizeof(struct profile_entry));
00371       if (prof_data == NULL)
00372          return -1;
00373       prof_data->entries = 0;
00374       prof_data->max_size = n;
00375    }
00376    if (prof_data->entries >= prof_data->max_size) {
00377       void *p;
00378       n = prof_data->max_size + 20;
00379       p = ast_realloc(prof_data, l + n*sizeof(struct profile_entry));
00380       if (p == NULL)
00381          return -1;
00382       prof_data = p;
00383       prof_data->max_size = n;
00384    }
00385    n = prof_data->entries++;
00386    prof_data->e[n].name = ast_strdup(name);
00387    prof_data->e[n].value = 0;
00388    prof_data->e[n].events = 0;
00389    prof_data->e[n].mark = 0;
00390    prof_data->e[n].scale = scale;
00391    return n;
00392 }

static int ast_all_zeros char *  s  )  [static]
 

Definition at line 1248 of file asterisk.c.

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

01249 {
01250    while (*s) {
01251       if (*s > 32)
01252          return 0;
01253       s++;  
01254    }
01255    return 1;
01256 }

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

Definition at line 1821 of file asterisk.c.

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

01822 {
01823    int i, idx, limit, count;
01824    int screenwidth = 0;
01825    int numoutput = 0, numoutputline = 0;
01826 
01827    screenwidth = ast_get_termcols(STDOUT_FILENO);
01828 
01829    /* find out how many entries can be put on one line, with two spaces between strings */
01830    limit = screenwidth / (max + 2);
01831    if (limit == 0)
01832       limit = 1;
01833 
01834    /* how many lines of output */
01835    count = len / limit;
01836    if (count * limit < len)
01837       count++;
01838 
01839    idx = 1;
01840 
01841    qsort(&matches[0], (size_t)(len), sizeof(char *), ast_el_sort_compare);
01842 
01843    for (; count > 0; count--) {
01844       numoutputline = 0;
01845       for (i=0; i < limit && matches[idx]; i++, idx++) {
01846 
01847          /* Don't print dupes */
01848          if ( (matches[idx+1] != NULL && strcmp(matches[idx], matches[idx+1]) == 0 ) ) {
01849             i--;
01850             free(matches[idx]);
01851             matches[idx] = NULL;
01852             continue;
01853          }
01854 
01855          numoutput++;
01856          numoutputline++;
01857          fprintf(stdout, "%-*s  ", max, matches[idx]);
01858          free(matches[idx]);
01859          matches[idx] = NULL;
01860       }
01861       if (numoutputline > 0)
01862          fprintf(stdout, "\n");
01863    }
01864 
01865    return numoutput;
01866 }

void ast_console_puts const char *  string  ) 
 

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

Definition at line 757 of file asterisk.c.

References ast_network_puts().

Referenced by chan_misdn_log().

00758 {
00759    fputs(string, stdout);
00760    fflush(stdout);
00761    ast_network_puts(string);
00762 }

void ast_console_puts_mutable const char *  string  ) 
 

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

Definition at line 734 of file asterisk.c.

References ast_network_puts_mutable().

Referenced by logger_print_normal().

00735 {
00736    fputs(string, stdout);
00737    fflush(stdout);
00738    ast_network_puts_mutable(string);
00739 }

void ast_console_toggle_mute int  fd  ) 
 

mute or unmute a console from logging

Definition at line 699 of file asterisk.c.

References ast_cli(), AST_MAX_CONNECTS, and consoles.

Referenced by handle_logger_mute().

00699                                      {
00700    int x;
00701    for (x = 0;x < AST_MAX_CONNECTS; x++) {
00702       if (fd == consoles[x].fd) {
00703          if (consoles[x].mute) {
00704             consoles[x].mute = 0;
00705             ast_cli(fd, "Console is not muted anymore.\n");
00706          } else {
00707             consoles[x].mute = 1;
00708             ast_cli(fd, "Console is muted.\n");
00709          }
00710          return;
00711       }
00712    }
00713    ast_cli(fd, "Couldn't find remote console.\n");
00714 }

static int ast_el_add_history char *   )  [static]
 

Definition at line 2015 of file asterisk.c.

References ast_el_initialize().

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

02016 {
02017    HistEvent ev;
02018 
02019    if (el_hist == NULL || el == NULL)
02020       ast_el_initialize();
02021    if (strlen(buf) > 256)
02022       return 0;
02023    return (history(el_hist, &ev, H_ENTER, buf));
02024 }

static int ast_el_initialize void   )  [static]
 

Definition at line 1980 of file asterisk.c.

References cli_complete(), and cli_prompt().

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

01981 {
01982    HistEvent ev;
01983    char *editor = getenv("AST_EDITOR");
01984 
01985    if (el != NULL)
01986       el_end(el);
01987    if (el_hist != NULL)
01988       history_end(el_hist);
01989 
01990    el = el_init("asterisk", stdin, stdout, stderr);
01991    el_set(el, EL_PROMPT, cli_prompt);
01992 
01993    el_set(el, EL_EDITMODE, 1);      
01994    el_set(el, EL_EDITOR, editor ? editor : "emacs");     
01995    el_hist = history_init();
01996    if (!el || !el_hist)
01997       return -1;
01998 
01999    /* setup history with 100 entries */
02000    history(el_hist, &ev, H_SETSIZE, 100);
02001 
02002    el_set(el, EL_HIST, history, el_hist);
02003 
02004    el_set(el, EL_ADDFN, "ed-complete", "Complete argument", cli_complete);
02005    /* Bind <tab> to command completion */
02006    el_set(el, EL_BIND, "^I", "ed-complete", NULL);
02007    /* Bind ? to command completion */
02008    el_set(el, EL_BIND, "?", "ed-complete", NULL);
02009    /* Bind ^D to redisplay */
02010    el_set(el, EL_BIND, "^D", "ed-redisplay", NULL);
02011 
02012    return 0;
02013 }

static int ast_el_read_char EditLine *  el,
char *  cp
[static]
 

Definition at line 1562 of file asterisk.c.

References ast_opt_exec, pollfd::events, pollfd::fd, and POLLIN.

Referenced by ast_remotecontrol().

01563 {
01564    int num_read = 0;
01565    int lastpos = 0;
01566    struct pollfd fds[2];
01567    int res;
01568    int max;
01569    char buf[512];
01570 
01571    for (;;) {
01572       max = 1;
01573       fds[0].fd = ast_consock;
01574       fds[0].events = POLLIN;
01575       if (!ast_opt_exec) {
01576          fds[1].fd = STDIN_FILENO;
01577          fds[1].events = POLLIN;
01578          max++;
01579       }
01580       res = poll(fds, max, -1);
01581       if (res < 0) {
01582          if (errno == EINTR)
01583             continue;
01584          ast_log(LOG_ERROR, "poll failed: %s\n", strerror(errno));
01585          break;
01586       }
01587 
01588       if (!ast_opt_exec && fds[1].revents) {
01589          num_read = read(STDIN_FILENO, cp, 1);
01590          if (num_read < 1) {
01591             break;
01592          } else 
01593             return (num_read);
01594       }
01595       if (fds[0].revents) {
01596          res = read(ast_consock, buf, sizeof(buf) - 1);
01597          /* if the remote side disappears exit */
01598          if (res < 1) {
01599             fprintf(stderr, "\nDisconnected from Asterisk server\n");
01600             if (!ast_opt_reconnect) {
01601                quit_handler(0, 0, 0, 0);
01602             } else {
01603                int tries;
01604                int reconnects_per_second = 20;
01605                fprintf(stderr, "Attempting to reconnect for 30 seconds\n");
01606                for (tries=0; tries < 30 * reconnects_per_second; tries++) {
01607                   if (ast_tryconnect()) {
01608                      fprintf(stderr, "Reconnect succeeded after %.3f seconds\n", 1.0 / reconnects_per_second * tries);
01609                      printf(term_quit());
01610                      WELCOME_MESSAGE;
01611                      break;
01612                   } else
01613                      usleep(1000000 / reconnects_per_second);
01614                }
01615                if (tries >= 30 * reconnects_per_second) {
01616                   fprintf(stderr, "Failed to reconnect for 30 seconds.  Quitting.\n");
01617                   quit_handler(0, 0, 0, 0);
01618                }
01619             }
01620          }
01621 
01622          buf[res] = '\0';
01623 
01624          if (!ast_opt_exec && !lastpos)
01625             write(STDOUT_FILENO, "\r", 1);
01626          write(STDOUT_FILENO, buf, res);
01627          if ((buf[res-1] == '\n') || (buf[res-2] == '\n')) {
01628             *cp = CC_REFRESH;
01629             return(1);
01630          } else
01631             lastpos = 1;
01632       }
01633    }
01634 
01635    *cp = '\0';
01636    return (0);
01637 }

static int ast_el_read_history char *   )  [static]
 

Definition at line 2036 of file asterisk.c.

References ast_all_zeros(), ast_el_add_history(), and ast_el_initialize().

Referenced by ast_remotecontrol().

02037 {
02038    char buf[256];
02039    FILE *f;
02040    int ret = -1;
02041 
02042    if (el_hist == NULL || el == NULL)
02043       ast_el_initialize();
02044 
02045    if ((f = fopen(filename, "r")) == NULL)
02046       return ret;
02047 
02048    while (!feof(f)) {
02049       fgets(buf, sizeof(buf), f);
02050       if (!strcmp(buf, "_HiStOrY_V2_\n"))
02051          continue;
02052       if (ast_all_zeros(buf))
02053          continue;
02054       if ((ret = ast_el_add_history(buf)) == -1)
02055          break;
02056    }
02057    fclose(f);
02058 
02059    return ret;
02060 }

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

Definition at line 1811 of file asterisk.c.

Referenced by ast_cli_display_match_list().

01812 {
01813    char *s1, *s2;
01814 
01815    s1 = ((char **)i1)[0];
01816    s2 = ((char **)i2)[0];
01817 
01818    return strcasecmp(s1, s2);
01819 }

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

Definition at line 1776 of file asterisk.c.

References AST_CLI_COMPLETE_EOF, ast_realloc, strdup, and strsep().

Referenced by cli_complete().

01777 {
01778    char **match_list = NULL, *retstr;
01779    size_t match_list_len;
01780    int matches = 0;
01781 
01782    match_list_len = 1;
01783    while ( (retstr = strsep(&buf, " ")) != NULL) {
01784 
01785       if (!strcmp(retstr, AST_CLI_COMPLETE_EOF))
01786          break;
01787       if (matches + 1 >= match_list_len) {
01788          match_list_len <<= 1;
01789          if (!(match_list = ast_realloc(match_list, match_list_len * sizeof(char *)))) {
01790             /* TODO: Handle memory allocation failure */
01791          }
01792       }
01793 
01794       match_list[matches++] = strdup(retstr);
01795    }
01796 
01797    if (!match_list)
01798       return (char **) NULL;
01799 
01800    if (matches >= match_list_len) {
01801       if (!(match_list = ast_realloc(match_list, (match_list_len + 1) * sizeof(char *)))) {
01802          /* TODO: Handle memory allocation failure */
01803       }
01804    }
01805 
01806    match_list[matches] = (char *) NULL;
01807 
01808    return match_list;
01809 }

static int ast_el_write_history char *   )  [static]
 

Definition at line 2026 of file asterisk.c.

References ast_el_initialize().

02027 {
02028    HistEvent ev;
02029 
02030    if (el_hist == NULL || el == NULL)
02031       ast_el_initialize();
02032 
02033    return (history(el_hist, &ev, H_SAVE, filename));
02034 }

static AST_LIST_HEAD_STATIC thread_list  ,
thread_list_t 
[static]
 

static AST_LIST_HEAD_STATIC file_versions  ,
file_version 
[static]
 

static AST_LIST_HEAD_STATIC atexits  ,
ast_atexit 
[static]
 

static int ast_makesocket void   )  [static]
 

Definition at line 892 of file asterisk.c.

References AF_LOCAL, ast_log(), AST_MAX_CONNECTS, ast_pthread_create_background, ast_register_verbose(), ast_strlen_zero(), consoles, group, listener(), LOG_WARNING, network_verboser(), and PF_LOCAL.

00893 {
00894    struct sockaddr_un sunaddr;
00895    int res;
00896    int x;
00897    uid_t uid = -1;
00898    gid_t gid = -1;
00899 
00900    for (x = 0; x < AST_MAX_CONNECTS; x++) 
00901       consoles[x].fd = -1;
00902    unlink(ast_config_AST_SOCKET);
00903    ast_socket = socket(PF_LOCAL, SOCK_STREAM, 0);
00904    if (ast_socket < 0) {
00905       ast_log(LOG_WARNING, "Unable to create control socket: %s\n", strerror(errno));
00906       return -1;
00907    }     
00908    memset(&sunaddr, 0, sizeof(sunaddr));
00909    sunaddr.sun_family = AF_LOCAL;
00910    ast_copy_string(sunaddr.sun_path, ast_config_AST_SOCKET, sizeof(sunaddr.sun_path));
00911    res = bind(ast_socket, (struct sockaddr *)&sunaddr, sizeof(sunaddr));
00912    if (res) {
00913       ast_log(LOG_WARNING, "Unable to bind socket to %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
00914       close(ast_socket);
00915       ast_socket = -1;
00916       return -1;
00917    }
00918    res = listen(ast_socket, 2);
00919    if (res < 0) {
00920       ast_log(LOG_WARNING, "Unable to listen on socket %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
00921       close(ast_socket);
00922       ast_socket = -1;
00923       return -1;
00924    }
00925    ast_register_verbose(network_verboser);
00926    ast_pthread_create_background(&lthread, NULL, listener, NULL);
00927 
00928    if (!ast_strlen_zero(ast_config_AST_CTL_OWNER)) {
00929       struct passwd *pw;
00930       if ((pw = getpwnam(ast_config_AST_CTL_OWNER)) == NULL)
00931          ast_log(LOG_WARNING, "Unable to find uid of user %s\n", ast_config_AST_CTL_OWNER);
00932       else
00933          uid = pw->pw_uid;
00934    }
00935       
00936    if (!ast_strlen_zero(ast_config_AST_CTL_GROUP)) {
00937       struct group *grp;
00938       if ((grp = getgrnam(ast_config_AST_CTL_GROUP)) == NULL)
00939          ast_log(LOG_WARNING, "Unable to find gid of group %s\n", ast_config_AST_CTL_GROUP);
00940       else
00941          gid = grp->gr_gid;
00942    }
00943 
00944    if (chown(ast_config_AST_SOCKET, uid, gid) < 0)
00945       ast_log(LOG_WARNING, "Unable to change ownership of %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
00946 
00947    if (!ast_strlen_zero(ast_config_AST_CTL_PERMISSIONS)) {
00948       int p1;
00949       mode_t p;
00950       sscanf(ast_config_AST_CTL_PERMISSIONS, "%o", &p1);
00951       p = p1;
00952       if ((chmod(ast_config_AST_SOCKET, p)) < 0)
00953          ast_log(LOG_WARNING, "Unable to change file permissions of %s: %s\n", ast_config_AST_SOCKET, strerror(errno));
00954    }
00955 
00956    return 0;
00957 }

int64_t ast_mark int  i,
int  startstop
 

Definition at line 426 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().

00427 {
00428    if (!prof_data || i < 0 || i > prof_data->entries) /* invalid index */
00429       return 0;
00430    if (startstop == 1)
00431       prof_data->e[i].mark = rdtsc();
00432    else {
00433       prof_data->e[i].mark = (rdtsc() - prof_data->e[i].mark);
00434       if (prof_data->e[i].scale > 1)
00435          prof_data->e[i].mark /= prof_data->e[i].scale;
00436       prof_data->e[i].value += prof_data->e[i].mark;
00437       prof_data->e[i].events++;
00438    }
00439    return prof_data->e[i].mark;
00440 }

AST_MUTEX_DEFINE_STATIC safe_system_lock   ) 
 

static void ast_network_puts const char *  string  )  [static]
 

write the string to all attached console clients

Definition at line 744 of file asterisk.c.

References AST_MAX_CONNECTS, consoles, and fdprint().

Referenced by ast_console_puts().

00745 {
00746    int x;
00747    for (x=0; x < AST_MAX_CONNECTS; x++) {
00748       if (consoles[x].fd > -1) 
00749          fdprint(consoles[x].p[1], string);
00750    }
00751 }

static void ast_network_puts_mutable const char *  string  )  [static]
 

log the string to all attached console clients

Definition at line 719 of file asterisk.c.

References AST_MAX_CONNECTS, consoles, and fdprint().

Referenced by ast_console_puts_mutable(), and network_verboser().

00720 {
00721    int x;
00722    for (x = 0;x < AST_MAX_CONNECTS; x++) {
00723       if (consoles[x].mute)
00724          continue;
00725       if (consoles[x].fd > -1) 
00726          fdprint(consoles[x].p[1], string);
00727    }
00728 }

int64_t ast_profile int  i,
int64_t  delta
 

Definition at line 394 of file asterisk.c.

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

00395 {
00396    if (!prof_data || i < 0 || i > prof_data->entries) /* invalid index */
00397       return 0;
00398    if (prof_data->e[i].scale > 1)
00399       delta /= prof_data->e[i].scale;
00400    prof_data->e[i].value += delta;
00401    prof_data->e[i].events++;
00402    return prof_data->e[i].value;
00403 }

static void ast_readconfig void   )  [static]
 

Definition at line 2185 of file asterisk.c.

References ast_config_load(), ast_log(), ast_opt_override_config, ast_variable_browse(), config, LOG_WARNING, ast_variable::name, ast_variable::next, and ast_variable::value.

02186 {
02187    struct ast_config *cfg;
02188    struct ast_variable *v;
02189    char *config = AST_CONFIG_FILE;
02190 
02191    if (ast_opt_override_config) {
02192       cfg = ast_config_load(ast_config_AST_CONFIG_FILE);
02193       if (!cfg)
02194          ast_log(LOG_WARNING, "Unable to open specified master config file '%s', using built-in defaults\n", ast_config_AST_CONFIG_FILE);
02195    } else 
02196       cfg = ast_config_load(config);
02197 
02198    /* init with buildtime config */
02199    ast_copy_string(ast_config_AST_CONFIG_DIR, AST_CONFIG_DIR, sizeof(ast_config_AST_CONFIG_DIR));
02200    ast_copy_string(ast_config_AST_SPOOL_DIR, AST_SPOOL_DIR, sizeof(ast_config_AST_SPOOL_DIR));
02201    ast_copy_string(ast_config_AST_MODULE_DIR, AST_MODULE_DIR, sizeof(ast_config_AST_MODULE_DIR));
02202    snprintf(ast_config_AST_MONITOR_DIR, sizeof(ast_config_AST_MONITOR_DIR) - 1, "%s/monitor", ast_config_AST_SPOOL_DIR);
02203    ast_copy_string(ast_config_AST_VAR_DIR, AST_VAR_DIR, sizeof(ast_config_AST_VAR_DIR));
02204    ast_copy_string(ast_config_AST_DATA_DIR, AST_DATA_DIR, sizeof(ast_config_AST_DATA_DIR));
02205    ast_copy_string(ast_config_AST_LOG_DIR, AST_LOG_DIR, sizeof(ast_config_AST_LOG_DIR));
02206    ast_copy_string(ast_config_AST_AGI_DIR, AST_AGI_DIR, sizeof(ast_config_AST_AGI_DIR));
02207    ast_copy_string(ast_config_AST_DB, AST_DB, sizeof(ast_config_AST_DB));
02208    ast_copy_string(ast_config_AST_KEY_DIR, AST_KEY_DIR, sizeof(ast_config_AST_KEY_DIR));
02209    ast_copy_string(ast_config_AST_PID, AST_PID, sizeof(ast_config_AST_PID));
02210    ast_copy_string(ast_config_AST_SOCKET, AST_SOCKET, sizeof(ast_config_AST_SOCKET));
02211    ast_copy_string(ast_config_AST_RUN_DIR, AST_RUN_DIR, sizeof(ast_config_AST_RUN_DIR));
02212 
02213    /* no asterisk.conf? no problem, use buildtime config! */
02214    if (!cfg) {
02215       return;
02216    }
02217 
02218    for (v = ast_variable_browse(cfg, "files"); v; v = v->next) {
02219       if (!strcasecmp(v->name, "astctlpermissions"))
02220          ast_copy_string(ast_config_AST_CTL_PERMISSIONS, v->value, sizeof(ast_config_AST_CTL_PERMISSIONS));
02221       else if (!strcasecmp(v->name, "astctlowner"))
02222          ast_copy_string(ast_config_AST_CTL_OWNER, v->value, sizeof(ast_config_AST_CTL_OWNER));
02223       else if (!strcasecmp(v->name, "astctlgroup"))
02224          ast_copy_string(ast_config_AST_CTL_GROUP, v->value, sizeof(ast_config_AST_CTL_GROUP));
02225       else if (!strcasecmp(v->name, "astctl"))
02226          ast_copy_string(ast_config_AST_CTL, v->value, sizeof(ast_config_AST_CTL));
02227    }
02228 
02229    for (v = ast_variable_browse(cfg, "directories"); v; v = v->next) {
02230       if (!strcasecmp(v->name, "astetcdir")) {
02231          ast_copy_string(ast_config_AST_CONFIG_DIR, v->value, sizeof(ast_config_AST_CONFIG_DIR));
02232       } else if (!strcasecmp(v->name, "astspooldir")) {
02233          ast_copy_string(ast_config_AST_SPOOL_DIR, v->value, sizeof(ast_config_AST_SPOOL_DIR));
02234          snprintf(ast_config_AST_MONITOR_DIR, sizeof(ast_config_AST_MONITOR_DIR) - 1, "%s/monitor", v->value);
02235       } else if (!strcasecmp(v->name, "astvarlibdir")) {
02236          ast_copy_string(ast_config_AST_VAR_DIR, v->value, sizeof(ast_config_AST_VAR_DIR));
02237          snprintf(ast_config_AST_DB, sizeof(ast_config_AST_DB), "%s/astdb", v->value);
02238       } else if (!strcasecmp(v->name, "astdatadir")) {
02239          ast_copy_string(ast_config_AST_DATA_DIR, v->value, sizeof(ast_config_AST_DATA_DIR));
02240          snprintf(ast_config_AST_KEY_DIR, sizeof(ast_config_AST_KEY_DIR), "%s/keys", v->value);
02241       } else if (!strcasecmp(v->name, "astlogdir")) {
02242          ast_copy_string(ast_config_AST_LOG_DIR, v->value, sizeof(ast_config_AST_LOG_DIR));
02243       } else if (!strcasecmp(v->name, "astagidir")) {
02244          ast_copy_string(ast_config_AST_AGI_DIR, v->value, sizeof(ast_config_AST_AGI_DIR));
02245       } else if (!strcasecmp(v->name, "astrundir")) {
02246          snprintf(ast_config_AST_PID, sizeof(ast_config_AST_PID), "%s/%s", v->value, "asterisk.pid");
02247          snprintf(ast_config_AST_SOCKET, sizeof(ast_config_AST_SOCKET), "%s/%s", v->value, ast_config_AST_CTL);
02248          ast_copy_string(ast_config_AST_RUN_DIR, v->value, sizeof(ast_config_AST_RUN_DIR));
02249       } else if (!strcasecmp(v->name, "astmoddir")) {
02250          ast_copy_string(ast_config_AST_MODULE_DIR, v->value, sizeof(ast_config_AST_MODULE_DIR));
02251       }
02252    }
02253 
02254    for (v = ast_variable_browse(cfg, "options"); v; v = v->next) {
02255       /* verbose level (-v at startup) */
02256       if (!strcasecmp(v->name, "verbose")) {
02257          option_verbose = atoi(v->value);
02258       /* whether or not to force timestamping in CLI verbose output. (-T at startup) */
02259       } else if (!strcasecmp(v->name, "timestamp")) {
02260          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TIMESTAMP);
02261       /* whether or not to support #exec in config files */
02262       } else if (!strcasecmp(v->name, "execincludes")) {
02263          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_EXEC_INCLUDES);
02264       /* debug level (-d at startup) */
02265       } else if (!strcasecmp(v->name, "debug")) {
02266          option_debug = 0;
02267          if (sscanf(v->value, "%d", &option_debug) != 1) {
02268             option_debug = ast_true(v->value);
02269          }
02270 #if HAVE_WORKING_FORK
02271       /* Disable forking (-f at startup) */
02272       } else if (!strcasecmp(v->name, "nofork")) {
02273          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_NO_FORK);
02274       /* Always fork, even if verbose or debug are enabled (-F at startup) */
02275       } else if (!strcasecmp(v->name, "alwaysfork")) {
02276          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_ALWAYS_FORK);
02277 #endif
02278       /* Run quietly (-q at startup ) */
02279       } else if (!strcasecmp(v->name, "quiet")) {
02280          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_QUIET);
02281       /* Run as console (-c at startup, implies nofork) */
02282       } else if (!strcasecmp(v->name, "console")) {
02283          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_CONSOLE);
02284       /* Run with high priority if the O/S permits (-p at startup) */
02285       } else if (!strcasecmp(v->name, "highpriority")) {
02286          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_HIGH_PRIORITY);
02287       /* Initialize RSA auth keys (IAX2) (-i at startup) */
02288       } else if (!strcasecmp(v->name, "initcrypto")) {
02289          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_INIT_KEYS);
02290       /* Disable ANSI colors for console (-c at startup) */
02291       } else if (!strcasecmp(v->name, "nocolor")) {
02292          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_NO_COLOR);
02293       /* Disable some usage warnings for picky people :p */
02294       } else if (!strcasecmp(v->name, "dontwarn")) {
02295          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_DONT_WARN);
02296       /* Dump core in case of crash (-g) */
02297       } else if (!strcasecmp(v->name, "dumpcore")) {
02298          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_DUMP_CORE);
02299       /* Cache recorded sound files to another directory during recording */
02300       } else if (!strcasecmp(v->name, "cache_record_files")) {
02301          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_CACHE_RECORD_FILES);
02302       /* Specify cache directory */
02303       }  else if (!strcasecmp(v->name, "record_cache_dir")) {
02304          ast_copy_string(record_cache_dir, v->value, AST_CACHE_DIR_LEN);
02305       /* Build transcode paths via SLINEAR, instead of directly */
02306       } else if (!strcasecmp(v->name, "transcode_via_sln")) {
02307          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TRANSCODE_VIA_SLIN);
02308       /* Transmit SLINEAR silence while a channel is being recorded */
02309       } else if (!strcasecmp(v->name, "transmit_silence_during_record")) {
02310          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_TRANSMIT_SILENCE);
02311       /* Enable internal timing */
02312       } else if (!strcasecmp(v->name, "internal_timing")) {
02313          ast_set2_flag(&ast_options, ast_true(v->value), AST_OPT_FLAG_INTERNAL_TIMING);
02314       } else if (!strcasecmp(v->name, "maxcalls")) {
02315          if ((sscanf(v->value, "%d", &option_maxcalls) != 1) || (option_maxcalls < 0)) {
02316             option_maxcalls = 0;
02317          }
02318       } else if (!strcasecmp(v->name, "maxload")) {
02319          double test[1];
02320 
02321          if (getloadavg(test, 1) == -1) {
02322             ast_log(LOG_ERROR, "Cannot obtain load average on this system. 'maxload' option disabled.\n");
02323             option_maxload = 0.0;
02324          } else if ((sscanf(v->value, "%lf", &option_maxload) != 1) || (option_maxload < 0.0)) {
02325             option_maxload = 0.0;
02326          }
02327       /* Set the maximum amount of open files */
02328       } else if (!strcasecmp(v->name, "maxfiles")) {
02329          set_ulimit(atoi(v->value));
02330       /* What user to run as */
02331       } else if (!strcasecmp(v->name, "runuser")) {
02332          ast_copy_string(ast_config_AST_RUN_USER, v->value, sizeof(ast_config_AST_RUN_USER));
02333       /* What group to run as */
02334       } else if (!strcasecmp(v->name, "rungroup")) {
02335          ast_copy_string(ast_config_AST_RUN_GROUP, v->value, sizeof(ast_config_AST_RUN_GROUP));
02336       } else if (!strcasecmp(v->name, "systemname")) {
02337          ast_copy_string(ast_config_AST_SYSTEM_NAME, v->value, sizeof(ast_config_AST_SYSTEM_NAME));
02338       } else if (!strcasecmp(v->name, "languageprefix")) {
02339          ast_language_is_prefix = ast_true(v->value);
02340       }
02341    }
02342    ast_config_destroy(cfg);
02343 }

int ast_register_atexit void(*)(void)  func  ) 
 

Register a function to be executed before Asterisk exits.

Parameters:
func The callback function to use.
Returns:
Zero on success, -1 on error.

Definition at line 571 of file asterisk.c.

References ast_calloc, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_UNLOCK, and ast_unregister_atexit().

Referenced by do_reload(), and load_module().

00572 {
00573    int res = -1;
00574    struct ast_atexit *ae;
00575    ast_unregister_atexit(func);  
00576    AST_LIST_LOCK(&atexits);
00577    if ((ae = ast_calloc(1, sizeof(*ae)))) {
00578       AST_LIST_INSERT_HEAD(&atexits, ae, list);
00579       ae->func = func;
00580       res = 0;
00581    }
00582    AST_LIST_UNLOCK(&atexits);
00583    return res;
00584 }

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 248 of file asterisk.c.

References ast_calloc, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_UNLOCK, ast_strdupa, and ast_strip_quoted().

00249 {
00250    struct file_version *new;
00251    char *work;
00252    size_t version_length;
00253 
00254    work = ast_strdupa(version);
00255    work = ast_strip(ast_strip_quoted(work, "$", "$"));
00256    version_length = strlen(work) + 1;
00257    
00258    if (!(new = ast_calloc(1, sizeof(*new) + version_length)))
00259       return;
00260 
00261    new->file = file;
00262    new->version = (char *) new + sizeof(*new);
00263    memcpy(new->version, work, version_length);
00264    AST_LIST_LOCK(&file_versions);
00265    AST_LIST_INSERT_HEAD(&file_versions, new, list);
00266    AST_LIST_UNLOCK(&file_versions);
00267 }

void ast_register_thread char *  name  ) 
 

Definition at line 298 of file asterisk.c.

References ast_calloc, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, and AST_LIST_UNLOCK.

Referenced by dummy_start().

00299 { 
00300    struct thread_list_t *new = ast_calloc(1, sizeof(*new));
00301 
00302    if (!new)
00303       return;
00304    new->id = pthread_self();
00305    new->name = name; /* steal the allocated memory for the thread name */
00306    AST_LIST_LOCK(&thread_list);
00307    AST_LIST_INSERT_HEAD(&thread_list, new, list);
00308    AST_LIST_UNLOCK(&thread_list);
00309 }

static void ast_remotecontrol char *  data  )  [static]
 

Definition at line 2062 of file asterisk.c.

References ast_el_initialize(), ast_el_read_char(), ast_el_read_history(), ast_log(), ast_opt_exec, ast_opt_mute, ast_strlen_zero(), ast_verbose(), pollfd::events, pollfd::fd, fdprint(), hostname, LOG_WARNING, poll(), POLLIN, remoteconsolehandler(), pollfd::revents, and strsep().

02063 {
02064    char buf[80];
02065    int res;
02066    char filename[80] = "";
02067    char *hostname;
02068    char *cpid;
02069    char *version;
02070    int pid;
02071    char tmp[80];
02072    char *stringp = NULL;
02073 
02074    char *ebuf;
02075    int num = 0;
02076 
02077    read(ast_consock, buf, sizeof(buf));
02078    if (data)
02079       write(ast_consock, data, strlen(data) + 1);
02080    stringp = buf;
02081    hostname = strsep(&stringp, "/");
02082    cpid = strsep(&stringp, "/");
02083    version = strsep(&stringp, "\n");
02084    if (!version)
02085       version = "<Version Unknown>";
02086    stringp = hostname;
02087    strsep(&stringp, ".");
02088    if (cpid)
02089       pid = atoi(cpid);
02090    else
02091       pid = -1;
02092    snprintf(tmp, sizeof(tmp), "core set verbose atleast %d", option_verbose);
02093    fdprint(ast_consock, tmp);
02094    snprintf(tmp, sizeof(tmp), "core set debug atleast %d", option_debug);
02095    fdprint(ast_consock, tmp);
02096    if (ast_opt_mute) {
02097       snprintf(tmp, sizeof(tmp), "log and verbose output currently muted ('logger unmute' to unmute)");
02098       fdprint(ast_consock, tmp);
02099    }
02100    ast_verbose("Connected to Asterisk %s currently running on %s (pid = %d)\n", version, hostname, pid);
02101    remotehostname = hostname;
02102    if (getenv("HOME")) 
02103       snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
02104    if (el_hist == NULL || el == NULL)
02105       ast_el_initialize();
02106 
02107    el_set(el, EL_GETCFN, ast_el_read_char);
02108 
02109    if (!ast_strlen_zero(filename))
02110       ast_el_read_history(filename);
02111 
02112    if (ast_opt_exec && data) {  /* hack to print output then exit if asterisk -rx is used */
02113       char tempchar;
02114       struct pollfd fds;
02115       fds.fd = ast_consock;
02116       fds.events = POLLIN;
02117       fds.revents = 0;
02118       while (poll(&fds, 1, 100) > 0)
02119          ast_el_read_char(el, &tempchar);
02120       return;
02121    }
02122    for (;;) {
02123       ebuf = (char *)el_gets(el, &num);
02124 
02125       if (!ast_strlen_zero(ebuf)) {
02126          if (ebuf[strlen(ebuf)-1] == '\n')
02127             ebuf[strlen(ebuf)-1] = '\0';
02128          if (!remoteconsolehandler(ebuf)) {
02129             res = write(ast_consock, ebuf, strlen(ebuf) + 1);
02130             if (res < 1) {
02131                ast_log(LOG_WARNING, "Unable to write: %s\n", strerror(errno));
02132                break;
02133             }
02134          }
02135       }
02136 
02137       if (need_reload) {
02138          need_reload = 0;
02139          ast_module_reload(NULL);
02140       }
02141    }
02142    printf("\nDisconnected from Asterisk server\n");
02143 }

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 617 of file asterisk.c.

References ast_mutex_lock(), ast_mutex_unlock(), and null_sig_handler().

Referenced by ast_safe_system().

00618 {
00619    unsigned int level;
00620 
00621    ast_mutex_lock(&safe_system_lock);
00622    level = safe_system_level++;
00623 
00624    /* only replace the handler if it has not already been done */
00625    if (level == 0)
00626       safe_system_prev_handler = signal(SIGCHLD, null_sig_handler);
00627 
00628    ast_mutex_unlock(&safe_system_lock);
00629 }

static void ast_run_atexits void   )  [static]
 

Definition at line 1093 of file asterisk.c.

References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, and ast_atexit::func.

01094 {
01095    struct ast_atexit *ae;
01096    AST_LIST_LOCK(&atexits);
01097    AST_LIST_TRAVERSE(&atexits, ae, list) {
01098       if (ae->func) 
01099          ae->func();
01100    }
01101    AST_LIST_UNLOCK(&atexits);
01102 }

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 645 of file asterisk.c.

References ast_opt_high_priority, ast_replace_sigchld(), and ast_set_priority().

Referenced by ast_closestream(), ast_monitor_change_fname(), ast_monitor_start(), ast_monitor_stop(), consolehandler(), process_text_line(), and remoteconsolehandler().

00646 {
00647    pid_t pid;
00648 #ifdef HAVE_WORKING_FORK
00649    int x;
00650 #endif
00651    int res;
00652    struct rusage rusage;
00653    int status;
00654 
00655 #if defined(HAVE_WORKING_FORK) || defined(HAVE_WORKING_VFORK)
00656    ast_replace_sigchld();
00657 
00658 #ifdef HAVE_WORKING_FORK
00659    pid = fork();
00660 #else
00661    pid = vfork();
00662 #endif   
00663 
00664    if (pid == 0) {
00665 #ifdef HAVE_WORKING_FORK
00666       if (ast_opt_high_priority)
00667          ast_set_priority(0);
00668       /* Close file descriptors and launch system command */
00669       for (x = STDERR_FILENO + 1; x < 4096; x++)
00670          close(x);
00671 #endif
00672       execl("/bin/sh", "/bin/sh", "-c", s, (char *) NULL);
00673       _exit(1);
00674    } else if (pid > 0) {
00675       for (;;) {
00676          res = wait4(pid, &status, 0, &rusage);
00677          if (res > -1) {
00678             res = WIFEXITED(status) ? WEXITSTATUS(status) : -1;
00679             break;
00680          } else if (errno != EINTR) 
00681             break;
00682       }
00683    } else {
00684       ast_log(LOG_WARNING, "Fork failed: %s\n", strerror(errno));
00685       res = -1;
00686    }
00687 
00688    ast_unreplace_sigchld();
00689 #else
00690    res = -1;
00691 #endif
00692 
00693    return res;
00694 }

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 1055 of file asterisk.c.

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

Referenced by ast_safe_system(), launch_script(), and spawn_mp3().

01056 {
01057    struct sched_param sched;
01058    memset(&sched, 0, sizeof(sched));
01059 #ifdef __linux__
01060    if (pri) {  
01061       sched.sched_priority = 10;
01062       if (sched_setscheduler(0, SCHED_RR, &sched)) {
01063          ast_log(LOG_WARNING, "Unable to set high priority\n");
01064          return -1;
01065       } else
01066          if (option_verbose)
01067             ast_verbose("Set to realtime thread\n");
01068    } else {
01069       sched.sched_priority = 0;
01070       if (sched_setscheduler(0, SCHED_OTHER, &sched)) {
01071          ast_log(LOG_WARNING, "Unable to set normal priority\n");
01072          return -1;
01073       }
01074    }
01075 #else
01076    if (pri) {
01077       if (setpriority(PRIO_PROCESS, 0, -10) == -1) {
01078          ast_log(LOG_WARNING, "Unable to set high priority\n");
01079          return -1;
01080       } else
01081          if (option_verbose)
01082             ast_verbose("Set to high priority\n");
01083    } else {
01084       if (setpriority(PRIO_PROCESS, 0, 0) == -1) {
01085          ast_log(LOG_WARNING, "Unable to set normal priority\n");
01086          return -1;
01087       }
01088    }
01089 #endif
01090    return 0;
01091 }

static int ast_tryconnect void   )  [static]
 

Definition at line 959 of file asterisk.c.

References AF_LOCAL, ast_log(), LOG_WARNING, and PF_LOCAL.

00960 {
00961    struct sockaddr_un sunaddr;
00962    int res;
00963    ast_consock = socket(PF_LOCAL, SOCK_STREAM, 0);
00964    if (ast_consock < 0) {
00965       ast_log(LOG_WARNING, "Unable to create socket: %s\n", strerror(errno));
00966       return 0;
00967    }
00968    memset(&sunaddr, 0, sizeof(sunaddr));
00969    sunaddr.sun_family = AF_LOCAL;
00970    ast_copy_string(sunaddr.sun_path, (char *)ast_config_AST_SOCKET, sizeof(sunaddr.sun_path));
00971    res = connect(ast_consock, (struct sockaddr *)&sunaddr, sizeof(sunaddr));
00972    if (res) {
00973       close(ast_consock);
00974       ast_consock = -1;
00975       return 0;
00976    } else
00977       return 1;
00978 }

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 586 of file asterisk.c.

References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, and ast_atexit::func.

Referenced by ast_register_atexit(), and do_reload().

00587 {
00588    struct ast_atexit *ae;
00589    AST_LIST_LOCK(&atexits);
00590    AST_LIST_TRAVERSE_SAFE_BEGIN(&atexits, ae, list) {
00591       if (ae->func == func) {
00592          AST_LIST_REMOVE_CURRENT(&atexits, list);
00593          break;
00594       }
00595    }
00596    AST_LIST_TRAVERSE_SAFE_END
00597    AST_LIST_UNLOCK(&atexits);
00598 }

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 269 of file asterisk.c.

References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, and free.

00270 {
00271    struct file_version *find;
00272 
00273    AST_LIST_LOCK(&file_versions);
00274    AST_LIST_TRAVERSE_SAFE_BEGIN(&file_versions, find, list) {
00275       if (!strcasecmp(find->file, file)) {
00276          AST_LIST_REMOVE_CURRENT(&file_versions, list);
00277          break;
00278       }
00279    }
00280    AST_LIST_TRAVERSE_SAFE_END;
00281    AST_LIST_UNLOCK(&file_versions);
00282    if (find)
00283       free(find);
00284 }

void ast_unregister_thread void *  id  ) 
 

Definition at line 311 of file asterisk.c.

References AST_LIST_LOCK, AST_LIST_REMOVE_CURRENT, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, AST_LIST_UNLOCK, and free.

Referenced by dummy_start().

00312 {
00313    struct thread_list_t *x;
00314 
00315    AST_LIST_LOCK(&thread_list);
00316    AST_LIST_TRAVERSE_SAFE_BEGIN(&thread_list, x, list) {
00317       if ((void *) x->id == id) {
00318          AST_LIST_REMOVE_CURRENT(&thread_list, list);
00319          break;
00320       }
00321    }
00322    AST_LIST_TRAVERSE_SAFE_END;
00323    AST_LIST_UNLOCK(&thread_list);
00324    if (x) {
00325       free(x->name);
00326       free(x);
00327    }
00328 }

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 631 of file asterisk.c.

References ast_mutex_lock(), and ast_mutex_unlock().

Referenced by agi_exec_full().

00632 {
00633    unsigned int level;
00634 
00635    ast_mutex_lock(&safe_system_lock);
00636    level = --safe_system_level;
00637 
00638    /* only restore the handler if we are the last one */
00639    if (level == 0)
00640       signal(SIGCHLD, safe_system_prev_handler);
00641 
00642    ast_mutex_unlock(&safe_system_lock);
00643 }

static void child_handler int  sig  )  [static]
 

Definition at line 1002 of file asterisk.c.

01003 {
01004    /* Must not ever ast_log or ast_verbose within signal handler */
01005    int n, status;
01006 
01007    /*
01008     * Reap all dead children -- not just one
01009     */
01010    for (n = 0; wait4(-1, &status, WNOHANG, NULL) > 0; n++)
01011       ;
01012    if (n == 0 && option_debug)   
01013       printf("Huh?  Child handler, but nobody there?\n");
01014    signal(sig, child_handler);
01015 }

static char* cli_complete EditLine *  el,
int  ch
[static]
 

Definition at line 1869 of file asterisk.c.

References AST_CLI_COMPLETE_EOF, ast_cli_completion_matches(), ast_el_strtoarr(), ast_malloc, ast_opt_remote, ast_realloc, fdprint(), free, and len.

Referenced by ast_el_initialize().

01870 {
01871    int len = 0;
01872    char *ptr;
01873    int nummatches = 0;
01874    char **matches;
01875    int retval = CC_ERROR;
01876    char buf[2048];
01877    int res;
01878 
01879    LineInfo *lf = (LineInfo *)el_line(el);
01880 
01881    *(char *)lf->cursor = '\0';
01882    ptr = (char *)lf->cursor;
01883    if (ptr) {
01884       while (ptr > lf->buffer) {
01885          if (isspace(*ptr)) {
01886             ptr++;
01887             break;
01888          }
01889          ptr--;
01890       }
01891    }
01892 
01893    len = lf->cursor - ptr;
01894 
01895    if (ast_opt_remote) {
01896       snprintf(buf, sizeof(buf),"_COMMAND NUMMATCHES \"%s\" \"%s\"", lf->buffer, ptr); 
01897       fdprint(ast_consock, buf);
01898       res = read(ast_consock, buf, sizeof(buf));
01899       buf[res] = '\0';
01900       nummatches = atoi(buf);
01901 
01902       if (nummatches > 0) {
01903          char *mbuf;
01904          int mlen = 0, maxmbuf = 2048;
01905          /* Start with a 2048 byte buffer */       
01906          if (!(mbuf = ast_malloc(maxmbuf)))
01907             return (char *)(CC_ERROR);
01908          snprintf(buf, sizeof(buf),"_COMMAND MATCHESARRAY \"%s\" \"%s\"", lf->buffer, ptr); 
01909          fdprint(ast_consock, buf);
01910          res = 0;
01911          mbuf[0] = '\0';
01912          while (!strstr(mbuf, AST_CLI_COMPLETE_EOF) && res != -1) {
01913             if (mlen + 1024 > maxmbuf) {
01914                /* Every step increment buffer 1024 bytes */
01915                maxmbuf += 1024;              
01916                if (!(mbuf = ast_realloc(mbuf, maxmbuf)))
01917                   return (char *)(CC_ERROR);
01918             }
01919             /* Only read 1024 bytes at a time */
01920             res = read(ast_consock, mbuf + mlen, 1024);
01921             if (res > 0)
01922                mlen += res;
01923          }
01924          mbuf[mlen] = '\0';
01925 
01926          matches = ast_el_strtoarr(mbuf);
01927          free(mbuf);
01928       } else
01929          matches = (char **) NULL;
01930    } else {
01931       char **p, *oldbuf=NULL;
01932       nummatches = 0;
01933       matches = ast_cli_completion_matches((char *)lf->buffer,ptr);
01934       for (p = matches; p && *p; p++) {
01935          if (!oldbuf || strcmp(*p,oldbuf))
01936             nummatches++;
01937          oldbuf = *p;
01938       }
01939    }
01940 
01941    if (matches) {
01942       int i;
01943       int matches_num, maxlen, match_len;
01944 
01945       if (matches[0][0] != '\0') {
01946          el_deletestr(el, (int) len);
01947          el_insertstr(el, matches[0]);
01948          retval = CC_REFRESH;
01949       }
01950 
01951       if (nummatches == 1) {
01952          /* Found an exact match */
01953          el_insertstr(el, " ");
01954          retval = CC_REFRESH;
01955       } else {
01956          /* Must be more than one match */
01957          for (i=1, maxlen=0; matches[i]; i++) {
01958             match_len = strlen(matches[i]);
01959             if (match_len > maxlen)
01960                maxlen = match_len;
01961          }
01962          matches_num = i - 1;
01963          if (matches_num >1) {
01964             fprintf(stdout, "\n");
01965             ast_cli_display_match_list(matches, nummatches, maxlen);
01966             retval = CC_REDISPLAY;
01967          } else { 
01968             el_insertstr(el," ");
01969             retval = CC_REFRESH;
01970          }
01971       }
01972       for (i = 0; matches[i]; i++)
01973          free(matches[i]);
01974       free(matches);
01975    }
01976 
01977    return (char *)(long)retval;
01978 }

static char* cli_prompt EditLine *  el  )  [static]
 

Definition at line 1639 of file asterisk.c.

References ast_opt_remote, COLOR_BLACK, COLOR_WHITE, hostname, and term_color_code().

Referenced by ast_el_initialize().

01640 {
01641    static char prompt[200];
01642    char *pfmt;
01643    int color_used = 0;
01644    char term_code[20];
01645 
01646    if ((pfmt = getenv("ASTERISK_PROMPT"))) {
01647       char *t = pfmt, *p = prompt;
01648       memset(prompt, 0, sizeof(prompt));
01649       while (*t != '\0' && *p < sizeof(prompt)) {
01650          if (*t == '%') {
01651             char hostname[MAXHOSTNAMELEN]="";
01652             int i;
01653             time_t ts;
01654             struct tm tm;
01655 #ifdef linux
01656             FILE *LOADAVG;
01657 #endif
01658             int fgcolor = COLOR_WHITE, bgcolor = COLOR_BLACK;
01659 
01660             t++;
01661             switch (*t) {
01662             case 'C': /* color */
01663                t++;
01664                if (sscanf(t, "%d;%d%n", &fgcolor, &bgcolor, &i) == 2) {
01665                   strncat(p, term_color_code(term_code, fgcolor, bgcolor, sizeof(term_code)),sizeof(prompt) - strlen(prompt) - 1);
01666                   t += i - 1;
01667                } else if (sscanf(t, "%d%n", &fgcolor, &i) == 1) {
01668                   strncat(p, term_color_code(term_code, fgcolor, 0, sizeof(term_code)),sizeof(prompt) - strlen(prompt) - 1);
01669                   t += i - 1;
01670                }
01671 
01672                /* If the color has been reset correctly, then there's no need to reset it later */
01673                color_used = ((fgcolor == COLOR_WHITE) && (bgcolor == COLOR_BLACK)) ? 0 : 1;
01674                break;
01675             case 'd': /* date */
01676                memset(&tm, 0, sizeof(tm));
01677                time(&ts);
01678                if (localtime_r(&ts, &tm)) 
01679                   strftime(p, sizeof(prompt) - strlen(prompt), "%Y-%m-%d", &tm);
01680                break;
01681             case 'h': /* hostname */
01682                if (!gethostname(hostname, sizeof(hostname) - 1))
01683                   strncat(p, hostname, sizeof(prompt) - strlen(prompt) - 1);
01684                else
01685                   strncat(p, "localhost", sizeof(prompt) - strlen(prompt) - 1);
01686                break;
01687             case 'H': /* short hostname */
01688                if (!gethostname(hostname, sizeof(hostname) - 1)) {
01689                   for (i = 0; i < sizeof(hostname); i++) {
01690                      if (hostname[i] == '.') {
01691                         hostname[i] = '\0';
01692                         break;
01693                      }
01694                   }
01695                   strncat(p, hostname, sizeof(prompt) - strlen(prompt) - 1);
01696                } else
01697                   strncat(p, "localhost", sizeof(prompt) - strlen(prompt) - 1);
01698                break;
01699 #ifdef linux
01700             case 'l': /* load avg */
01701                t++;
01702                if ((LOADAVG = fopen("/proc/loadavg", "r"))) {
01703                   float avg1, avg2, avg3;
01704                   int actproc, totproc, npid, which;
01705                   fscanf(LOADAVG, "%f %f %f %d/%d %d",
01706                      &avg1, &avg2, &avg3, &actproc, &totproc, &npid);
01707                   if (sscanf(t, "%d", &which) == 1) {
01708                      switch (which) {
01709                      case 1:
01710                         snprintf(p, sizeof(prompt) - strlen(prompt), "%.2f", avg1);
01711                         break;
01712                      case 2:
01713                         snprintf(p, sizeof(prompt) - strlen(prompt), "%.2f", avg2);
01714                         break;
01715                      case 3:
01716                         snprintf(p, sizeof(prompt) - strlen(prompt), "%.2f", avg3);
01717                         break;
01718                      case 4:
01719                         snprintf(p, sizeof(prompt) - strlen(prompt), "%d/%d", actproc, totproc);
01720                         break;
01721                      case 5:
01722                         snprintf(p, sizeof(prompt) - strlen(prompt), "%d", npid);
01723                         break;
01724                      }
01725                   }
01726                }
01727                break;
01728 #endif
01729             case 's': /* Asterisk system name (from asterisk.conf) */
01730                strncat(p, ast_config_AST_SYSTEM_NAME, sizeof(prompt) - strlen(prompt) - 1);
01731                break;
01732             case 't': /* time */
01733                memset(&tm, 0, sizeof(tm));
01734                time(&ts);
01735                if (localtime_r(&ts, &tm))
01736                   strftime(p, sizeof(prompt) - strlen(prompt), "%H:%M:%S", &tm);
01737                break;
01738             case '#': /* process console or remote? */
01739                if (!ast_opt_remote) 
01740                   strncat(p, "#", sizeof(prompt) - strlen(prompt) - 1);
01741                else
01742                   strncat(p, ">", sizeof(prompt) - strlen(prompt) - 1);
01743                break;
01744             case '%': /* literal % */
01745                strncat(p, "%", sizeof(prompt) - strlen(prompt) - 1);
01746                break;
01747             case '\0': /* % is last character - prevent bug */
01748                t--;
01749                break;
01750             }
01751             while (*p != '\0')
01752                p++;
01753             t++;
01754          } else {
01755             *p = *t;
01756             p++;
01757             t++;
01758          }
01759       }
01760       if (color_used) {
01761          /* Force colors back to normal at end */
01762          term_color_code(term_code, COLOR_WHITE, COLOR_BLACK, sizeof(term_code));
01763          if (strlen(term_code) > sizeof(prompt) - strlen(prompt))
01764             strncat(prompt + sizeof(prompt) - strlen(term_code) - 1, term_code, strlen(term_code));
01765          else
01766             strncat(p, term_code, sizeof(term_code));
01767       }
01768    } else if (remotehostname)
01769       snprintf(prompt, sizeof(prompt), ASTERISK_PROMPT2, remotehostname);
01770    else
01771       snprintf(prompt, sizeof(prompt), ASTERISK_PROMPT);
01772 
01773    return(prompt);   
01774 }

static char* complete_show_version_files const char *  line,
const char *  word,
int  pos,
int  state
[static]
 

Definition at line 548 of file asterisk.c.

References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, and ast_strdup.

00549 {
00550    struct file_version *find;
00551    int which = 0;
00552    char *ret = NULL;
00553    int matchlen = strlen(word);
00554 
00555    if (pos != 3)
00556       return NULL;
00557 
00558    AST_LIST_LOCK(&file_versions);
00559    AST_LIST_TRAVERSE(&file_versions, find, list) {
00560       if (!strncasecmp(word, find->file, matchlen) && ++which > state) {
00561          ret = ast_strdup(find->file);
00562          break;
00563       }
00564    }
00565    AST_LIST_UNLOCK(&file_versions);
00566 
00567    return ret;
00568 }

static void console_verboser const char *  s  )  [static]
 

Definition at line 1227 of file asterisk.c.

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

01228 {
01229    char tmp[80];
01230    const char *c = NULL;
01231 
01232    if ((c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_4)) ||
01233        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_3)) ||
01234        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_2)) ||
01235        (c = fix_header(tmp, sizeof(tmp), s, VERBOSE_PREFIX_1))) {
01236       fputs(tmp, stdout);
01237       fputs(c, stdout);
01238    } else
01239       fputs(s, stdout);
01240 
01241    fflush(stdout);
01242    
01243    /* Wake up a poll()ing console */
01244    if (ast_opt_console && consolethread != AST_PTHREADT_NULL)
01245       pthread_kill(consolethread, SIGURG);
01246 }

static void consolehandler char *  s  )  [static]
 

Definition at line 1258 of file asterisk.c.

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

01259 {
01260    printf(term_end());
01261    fflush(stdout);
01262 
01263    /* Called when readline data is available */
01264    if (!ast_all_zeros(s))
01265       ast_el_add_history(s);
01266    /* The real handler for bang */
01267    if (s[0] == '!') {
01268       if (s[1])
01269          ast_safe_system(s+1);
01270       else
01271          ast_safe_system(getenv("SHELL") ? getenv("SHELL") : "/bin/sh");
01272    } else 
01273       ast_cli_command(STDOUT_FILENO, s);
01274 }

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

Definition at line 600 of file asterisk.c.

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

00601 {
00602    return write(fd, s, strlen(s) + 1);
00603 }

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

Definition at line 1216 of file asterisk.c.

References COLOR_GRAY, and term_color().

Referenced by console_verboser().

01217 {
01218    const char *c;
01219    if (!strncmp(s, cmp, strlen(cmp))) {
01220       c = s + strlen(cmp);
01221       term_color(outbuf, cmp, COLOR_GRAY, 0, maxout);
01222       return c;
01223    }
01224    return NULL;
01225 }

static int handle_abort_halt int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1418 of file asterisk.c.

References ast_cancel_shutdown(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01419 {
01420    if (argc != 2)
01421       return RESULT_SHOWUSAGE;
01422    ast_cancel_shutdown();
01423    shuttingdown = 0;
01424    return RESULT_SUCCESS;
01425 }

static int handle_bang int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1427 of file asterisk.c.

References RESULT_SUCCESS.

01428 {
01429    return RESULT_SUCCESS;
01430 }

static int handle_restart_gracefully int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1401 of file asterisk.c.

References quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01402 {
01403    if (argc != 2)
01404       return RESULT_SHOWUSAGE;
01405    quit_handler(0, 1 /* nicely */, 1 /* safely */, 1 /* restart */);
01406    return RESULT_SUCCESS;
01407 }

static int handle_restart_now int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1393 of file asterisk.c.

References quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01394 {
01395    if (argc != 2)
01396       return RESULT_SHOWUSAGE;
01397    quit_handler(0, 0 /* not nicely */, 1 /* safely */, 1 /* restart */);
01398    return RESULT_SUCCESS;
01399 }

static int handle_restart_when_convenient int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1409 of file asterisk.c.

References ast_cli(), quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01410 {
01411    if (argc != 3)
01412       return RESULT_SHOWUSAGE;
01413    ast_cli(fd, "Waiting for inactivity to perform restart\n");
01414    quit_handler(0, 2 /* really nicely */, 1 /* safely */, 1 /* restart */);
01415    return RESULT_SUCCESS;
01416 }

static int handle_show_profile int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 442 of file asterisk.c.

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

00443 {
00444    int i, min, max;
00445    char *search = NULL;
00446 
00447    if (prof_data == NULL)
00448       return 0;
00449 
00450    min = 0;
00451    max = prof_data->entries;
00452    if  (argc > 3) { /* specific entries */
00453       if (isdigit(argv[3][0])) {
00454          min = atoi(argv[3]);
00455          if (argc == 5 && strcmp(argv[4], "-"))
00456             max = atoi(argv[4]);
00457       } else
00458          search = argv[3];
00459    }
00460    if (max > prof_data->entries)
00461       max = prof_data->entries;
00462    if (!strcmp(argv[1], "clear")) {
00463       for (i= min; i < max; i++) {
00464          if (!search || strstr(prof_data->e[i].name, search)) {
00465             prof_data->e[i].value = 0;
00466             prof_data->e[i].events = 0;
00467          }
00468       }
00469       return 0;
00470    }
00471    ast_cli(fd, "profile values (%d, allocated %d)\n-------------------\n",
00472       prof_data->entries, prof_data->max_size);
00473    ast_cli(fd, "%6s   %8s  %10s %12s %12s  %s\n", "ID", "Scale", "Events",
00474          "Value", "Average", "Name");
00475    for (i = min; i < max; i++) {
00476       struct profile_entry *e = &prof_data->e[i];
00477       if (!search || strstr(prof_data->e[i].name, search))
00478           ast_cli(fd, "%6d: [%8ld] %10ld %12lld %12lld  %s\n",
00479          i,
00480          (long)e->scale,
00481          (long)e->events, (long long)e->value,
00482          (long long)(e->events ? e->value / e->events : e->value),
00483          e->name);
00484    }
00485    return 0;
00486 }

static int handle_show_threads int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 330 of file asterisk.c.

References ast_cli(), AST_LIST_LOCK, AST_LIST_TRAVERSE, and AST_LIST_UNLOCK.

00331 {
00332    int count = 0;
00333    struct thread_list_t *cur;
00334 
00335    AST_LIST_LOCK(&thread_list);
00336    AST_LIST_TRAVERSE(&thread_list, cur, list) {
00337       ast_cli(fd, "%p %s\n", (void *)cur->id, cur->name);
00338       count++;
00339    }
00340         AST_LIST_UNLOCK(&thread_list);
00341    ast_cli(fd, "%d threads listed.\n", count);
00342    return 0;
00343 }

static int handle_show_version_files int  fd,
int  argc,
char *  argv[]
[static]
 

CLI command to list module versions.

Definition at line 494 of file asterisk.c.

References ast_cli(), AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, FORMAT, RESULT_SHOWUSAGE, and RESULT_SUCCESS.

00495 {
00496 #define FORMAT "%-25.25s %-40.40s\n"
00497    struct file_version *iterator;
00498    regex_t regexbuf;
00499    int havepattern = 0;
00500    int havename = 0;
00501    int count_files = 0;
00502 
00503    switch (argc) {
00504    case 5:
00505       if (!strcasecmp(argv[3], "like")) {
00506          if (regcomp(&regexbuf, argv[4], REG_EXTENDED | REG_NOSUB))
00507             return RESULT_SHOWUSAGE;
00508          havepattern = 1;
00509       } else
00510          return RESULT_SHOWUSAGE;
00511       break;
00512    case 4:
00513       havename = 1;
00514       break;
00515    case 3:
00516       break;
00517    default:
00518       return RESULT_SHOWUSAGE;
00519    }
00520 
00521    ast_cli(fd, FORMAT, "File", "Revision");
00522    ast_cli(fd, FORMAT, "----", "--------");
00523    AST_LIST_LOCK(&file_versions);
00524    AST_LIST_TRAVERSE(&file_versions, iterator, list) {
00525       if (havename && strcasecmp(iterator->file, argv[3]))
00526          continue;
00527 
00528       if (havepattern && regexec(&regexbuf, iterator->file, 0, NULL, 0))
00529          continue;
00530 
00531       ast_cli(fd, FORMAT, iterator->file, iterator->version);
00532       count_files++;
00533       if (havename)
00534          break;
00535    }
00536    AST_LIST_UNLOCK(&file_versions);
00537    if (!havename) {
00538       ast_cli(fd, "%d files listed.\n", count_files);
00539    }
00540 
00541    if (havepattern)
00542       regfree(&regexbuf);
00543 
00544    return RESULT_SUCCESS;
00545 #undef FORMAT
00546 }

static int handle_shutdown_gracefully int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1376 of file asterisk.c.

References quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01377 {
01378    if (argc != 2)
01379       return RESULT_SHOWUSAGE;
01380    quit_handler(0, 1 /* nicely */, 1 /* safely */, 0 /* no restart */);
01381    return RESULT_SUCCESS;
01382 }

static int handle_shutdown_now int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1368 of file asterisk.c.

References quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01369 {
01370    if (argc != 2)
01371       return RESULT_SHOWUSAGE;
01372    quit_handler(0, 0 /* Not nice */, 1 /* safely */, 0 /* not restart */);
01373    return RESULT_SUCCESS;
01374 }

static int handle_shutdown_when_convenient int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1384 of file asterisk.c.

References ast_cli(), quit_handler(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01385 {
01386    if (argc != 3)
01387       return RESULT_SHOWUSAGE;
01388    ast_cli(fd, "Waiting for inactivity to perform halt\n");
01389    quit_handler(0, 2 /* really nicely */, 1 /* safely */, 0 /* don't restart */);
01390    return RESULT_SUCCESS;
01391 }

static int handle_version int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1348 of file asterisk.c.

References ast_cli(), RESULT_SHOWUSAGE, and RESULT_SUCCESS.

01349 {
01350    if (argc != 3)
01351       return RESULT_SHOWUSAGE;
01352    ast_cli(fd, "Asterisk %s built by %s @ %s on a %s running %s on %s\n",
01353       ASTERISK_VERSION, ast_build_user, ast_build_hostname,
01354       ast_build_machine, ast_build_os, ast_build_date);
01355    return RESULT_SUCCESS;
01356 }

static void hup_handler int  num  )  [static]
 

Definition at line 992 of file asterisk.c.

00993 {
00994    if (option_verbose > 1) 
00995       printf("Received HUP signal -- Reloading configs\n");
00996    if (restartnow)
00997       execvp(_argv[0], _argv);
00998    need_reload = 1;
00999    signal(num, hup_handler);
01000 }

static void* listener void *  unused  )  [static]
 

Definition at line 826 of file asterisk.c.

References AF_LOCAL, ast_log(), AST_MAX_CONNECTS, ast_opt_mute, ast_pthread_create_background, consoles, pollfd::events, console::fd, pollfd::fd, fdprint(), len, LOG_ERROR, LOG_WARNING, console::mute, netconsole(), poll(), POLLIN, and s.

Referenced by ast_makesocket().

00827 {
00828    struct sockaddr_un sunaddr;
00829    int s;
00830    socklen_t len;
00831    int x;
00832    int flags;
00833    struct pollfd fds[1];
00834    pthread_attr_t attr;
00835    pthread_attr_init(&attr);
00836    pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
00837    for (;;) {
00838       if (ast_socket < 0)
00839          return NULL;
00840       fds[0].fd = ast_socket;
00841       fds[0].events = POLLIN;
00842       s = poll(fds, 1, -1);
00843       pthread_testcancel();
00844       if (s < 0) {
00845          if (errno != EINTR)
00846             ast_log(LOG_WARNING, "poll returned error: %s\n", strerror(errno));
00847          continue;
00848       }
00849       len = sizeof(sunaddr);
00850       s = accept(ast_socket, (struct sockaddr *)&sunaddr, &len);
00851       if (s < 0) {
00852          if (errno != EINTR)
00853             ast_log(LOG_WARNING, "Accept returned %d: %s\n", s, strerror(errno));
00854       } else {
00855          for (x = 0; x < AST_MAX_CONNECTS; x++) {
00856             if (consoles[x].fd < 0) {
00857                if (socketpair(AF_LOCAL, SOCK_STREAM, 0, consoles[x].p)) {
00858                   ast_log(LOG_ERROR, "Unable to create pipe: %s\n", strerror(errno));
00859                   consoles[x].fd = -1;
00860                   fdprint(s, "Server failed to create pipe\n");
00861                   close(s);
00862                   break;
00863                }
00864                flags = fcntl(consoles[x].p[1], F_GETFL);
00865                fcntl(consoles[x].p[1], F_SETFL, flags | O_NONBLOCK);
00866                consoles[x].fd = s;
00867                consoles[x].mute = ast_opt_mute;
00868                if (ast_pthread_create_background(&consoles[x].t, &attr, netconsole, &consoles[x])) {
00869                   ast_log(LOG_ERROR, "Unable to spawn thread to handle connection: %s\n", strerror(errno));
00870                   close(consoles[x].p[0]);
00871                   close(consoles[x].p[1]);
00872                   consoles[x].fd = -1;
00873                   fdprint(s, "Server failed to spawn thread\n");
00874                   close(s);
00875                }
00876                break;
00877             }
00878          }
00879          if (x >= AST_MAX_CONNECTS) {
00880             fdprint(s, "No more connections allowed\n");
00881             ast_log(LOG_WARNING, "No more connections allowed\n");
00882             close(s);
00883          } else if (consoles[x].fd > -1) {
00884             if (option_verbose > 2) 
00885                ast_verbose(VERBOSE_PREFIX_3 "Remote UNIX connection\n");
00886          }
00887       }
00888    }
00889    return NULL;
00890 }

int main int  argc,
char *  argv[]
 

Definition at line 2345 of file asterisk.c.

References AST_OPT_FLAG_NO_FORK, AST_OPT_FLAG_REMOTE, ast_options, ast_set_flag, and hostname.

02346 {
02347    int c;
02348    char filename[80] = "";
02349    char hostname[MAXHOSTNAMELEN] = "";
02350    char tmp[80];
02351    char * xarg = NULL;
02352    int x;
02353    FILE *f;
02354    sigset_t sigs;
02355    int num;
02356    int is_child_of_nonroot = 0;
02357    char *buf;
02358    char *runuser = NULL, *rungroup = NULL;
02359 
02360    /* Remember original args for restart */
02361    if (argc > sizeof(_argv) / sizeof(_argv[0]) - 1) {
02362       fprintf(stderr, "Truncating argument size to %d\n", (int)(sizeof(_argv) / sizeof(_argv[0])) - 1);
02363       argc = sizeof(_argv) / sizeof(_argv[0]) - 1;
02364    }
02365    for (x=0; x<argc; x++)
02366       _argv[x] = argv[x];
02367    _argv[x] = NULL;
02368 
02369    /* if the progname is rasterisk consider it a remote console */
02370    if (argv[0] && (strstr(argv[0], "rasterisk")) != NULL) {
02371       ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE);
02372    }
02373    if (gethostname(hostname, sizeof(hostname)-1))
02374       ast_copy_string(hostname, "<Unknown>", sizeof(hostname));
02375    ast_mainpid = getpid();
02376    ast_ulaw_init();
02377    ast_alaw_init();
02378    callerid_init();
02379    ast_builtins_init();
02380    ast_utils_init();
02381    tdd_init();
02382    /* When Asterisk restarts after it has dropped the root privileges,
02383     * it can't issue setuid(), setgid(), setgroups() or set_priority() 
02384     */
02385    if (getenv("ASTERISK_ALREADY_NONROOT"))
02386       is_child_of_nonroot=1;
02387    if (getenv("HOME")) 
02388       snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
02389    /* Check for options */
02390    while ((c = getopt(argc, argv, "mtThfFdvVqprRgciInx:U:G:C:L:M:")) != -1) {
02391       switch (c) {
02392 #if HAVE_WORKING_FORK
02393       case 'F':
02394          ast_set_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK);
02395          break;
02396       case 'f':
02397          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
02398          break;
02399 #endif
02400       case 'd':
02401          option_debug++;
02402          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
02403          break;
02404       case 'c':
02405          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_CONSOLE);
02406          break;
02407       case 'n':
02408          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_COLOR);
02409          break;
02410       case 'r':
02411          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE);
02412          break;
02413       case 'R':
02414          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK | AST_OPT_FLAG_REMOTE | AST_OPT_FLAG_RECONNECT);
02415          break;
02416       case 'p':
02417          ast_set_flag(&ast_options, AST_OPT_FLAG_HIGH_PRIORITY);
02418          break;
02419       case 'v':
02420          option_verbose++;
02421          ast_set_flag(&ast_options, AST_OPT_FLAG_NO_FORK);
02422          break;
02423       case 'm':
02424          ast_set_flag(&ast_options, AST_OPT_FLAG_MUTE);
02425          break;
02426       case 'M':
02427          if ((sscanf(optarg, "%d", &option_maxcalls) != 1) || (option_maxcalls < 0))
02428             option_maxcalls = 0;
02429          break;
02430       case 'L':
02431          if ((sscanf(optarg, "%lf", &option_maxload) != 1) || (option_maxload < 0.0))
02432             option_maxload = 0.0;
02433          break;
02434       case 'q':
02435          ast_set_flag(&ast_options, AST_OPT_FLAG_QUIET);
02436          break;
02437       case 't':
02438          ast_set_flag(&ast_options, AST_OPT_FLAG_CACHE_RECORD_FILES);
02439          break;
02440       case 'T':
02441          ast_set_flag(&ast_options, AST_OPT_FLAG_TIMESTAMP);
02442          break;
02443       case 'x':
02444          ast_set_flag(&ast_options, AST_OPT_FLAG_EXEC);
02445          xarg = optarg;
02446          break;
02447       case 'C':
02448          ast_copy_string(ast_config_AST_CONFIG_FILE, optarg, sizeof(ast_config_AST_CONFIG_FILE));
02449          ast_set_flag(&ast_options, AST_OPT_FLAG_OVERRIDE_CONFIG);
02450          break;
02451       case 'I':
02452          ast_set_flag(&ast_options, AST_OPT_FLAG_INTERNAL_TIMING);
02453          break;
02454       case 'i':
02455          ast_set_flag(&ast_options, AST_OPT_FLAG_INIT_KEYS);
02456          break;
02457       case 'g':
02458          ast_set_flag(&ast_options, AST_OPT_FLAG_DUMP_CORE);
02459          break;
02460       case 'h':
02461          show_cli_help();
02462          exit(0);
02463       case 'V':
02464          show_version();
02465          exit(0);
02466       case 'U':
02467          runuser = optarg;
02468          break;
02469       case 'G':
02470          rungroup = optarg;
02471          break;
02472       case '?':
02473          exit(1);
02474       }
02475    }
02476 
02477    if (ast_opt_console || option_verbose || (ast_opt_remote && !ast_opt_exec)) {
02478       ast_register_verbose(console_verboser);
02479       WELCOME_MESSAGE;
02480    }
02481 
02482    if (ast_opt_console && !option_verbose) 
02483       ast_verbose("[ Booting...\n");
02484 
02485    if (ast_opt_always_fork && (ast_opt_remote || ast_opt_console)) {
02486       ast_log(LOG_WARNING, "'alwaysfork' is not compatible with console or remote console mode; ignored\n");
02487       ast_clear_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK);
02488    }
02489 
02490    /* For remote connections, change the name of the remote connection.
02491     * We do this for the benefit of init scripts (which need to know if/when
02492     * the main asterisk process has died yet). */
02493    if (ast_opt_remote) {
02494       strcpy(argv[0], "rasterisk");
02495       for (x = 1; x < argc; x++) {
02496          argv[x] = argv[0] + 10;
02497       }
02498    }
02499 
02500    if (ast_opt_console && !option_verbose) 
02501       ast_verbose("[ Reading Master Configuration ]\n");
02502    ast_readconfig();
02503 
02504    if (!ast_language_is_prefix && !ast_opt_remote)
02505       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");
02506 
02507    if (ast_opt_dump_core) {
02508       struct rlimit l;
02509       memset(&l, 0, sizeof(l));
02510       l.rlim_cur = RLIM_INFINITY;
02511       l.rlim_max = RLIM_INFINITY;
02512       if (setrlimit(RLIMIT_CORE, &l)) {
02513          ast_log(LOG_WARNING, "Unable to disable core size resource limit: %s\n", strerror(errno));
02514       }
02515    }
02516 
02517    if ((!rungroup) && !ast_strlen_zero(ast_config_AST_RUN_GROUP))
02518       rungroup = ast_config_AST_RUN_GROUP;
02519    if ((!runuser) && !ast_strlen_zero(ast_config_AST_RUN_USER))
02520       runuser = ast_config_AST_RUN_USER;
02521 
02522 #ifndef __CYGWIN__
02523 
02524    if (!is_child_of_nonroot) 
02525       ast_set_priority(ast_opt_high_priority);
02526 
02527    if (!is_child_of_nonroot && rungroup) {
02528       struct group *gr;
02529       gr = getgrnam(rungroup);
02530       if (!gr) {
02531          ast_log(LOG_WARNING, "No such group '%s'!\n", rungroup);
02532          exit(1);
02533       }
02534       if (setgid(gr->gr_gid)) {
02535          ast_log(LOG_WARNING, "Unable to setgid to %d (%s)\n", (int)gr->gr_gid, rungroup);
02536          exit(1);
02537       }
02538       if (setgroups(0, NULL)) {
02539          ast_log(LOG_WARNING, "Unable to drop unneeded groups\n");
02540          exit(1);
02541       }
02542       if (option_verbose)
02543          ast_verbose("Running as group '%s'\n", rungroup);
02544    }
02545 
02546    if (!is_child_of_nonroot && runuser) {
02547 #ifdef HAVE_CAP
02548       int has_cap = 1;
02549 #endif /* HAVE_CAP */
02550       struct passwd *pw;
02551       pw = getpwnam(runuser);
02552       if (!pw) {
02553          ast_log(LOG_WARNING, "No such user '%s'!\n", runuser);
02554          exit(1);
02555       }
02556 #ifdef HAVE_CAP
02557       if (prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0)) {
02558          ast_log(LOG_WARNING, "Unable to keep capabilities.\n");
02559          has_cap = 0;
02560       }
02561 #endif /* HAVE_CAP */
02562       if (!rungroup) {
02563          if (setgid(pw->pw_gid)) {
02564             ast_log(LOG_WARNING, "Unable to setgid to %d!\n", (int)pw->pw_gid);
02565             exit(1);
02566          }
02567          if (initgroups(pw->pw_name, pw->pw_gid)) {
02568             ast_log(LOG_WARNING, "Unable to init groups for '%s'\n", runuser);
02569             exit(1);
02570          }
02571       }
02572       if (setuid(pw->pw_uid)) {
02573          ast_log(LOG_WARNING, "Unable to setuid to %d (%s)\n", (int)pw->pw_uid, runuser);
02574          exit(1);
02575       }
02576       setenv("ASTERISK_ALREADY_NONROOT", "yes", 1);
02577       if (option_verbose)
02578          ast_verbose("Running as user '%s'\n", runuser);
02579 #ifdef HAVE_CAP
02580       if (has_cap) {
02581          cap_t cap;
02582 
02583          cap = cap_from_text("cap_net_admin=ep");
02584 
02585          if (cap_set_proc(cap))
02586             ast_log(LOG_WARNING, "Unable to install capabilities.\n");
02587 
02588          if (cap_free(cap))
02589             ast_log(LOG_WARNING, "Unable to drop capabilities.\n");
02590       }
02591 #endif /* HAVE_CAP */
02592    }
02593 
02594 #endif /* __CYGWIN__ */
02595 
02596 #ifdef linux
02597    if (geteuid() && ast_opt_dump_core) {
02598       if (prctl(PR_SET_DUMPABLE, 1, 0, 0, 0) < 0) {
02599          ast_log(LOG_WARNING, "Unable to set the process for core dumps after changing to a non-root user. %s\n", strerror(errno));
02600       }  
02601    }
02602 #endif
02603 
02604    ast_term_init();
02605    printf(term_end());
02606    fflush(stdout);
02607 
02608    if (ast_opt_console && !option_verbose) 
02609       ast_verbose("[ Initializing Custom Configuration Options ]\n");
02610    /* custom config setup */
02611    register_config_cli();
02612    read_config_maps();
02613    
02614    if (ast_opt_console) {
02615       if (el_hist == NULL || el == NULL)
02616          ast_el_initialize();
02617 
02618       if (!ast_strlen_zero(filename))
02619          ast_el_read_history(filename);
02620    }
02621 
02622    if (ast_tryconnect()) {
02623       /* One is already running */
02624       if (ast_opt_remote) {
02625          if (ast_opt_exec) {
02626             ast_remotecontrol(xarg);
02627             quit_handler(0, 0, 0, 0);
02628             exit(0);
02629          }
02630          printf(term_quit());
02631          ast_remotecontrol(NULL);
02632          quit_handler(0, 0, 0, 0);
02633          exit(0);
02634       } else {
02635          ast_log(LOG_ERROR, "Asterisk already running on %s.  Use 'asterisk -r' to connect.\n", ast_config_AST_SOCKET);
02636          printf(term_quit());
02637          exit(1);
02638       }
02639    } else if (ast_opt_remote || ast_opt_exec) {
02640       ast_log(LOG_ERROR, "Unable to connect to remote asterisk (does %s exist?)\n", ast_config_AST_SOCKET);
02641       printf(term_quit());
02642       exit(1);
02643    }
02644    /* Blindly write pid file since we couldn't connect */
02645    unlink(ast_config_AST_PID);
02646    f = fopen(ast_config_AST_PID, "w");
02647    if (f) {
02648       fprintf(f, "%ld\n", (long)getpid());
02649       fclose(f);
02650    } else
02651       ast_log(LOG_WARNING, "Unable to open pid file '%s': %s\n", ast_config_AST_PID, strerror(errno));
02652 
02653 #if HAVE_WORKING_FORK
02654    if (ast_opt_always_fork || !ast_opt_no_fork) {
02655       daemon(0, 0);
02656       ast_mainpid = getpid();
02657       /* Blindly re-write pid file since we are forking */
02658       unlink(ast_config_AST_PID);
02659       f = fopen(ast_config_AST_PID, "w");
02660       if (f) {
02661          fprintf(f, "%ld\n", (long)ast_mainpid);
02662          fclose(f);
02663       } else
02664          ast_log(LOG_WARNING, "Unable to open pid file '%s': %s\n", ast_config_AST_PID, strerror(errno));
02665    }
02666 #endif
02667 
02668    /* Test recursive mutex locking. */
02669    if (test_for_thread_safety())
02670       ast_verbose("Warning! Asterisk is not thread safe.\n");
02671 
02672    ast_makesocket();
02673    sigemptyset(&sigs);
02674    sigaddset(&sigs, SIGHUP);
02675    sigaddset(&sigs, SIGTERM);
02676    sigaddset(&sigs, SIGINT);
02677    sigaddset(&sigs, SIGPIPE);
02678    sigaddset(&sigs, SIGWINCH);
02679    pthread_sigmask(SIG_BLOCK, &sigs, NULL);
02680    signal(SIGURG, urg_handler);
02681    signal(SIGINT, __quit_handler);
02682    signal(SIGTERM, __quit_handler);
02683    signal(SIGHUP, hup_handler);
02684    signal(SIGCHLD, child_handler);
02685    signal(SIGPIPE, SIG_IGN);
02686 
02687    /* ensure that the random number generators are seeded with a different value every time
02688       Asterisk is started
02689    */
02690    srand((unsigned int) getpid() + (unsigned int) time(NULL));
02691    initstate((unsigned int) getpid() * 65536 + (unsigned int) time(NULL), randompool, sizeof(randompool));
02692 
02693    if (init_logger()) {    /* Start logging subsystem */
02694       printf(term_quit());
02695       exit(1);
02696    }
02697 
02698    threadstorage_init();
02699 
02700    if (load_modules(1)) {     /* Load modules */
02701       printf(term_quit());
02702       exit(1);
02703    }
02704 
02705    if (dnsmgr_init()) {    /* Initialize the DNS manager */
02706       printf(term_quit());
02707       exit(1);
02708    }
02709 
02710    ast_http_init();     /* Start the HTTP server, if needed */
02711 
02712    ast_channels_init();
02713 
02714    if (init_manager()) {
02715       printf(term_quit());
02716       exit(1);
02717    }
02718 
02719    if (ast_cdr_engine_init()) {
02720       printf(term_quit());
02721       exit(1);
02722    }
02723 
02724    if (ast_device_state_engine_init()) {
02725       printf(term_quit());
02726       exit(1);
02727    }
02728 
02729    ast_rtp_init();
02730 
02731    ast_udptl_init();
02732 
02733    if (ast_image_init()) {
02734       printf(term_quit());
02735       exit(1);
02736    }
02737 
02738    if (ast_file_init()) {
02739       printf(term_quit());
02740       exit(1);
02741    }
02742 
02743    if (load_pbx()) {
02744       printf(term_quit());
02745       exit(1);
02746    }
02747 
02748    if (init_framer()) {
02749       printf(term_quit());
02750       exit(1);
02751    }
02752 
02753    if (astdb_init()) {
02754       printf(term_quit());
02755       exit(1);
02756    }
02757 
02758    if (ast_enum_init()) {
02759       printf(term_quit());
02760       exit(1);
02761    }
02762 
02763    if (load_modules(0)) {
02764       printf(term_quit());
02765       exit(1);
02766    }
02767 
02768    dnsmgr_start_refresh();
02769 
02770    /* We might have the option of showing a console, but for now just
02771       do nothing... */
02772    if (ast_opt_console && !option_verbose)
02773       ast_verbose(" ]\n");
02774    if (option_verbose || ast_opt_console)
02775       ast_verbose(term_color(tmp, "Asterisk Ready.\n", COLOR_BRWHITE, COLOR_BLACK, sizeof(tmp)));
02776    if (ast_opt_no_fork)
02777       consolethread = pthread_self();
02778 
02779    ast_set_flag(&ast_options, AST_OPT_FLAG_FULLY_BOOTED);
02780    pthread_sigmask(SIG_UNBLOCK, &sigs, NULL);
02781 
02782 #ifdef __AST_DEBUG_MALLOC
02783    __ast_mm_init();
02784 #endif   
02785 
02786    time(&ast_startuptime);
02787    ast_cli_register_multiple(cli_asterisk, sizeof(cli_asterisk) / sizeof(struct ast_cli_entry));
02788 
02789    if (ast_opt_console) {
02790       /* Console stuff now... */
02791       /* Register our quit function */
02792       char title[256];
02793       set_icon("Asterisk");
02794       snprintf(title, sizeof(title), "Asterisk Console on '%s' (pid %ld)", hostname, (long)ast_mainpid);
02795       set_title(title);
02796 
02797       for (;;) {
02798          buf = (char *)el_gets(el, &num);
02799          if (buf) {
02800             if (buf[strlen(buf)-1] == '\n')
02801                buf[strlen(buf)-1] = '\0';
02802 
02803             consolehandler((char *)buf);
02804          } else if (ast_opt_remote && (write(STDOUT_FILENO, "\nUse EXIT or QUIT to exit the asterisk console\n",
02805                strlen("\nUse EXIT or QUIT to exit the asterisk console\n")) < 0)) {
02806             /* Whoa, stdout disappeared from under us... Make /dev/null's */
02807             int fd;
02808             fd = open("/dev/null", O_RDWR);
02809             if (fd > -1) {
02810                dup2(fd, STDOUT_FILENO);
02811                dup2(fd, STDIN_FILENO);
02812             } else
02813                ast_log(LOG_WARNING, "Failed to open /dev/null to recover from dead console. Bad things will happen!\n");
02814             break;
02815          }
02816          if (need_reload) {
02817             need_reload = 0;
02818             ast_module_reload(NULL);
02819          }
02820       }
02821    }
02822    /* Do nothing */
02823    for (;;) {  /* apparently needed for Mac OS X */
02824       struct pollfd p = { -1 /* no descriptor */, 0, 0 };
02825       poll(&p, 0, -1);
02826       /* SIGHUP will cause this to break out of poll() */
02827       if (need_reload) {
02828          need_reload = 0;
02829          ast_module_reload(NULL);
02830       }
02831    }
02832 
02833    return 0;
02834 }

static void* netconsole void *  vconsole  )  [static]
 

Definition at line 771 of file asterisk.c.

References ast_log(), pollfd::events, pollfd::fd, console::fd, fdprint(), hostname, LOG_WARNING, console::p, poll(), POLLIN, and pollfd::revents.

Referenced by listener().

00772 {
00773    struct console *con = vconsole;
00774    char hostname[MAXHOSTNAMELEN] = "";
00775    char tmp[512];
00776    int res;
00777    struct pollfd fds[2];
00778    
00779    if (gethostname(hostname, sizeof(hostname)-1))
00780       ast_copy_string(hostname, "<Unknown>", sizeof(hostname));
00781    snprintf(tmp, sizeof(tmp), "%s/%ld/%s\n", hostname, (long)ast_mainpid, ASTERISK_VERSION);
00782    fdprint(con->fd, tmp);
00783    for (;;) {
00784       fds[0].fd = con->fd;
00785       fds[0].events = POLLIN;
00786       fds[0].revents = 0;
00787       fds[1].fd = con->p[0];
00788       fds[1].events = POLLIN;
00789       fds[1].revents = 0;
00790 
00791       res = poll(fds, 2, -1);
00792       if (res < 0) {
00793          if (errno != EINTR)
00794             ast_log(LOG_WARNING, "poll returned < 0: %s\n", strerror(errno));
00795          continue;
00796       }
00797       if (fds[0].revents) {
00798          res = read(con->fd, tmp, sizeof(tmp));
00799          if (res < 1) {
00800             break;
00801          }
00802          tmp[res] = 0;
00803          ast_cli_command(con->fd, tmp);
00804       }
00805       if (fds[1].revents) {
00806          res = read(con->p[0], tmp, sizeof(tmp));
00807          if (res < 1) {
00808             ast_log(LOG_ERROR, "read returned %d\n", res);
00809             break;
00810          }
00811          res = write(con->fd, tmp, res);
00812          if (res < 1)
00813             break;
00814       }
00815    }
00816    if (option_verbose > 2) 
00817       ast_verbose(VERBOSE_PREFIX_3 "Remote UNIX connection disconnected\n");
00818    close(con->fd);
00819    close(con->p[0]);
00820    close(con->p[1]);
00821    con->fd = -1;
00822    
00823    return NULL;
00824 }

static void network_verboser const char *  s  )  [static]
 

Definition at line 764 of file asterisk.c.

References ast_network_puts_mutable().

Referenced by ast_makesocket().

00765 {
00766    ast_network_puts_mutable(s);
00767 }

static void null_sig_handler int  signal  )  [static]
 

NULL handler so we can collect the child exit status.

Definition at line 606 of file asterisk.c.

Referenced by ast_replace_sigchld().

00607 {
00608 
00609 }

static void quit_handler int  num,
int  nice,
int  safeshutdown,
int  restart
[static]
 

Definition at line 1104 of file asterisk.c.

References ast_active_channels(), ast_begin_shutdown(), ast_cdr_engine_term(), ast_opt_console, ast_verbose(), and s.

Referenced by __quit_handler(), handle_restart_gracefully(), handle_restart_now(), handle_restart_when_convenient(), handle_shutdown_gracefully(), handle_shutdown_now(), handle_shutdown_when_convenient(), and remoteconsolehandler().

01105 {
01106    char filename[80] = "";
01107    time_t s,e;
01108    int x;
01109    /* Try to get as many CDRs as possible submitted to the backend engines (if in batch mode) */
01110    ast_cdr_engine_term();
01111    if (safeshutdown) {
01112       shuttingdown = 1;
01113       if (!nice) {
01114          /* Begin shutdown routine, hanging up active channels */
01115          ast_begin_shutdown(1);
01116          if (option_verbose && ast_opt_console)
01117             ast_verbose("Beginning asterisk %s....\n", restart ? "restart" : "shutdown");
01118          time(&s);
01119          for (;;) {
01120             time(&e);
01121             /* Wait up to 15 seconds for all channels to go away */
01122             if ((e - s) > 15)
01123                break;
01124             if (!ast_active_channels())
01125                break;
01126             if (!shuttingdown)
01127                break;
01128             /* Sleep 1/10 of a second */
01129             usleep(100000);
01130          }
01131       } else {
01132          if (nice < 2)
01133             ast_begin_shutdown(0);
01134          if (option_verbose && ast_opt_console)
01135             ast_verbose("Waiting for inactivity to perform %s...\n", restart ? "restart" : "halt");
01136          for (;;) {
01137             if (!ast_active_channels())
01138                break;
01139             if (!shuttingdown)
01140                break;
01141             sleep(1);
01142          }
01143       }
01144 
01145       if (!shuttingdown) {
01146          if (option_verbose && ast_opt_console)
01147             ast_verbose("Asterisk %s cancelled.\n", restart ? "restart" : "shutdown");
01148          return;
01149       }
01150    }
01151    if (ast_opt_console || ast_opt_remote) {
01152       if (getenv("HOME")) 
01153          snprintf(filename, sizeof(filename), "%s/.asterisk_history", getenv("HOME"));
01154       if (!ast_strlen_zero(filename))
01155          ast_el_write_history(filename);
01156       if (el != NULL)
01157          el_end(el);
01158       if (el_hist != NULL)
01159          history_end(el_hist);
01160    }
01161    if (option_verbose)
01162       ast_verbose("Executing last minute cleanups\n");
01163    ast_run_atexits();
01164    /* Called on exit */
01165    if (option_verbose && ast_opt_console)
01166       ast_verbose("Asterisk %s ending (%d).\n", ast_active_channels() ? "uncleanly" : "cleanly", num);
01167    if (option_debug)
01168       ast_log(LOG_DEBUG, "Asterisk ending (%d).\n", num);
01169    manager_event(EVENT_FLAG_SYSTEM, "Shutdown", "Shutdown: %s\r\nRestart: %s\r\n", ast_active_channels() ? "Uncleanly" : "Cleanly", restart ? "True" : "False");
01170    if (ast_socket > -1) {
01171       pthread_cancel(lthread);
01172       close(ast_socket);
01173       ast_socket = -1;
01174       unlink(ast_config_AST_SOCKET);
01175    }
01176    if (ast_consock > -1)
01177       close(ast_consock);
01178    if (!ast_opt_remote)
01179       unlink(ast_config_AST_PID);
01180    printf(term_quit());
01181    if (restart) {
01182       if (option_verbose || ast_opt_console)
01183          ast_verbose("Preparing for Asterisk restart...\n");
01184       /* Mark all FD's for closing on exec */
01185       for (x=3; x < 32768; x++) {
01186          fcntl(x, F_SETFD, FD_CLOEXEC);
01187       }
01188       if (option_verbose || ast_opt_console)
01189          ast_verbose("Restarting Asterisk NOW...\n");
01190       restartnow = 1;
01191 
01192       /* close logger */
01193       close_logger();
01194 
01195       /* If there is a consolethread running send it a SIGHUP 
01196          so it can execvp, otherwise we can do it ourselves */
01197       if ((consolethread != AST_PTHREADT_NULL) && (consolethread != pthread_self())) {
01198          pthread_kill(consolethread, SIGHUP);
01199          /* Give the signal handler some time to complete */
01200          sleep(2);
01201       } else
01202          execvp(_argv[0], _argv);
01203    
01204    } else {
01205       /* close logger */
01206       close_logger();
01207    }
01208    exit(0);
01209 }

static __inline uint64_t rdtsc void   )  [static]
 

Definition at line 420 of file asterisk.c.

Referenced by ast_mark().

00421 {
00422    return 0;
00423 }

static int remoteconsolehandler char *  s  )  [static]
 

Definition at line 1276 of file asterisk.c.

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

Referenced by ast_remotecontrol().

01277 {
01278    int ret = 0;
01279 
01280    /* Called when readline data is available */
01281    if (!ast_all_zeros(s))
01282       ast_el_add_history(s);
01283    /* The real handler for bang */
01284    if (s[0] == '!') {
01285       if (s[1])
01286          ast_safe_system(s+1);
01287       else
01288          ast_safe_system(getenv("SHELL") ? getenv("SHELL") : "/bin/sh");
01289       ret = 1;
01290    }
01291    if ((strncasecmp(s, "quit", 4) == 0 || strncasecmp(s, "exit", 4) == 0) &&
01292        (s[4] == '\0' || isspace(s[4]))) {
01293       quit_handler(0, 0, 0, 0);
01294       ret = 1;
01295    }
01296 
01297    return ret;
01298 }

static void set_icon char *  text  )  [static]
 

Definition at line 1047 of file asterisk.c.

01048 {
01049    if (getenv("TERM") && strstr(getenv("TERM"), "xterm"))
01050       fprintf(stdout, "\033]1;%s\007", text);
01051 }

static void set_title char *  text  )  [static]
 

Set an X-term or screen title.

Definition at line 1041 of file asterisk.c.

01042 {
01043    if (getenv("TERM") && strstr(getenv("TERM"), "xterm"))
01044       fprintf(stdout, "\033]2;%s\007", text);
01045 }

static void set_ulimit int  value  )  [static]
 

Set maximum open files.

Definition at line 1018 of file asterisk.c.

References ast_log(), LOG_NOTICE, and LOG_WARNING.

01019 {
01020    struct rlimit l = {0, 0};
01021    
01022    if (value <= 0) {
01023       ast_log(LOG_WARNING, "Unable to change max files open to invalid value %i\n",value);
01024       return;
01025    }
01026    
01027    l.rlim_cur = value;
01028    l.rlim_max = value;
01029    
01030    if (setrlimit(RLIMIT_NOFILE, &l)) {
01031       ast_log(LOG_WARNING, "Unable to disable core size resource limit: %s\n",strerror(errno));
01032       return;
01033    }
01034    
01035    ast_log(LOG_NOTICE, "Setting max files open to %d\n",value);
01036    
01037    return;
01038 }

static int show_cli_help void   )  [static]
 

Definition at line 2151 of file asterisk.c.

02151                                {
02152    printf("Asterisk " ASTERISK_VERSION ", Copyright (C) 1999 - 2006, Digium, Inc. and others.\n");
02153    printf("Usage: asterisk [OPTIONS]\n");
02154    printf("Valid Options:\n");
02155    printf("   -V              Display version number and exit\n");
02156    printf("   -C <configfile> Use an alternate configuration file\n");
02157    printf("   -G <group>      Run as a group other than the caller\n");
02158    printf("   -U <user>       Run as a user other than the caller\n");
02159    printf("   -c              Provide console CLI\n");
02160    printf("   -d              Enable extra debugging\n");
02161 #if HAVE_WORKING_FORK
02162    printf("   -f              Do not fork\n");
02163    printf("   -F              Always fork\n");
02164 #endif
02165    printf("   -g              Dump core in case of a crash\n");
02166    printf("   -h              This help screen\n");
02167    printf("   -i              Initialize crypto keys at startup\n");
02168    printf("   -I              Enable internal timing if Zaptel timer is available\n");
02169    printf("   -L <load>       Limit the maximum load average before rejecting new calls\n");
02170    printf("   -M <value>      Limit the maximum number of calls to the specified value\n");
02171    printf("   -m              Mute the console from debugging and verbose output\n");
02172    printf("   -n              Disable console colorization\n");
02173    printf("   -p              Run as pseudo-realtime thread\n");
02174    printf("   -q              Quiet mode (suppress output)\n");
02175    printf("   -r              Connect to Asterisk on this machine\n");
02176    printf("   -R              Connect to Asterisk, and attempt to reconnect if disconnected\n");
02177    printf("   -t              Record soundfiles in /var/tmp and move them where they belong after they are done.\n");
02178    printf("   -T              Display the time in [Mmm dd hh:mm:ss] format for each line of output to the CLI.\n");
02179    printf("   -v              Increase verbosity (multiple v's = more verbose)\n");
02180    printf("   -x <cmd>        Execute command <cmd> (only valid with -r)\n");
02181    printf("\n");
02182    return 0;
02183 }

static int show_license int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1485 of file asterisk.c.

References ast_cli(), and RESULT_SUCCESS.

01486 {
01487    int x;
01488 
01489    for (x = 0; x < sizeof(license_lines) / sizeof(license_lines[0]); x++)
01490       ast_cli(fd, (char *) license_lines[x]);
01491 
01492    return RESULT_SUCCESS;
01493 }

static int show_version void   )  [static]
 

Definition at line 2145 of file asterisk.c.

02146 {
02147    printf("Asterisk " ASTERISK_VERSION "\n");
02148    return 0;
02149 }

static int show_warranty int  fd,
int  argc,
char *  argv[]
[static]
 

Definition at line 1456 of file asterisk.c.

References ast_cli(), and RESULT_SUCCESS.

01457 {
01458    int x;
01459 
01460    for (x = 0; x < sizeof(warranty_lines) / sizeof(warranty_lines[0]); x++)
01461       ast_cli(fd, (char *) warranty_lines[x]);
01462 
01463    return RESULT_SUCCESS;
01464 }

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 986 of file asterisk.c.

00987 {
00988    signal(num, urg_handler);
00989    return;
00990 }


Variable Documentation

char* _argv[256] [static]
 

Definition at line 230 of file asterisk.c.

const char abort_halt_help[] [static]
 

Initial value:

 
"Usage: abort shutdown\n"
"       Causes Asterisk to abort an executing shutdown or restart, and resume normal\n"
"       call operations.\n"

Definition at line 1300 of file asterisk.c.

const char* ast_build_date
 

Definition at line 32 of file buildinfo.c.

const char* ast_build_hostname
 

Definition at line 28 of file buildinfo.c.

const char* ast_build_kernel
 

Definition at line 29 of file buildinfo.c.

const char* ast_build_machine
 

Definition at line 30 of file buildinfo.c.

const char* ast_build_os
 

Definition at line 31 of file buildinfo.c.

const char* ast_build_user
 

Definition at line 33 of file buildinfo.c.

char ast_config_AST_AGI_DIR[PATH_MAX]
 

Definition at line 209 of file asterisk.c.

Referenced by launch_script().

char ast_config_AST_CONFIG_DIR[PATH_MAX]
 

Definition at line 201 of file asterisk.c.

Referenced by config_text_file_load(), config_text_file_save(), handle_save_dialplan(), launch_script(), and pbx_load_module().

char ast_config_AST_CONFIG_FILE[PATH_MAX]
 

Definition at line 202 of file asterisk.c.

Referenced by launch_script().

char ast_config_AST_CTL[PATH_MAX] = "asterisk.ctl"
 

Definition at line 220 of file asterisk.c.

char ast_config_AST_CTL_GROUP[PATH_MAX] = "\0"
 

Definition at line 219 of file asterisk.c.

char ast_config_AST_CTL_OWNER[PATH_MAX] = "\0"
 

Definition at line 218 of file asterisk.c.

char ast_config_AST_CTL_PERMISSIONS[PATH_MAX]
 

Definition at line 217 of file asterisk.c.

char ast_config_AST_DATA_DIR[PATH_MAX]
 

Definition at line 207 of file asterisk.c.

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

char ast_config_AST_DB[PATH_MAX]
 

Definition at line 210 of file asterisk.c.

Referenced by dbinit().

char ast_config_AST_KEY_DIR[PATH_MAX]
 

Definition at line 211 of file asterisk.c.

Referenced by crypto_load(), init_keys(), and launch_script().

char ast_config_AST_LOG_DIR[PATH_MAX]
 

Definition at line 208 of file asterisk.c.

Referenced by init_logger(), launch_script(), make_logchannel(), and reload_logger().

char ast_config_AST_MODULE_DIR[PATH_MAX]
 

Definition at line 203 of file asterisk.c.

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

char ast_config_AST_MONITOR_DIR[PATH_MAX]
 

Definition at line 205 of file asterisk.c.

Referenced by ast_monitor_change_fname(), ast_monitor_start(), ast_monitor_stop(), and launch_script().

char ast_config_AST_PID[PATH_MAX]
 

Definition at line 212 of file asterisk.c.

char ast_config_AST_RUN_DIR[PATH_MAX]
 

Definition at line 214 of file asterisk.c.

Referenced by launch_script().

char ast_config_AST_RUN_GROUP[PATH_MAX]
 

Definition at line 216 of file asterisk.c.

char ast_config_AST_RUN_USER[PATH_MAX]
 

Definition at line 215 of file asterisk.c.

char ast_config_AST_SOCKET[PATH_MAX]
 

Definition at line 213 of file asterisk.c.

char ast_config_AST_SPOOL_DIR[PATH_MAX]
 

Definition at line 204 of file asterisk.c.

Referenced by launch_script(), and load_module().

char ast_config_AST_SYSTEM_NAME[20] = ""
 

Definition at line 221 of file asterisk.c.

Referenced by pbx_retrieve_variable(), realtime_update_peer(), reload_config(), and reset_global_settings().

char ast_config_AST_VAR_DIR[PATH_MAX]
 

Definition at line 206 of file asterisk.c.

Referenced by ael2_semantic_check(), and launch_script().

int ast_consock = -1 [static]
 

UNIX Socket for controlling another asterisk

Definition at line 170 of file asterisk.c.

time_t ast_lastreloadtime
 

Definition at line 187 of file asterisk.c.

Referenced by handle_showuptime().

pid_t ast_mainpid
 

Definition at line 171 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 169 of file asterisk.c.

time_t ast_startuptime
 

Definition at line 186 of file asterisk.c.

Referenced by handle_showuptime().

const char bang_help[] [static]
 

Initial value:

"Usage: !<command>\n"
"       Executes a given shell command\n"

Definition at line 1332 of file asterisk.c.

struct ast_cli_entry cli_asterisk[] [static]
 

Definition at line 1499 of file asterisk.c.

struct console consoles[AST_MAX_CONNECTS]
 

Definition at line 193 of file asterisk.c.

Referenced by 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 233 of file asterisk.c.

Referenced by show_console().

char debug_filename[AST_FILENAME_MAX] = ""
 

Definition at line 167 of file asterisk.c.

Referenced by ast_log().

char defaultlanguage[MAX_LANGUAGE] = DEFAULT_LANGUAGE
 

Definition at line 195 of file asterisk.c.

EditLine* el [static]
 

Definition at line 190 of file asterisk.c.

Referenced by __ast_context_destroy(), ast_add_extension2(), handle_save_dialplan(), and show_dialplan_helper().

History* el_hist [static]
 

Definition at line 189 of file asterisk.c.

const char* license_lines[] [static]
 

Definition at line 1466 of file asterisk.c.

pthread_t lthread [static]
 

Definition at line 769 of file asterisk.c.

unsigned int need_reload [static]
 

Definition at line 237 of file asterisk.c.

struct profile_data* prof_data [static]
 

Definition at line 359 of file asterisk.c.

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

char randompool[256] [static]
 

Definition at line 235 of file asterisk.c.

char record_cache_dir[AST_CACHE_DIR_LEN] = AST_TMP_DIR
 

Definition at line 166 of file asterisk.c.

Referenced by ast_writefile().

char* remotehostname [static]
 

Definition at line 191 of file asterisk.c.

const char restart_gracefully_help[] [static]
 

Initial value:

 
"Usage: restart gracefully\n"
"       Causes Asterisk to stop accepting new calls and exec() itself performing a cold\n"
"       restart when all active calls have ended.\n"

Definition at line 1323 of file asterisk.c.

const char restart_now_help[] [static]
 

Initial value:

 
"Usage: restart now\n"
"       Causes Asterisk to hangup all calls and exec() itself performing a cold\n"
"       restart.\n"

Definition at line 1318 of file asterisk.c.

const char restart_when_convenient_help[] [static]
 

Initial value:

 
"Usage: restart when convenient\n"
"       Causes Asterisk to perform a cold restart when all active calls have ended.\n"

Definition at line 1328 of file asterisk.c.

int restartnow [static]
 

Definition at line 232 of file asterisk.c.

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 614 of file asterisk.c.

void* safe_system_prev_handler [static]
 

Definition at line 615 of file asterisk.c.

const char show_license_help[] [static]
 

Initial value:

"Usage: core show license\n"
"  Shows the license(s) for this copy of Asterisk.\n"

Definition at line 1340 of file asterisk.c.

const char show_threads_help[] [static]
 

Initial value:

"Usage: core show threads\n"
"       List threads currently active in the system.\n"

Definition at line 294 of file asterisk.c.

const char show_version_files_help[] [static]
 

Initial value:

 
"Usage: core show file version [like <pattern>]\n"
"       Lists the revision numbers of the files used to build this copy of Asterisk.\n"
"       Optional regular expression pattern is used to filter the file list.\n"

Definition at line 488 of file asterisk.c.

const char show_warranty_help[] [static]
 

Initial value:

"Usage: core show warranty\n"
"  Shows the warranty (if any) for this copy of Asterisk.\n"

Definition at line 1336 of file asterisk.c.

const char shutdown_gracefully_help[] [static]
 

Initial value:

 
"Usage: stop gracefully\n"
"       Causes Asterisk to not accept new calls, and exit when all\n"
"       active calls have terminated normally.\n"

Definition at line 1309 of file asterisk.c.

const char shutdown_now_help[] [static]
 

Initial value:

 
"Usage: stop now\n"
"       Shuts down a running Asterisk immediately, hanging up all active calls .\n"

Definition at line 1305 of file asterisk.c.

const char shutdown_when_convenient_help[] [static]
 

Initial value:

 
"Usage: stop when convenient\n"
"       Causes Asterisk to perform a shutdown when all active calls have ended.\n"

Definition at line 1314 of file asterisk.c.

int shuttingdown [static]
 

Definition at line 231 of file asterisk.c.

const char version_help[] [static]
 

Initial value:

"Usage: core show version\n"
"       Shows Asterisk version information.\n"

Definition at line 1344 of file asterisk.c.

const char* warranty_lines[] [static]