Comedian Mail - Voicemail System. More...
#include "asterisk.h"#include "asterisk/paths.h"#include <sys/time.h>#include <sys/stat.h>#include <sys/mman.h>#include <time.h>#include <dirent.h>#include "asterisk/logger.h"#include "asterisk/lock.h"#include "asterisk/file.h"#include "asterisk/channel.h"#include "asterisk/pbx.h"#include "asterisk/config.h"#include "asterisk/say.h"#include "asterisk/module.h"#include "asterisk/adsi.h"#include "asterisk/app.h"#include "asterisk/manager.h"#include "asterisk/dsp.h"#include "asterisk/localtime.h"#include "asterisk/cli.h"#include "asterisk/utils.h"#include "asterisk/stringfields.h"#include "asterisk/smdi.h"#include "asterisk/event.h"#include "asterisk/taskprocessor.h"
Go to the source code of this file.
Data Structures | |
| struct | ast_vm_user |
| struct | baseio |
| struct | leave_vm_options |
| Options for leaving voicemail with the voicemail() application. More... | |
| struct | mwi_sub |
| An MWI subscription. More... | |
| struct | mwi_sub_task |
| struct | mwi_subs |
| struct | users |
| struct | vm_state |
| struct | vm_zone |
| struct | zones |
Defines | |
| #define | ASTERISK_USERNAME "asterisk" |
| #define | BASELINELEN 72 |
| #define | BASEMAXINLINE 256 |
| #define | CHUNKSIZE 65536 |
| #define | COMMAND_TIMEOUT 5000 |
| #define | COPY(a, b, c, d, e, f, g, h) (copy_plain_file(g,h)); |
| #define | DEFAULT_LISTEN_CONTROL_FORWARD_KEY "#" |
| #define | DEFAULT_LISTEN_CONTROL_PAUSE_KEY "0" |
| #define | DEFAULT_LISTEN_CONTROL_RESTART_KEY "2" |
| #define | DEFAULT_LISTEN_CONTROL_REVERSE_KEY "*" |
| #define | DEFAULT_LISTEN_CONTROL_STOP_KEY "13456789" |
| #define | DEFAULT_POLL_FREQ 30 |
| #define | DELETE(a, b, c, d) (vm_delete(c)) |
| #define | DISPOSE(a, b) |
| #define | ENDL "\n" |
| #define | eol "\r\n" |
| #define | ERROR_LOCK_PATH -100 |
| #define | EXISTS(a, b, c, d) (ast_fileexists(c,NULL,d) > 0) |
| #define | HVSU_OUTPUT_FORMAT "%-10s %-5s %-25s %-10s %6s\n" |
| #define | HVSZ_OUTPUT_FORMAT "%-15s %-20s %-45s\n" |
| #define | INTRO "vm-intro" |
| #define | MAX_DATETIME_FORMAT 512 |
| #define | MAX_NUM_CID_CONTEXTS 10 |
| #define | MAXMSG 100 |
| #define | MAXMSGLIMIT 9999 |
| #define | MINPASSWORD 0 |
| #define | PWDCHANGE_EXTERNAL (1 << 2) |
| #define | PWDCHANGE_INTERNAL (1 << 1) |
| #define | RENAME(a, b, c, d, e, f, g, h) (rename_file(g,h)); |
| #define | RETRIEVE(a, b, c, d) |
| #define | SENDMAIL "/usr/sbin/sendmail -t" |
| #define | SMDI_MWI_WAIT_TIMEOUT 1000 |
| #define | STORE(a, b, c, d, e, f, g, h, i, j) |
| #define | tdesc "Comedian Mail (Voicemail System)" |
| #define | VALID_DTMF "1234567890*#" |
| #define | VM_ALLOCED (1 << 13) |
| #define | VM_ATTACH (1 << 11) |
| #define | VM_DELETE (1 << 12) |
| #define | VM_DIRECFORWARD (1 << 10) |
| #define | VM_ENVELOPE (1 << 4) |
| #define | VM_FORCEGREET (1 << 8) |
| #define | VM_FORCENAME (1 << 7) |
| #define | VM_FWDURGAUTO (1 << 18) |
| #define | VM_MESSAGEWRAP (1 << 17) |
| #define | VM_MOVEHEARD (1 << 16) |
| #define | VM_OPERATOR (1 << 1) |
| #define | VM_PBXSKIP (1 << 9) |
| #define | VM_REVIEW (1 << 0) |
| #define | VM_SAYCID (1 << 2) |
| #define | VM_SAYDURATION (1 << 5) |
| #define | VM_SEARCH (1 << 14) |
| #define | VM_SKIPAFTERCMD (1 << 6) |
| #define | VM_SVMAIL (1 << 3) |
| #define | VM_TEMPGREETWARN (1 << 15) |
| #define | VMSTATE_MAX_MSG_ARRAY 256 |
| #define | VOICEMAIL_CONFIG "voicemail.conf" |
| #define | VOICEMAIL_DIR_MODE 0777 |
| #define | VOICEMAIL_FILE_MODE 0666 |
Enumerations | |
| enum | { NEW_FOLDER, OLD_FOLDER, WORK_FOLDER, FAMILY_FOLDER, FRIENDS_FOLDER, GREETINGS_FOLDER } |
| enum | { OPT_SILENT = (1 << 0), OPT_BUSY_GREETING = (1 << 1), OPT_UNAVAIL_GREETING = (1 << 2), OPT_RECORDGAIN = (1 << 3), OPT_PREPEND_MAILBOX = (1 << 4), OPT_AUTOPLAY = (1 << 6), OPT_DTMFEXIT = (1 << 7), OPT_MESSAGE_Urgent = (1 << 8), OPT_MESSAGE_PRIORITY = (1 << 9) } |
| enum | { OPT_ARG_RECORDGAIN = 0, OPT_ARG_PLAYFOLDER = 1, OPT_ARG_DTMFEXIT = 2, OPT_ARG_ARRAY_SIZE = 3 } |
Functions | |
| static int | __has_voicemail (const char *context, const char *mailbox, const char *folder, int shortcircuit) |
| static void | __reg_module (void) |
| static void | __unreg_module (void) |
| static int | acf_mailbox_exists (struct ast_channel *chan, const char *cmd, char *args, char *buf, size_t len) |
| static int | add_email_attachment (FILE *p, struct ast_vm_user *vmu, char *format, char *attach, char *greeting_attachment, char *mailbox, char *bound, char *filename, int last, int msgnum) |
| static void | adsi_begin (struct ast_channel *chan, int *useadsi) |
| static void | adsi_delete (struct ast_channel *chan, struct vm_state *vms) |
| static void | adsi_folders (struct ast_channel *chan, int start, char *label) |
| static void | adsi_goodbye (struct ast_channel *chan) |
| static int | adsi_load_vmail (struct ast_channel *chan, int *useadsi) |
| static void | adsi_login (struct ast_channel *chan) |
| static int | adsi_logo (unsigned char *buf) |
| static void | adsi_message (struct ast_channel *chan, struct vm_state *vms) |
| static void | adsi_password (struct ast_channel *chan) |
| static void | adsi_status (struct ast_channel *chan, struct vm_state *vms) |
| static void | adsi_status2 (struct ast_channel *chan, struct vm_state *vms) |
| static int | advanced_options (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, int msg, int option, signed char record_gain) |
| The advanced options within a message. | |
| static int | append_mailbox (const char *context, const char *box, const char *data) |
| static void | apply_option (struct ast_vm_user *vmu, const char *var, const char *value) |
| Sets a a specific property value. | |
| static void | apply_options (struct ast_vm_user *vmu, const char *options) |
| Destructively Parse options and apply. | |
| static void | apply_options_full (struct ast_vm_user *retval, struct ast_variable *var) |
| Loads the options specific to a voicemail user. | |
| static int | base_encode (char *filename, FILE *so) |
| Performs a base 64 encode algorithm on the contents of a File. | |
| static int | change_password_realtime (struct ast_vm_user *vmu, const char *password) |
| Performs a change of the voicemail passowrd in the realtime engine. | |
| static int | check_mime (const char *str) |
| Check if the string would need encoding within the MIME standard, to avoid confusing certain mail software that expects messages to be 7-bit clean. | |
| static int | check_password (struct ast_vm_user *vmu, char *password) |
| Check that password meets minimum required length. | |
| static int | close_mailbox (struct vm_state *vms, struct ast_vm_user *vmu) |
| static char * | complete_voicemail_show_users (const char *line, const char *word, int pos, int state) |
| static int | copy (char *infile, char *outfile) |
| Utility function to copy a file. | |
| static int | copy_message (struct ast_channel *chan, struct ast_vm_user *vmu, int imbox, int msgnum, long duration, struct ast_vm_user *recip, char *fmt, char *dir, const char *flag) |
| Copies a message from one mailbox to another. | |
| static void | copy_plain_file (char *frompath, char *topath) |
| Copies a voicemail information (envelope) file. | |
| static int | count_messages (struct ast_vm_user *vmu, char *dir) |
| Find all .txt files - even if they are not in sequence from 0000. | |
| static int | create_dirpath (char *dest, int len, const char *context, const char *ext, const char *folder) |
| basically mkdir -p $dest/$context/$ext/$folder | |
| static int | dialout (struct ast_channel *chan, struct ast_vm_user *vmu, char *num, char *outgoing_context) |
| static char * | encode_mime_str (const char *start, char *end, size_t endsize, size_t preamble, size_t postamble) |
| Encode a string according to the MIME rules for encoding strings that are not 7-bit clean or contain control characters. | |
| static struct ast_vm_user * | find_or_create (const char *context, const char *box) |
| static struct ast_vm_user * | find_user (struct ast_vm_user *ivm, const char *context, const char *mailbox) |
| Finds a voicemail user from the users file or the realtime engine. | |
| static struct ast_vm_user * | find_user_realtime (struct ast_vm_user *ivm, const char *context, const char *mailbox) |
| Finds a voicemail user from the realtime engine. | |
| static int | forward_message (struct ast_channel *chan, char *context, struct vm_state *vms, struct ast_vm_user *sender, char *fmt, int is_new_message, signed char record_gain, int urgent) |
| Sends a voicemail message to a mailbox recipient. | |
| static void | free_user (struct ast_vm_user *vmu) |
| static void | free_vm_users (void) |
| Free the users structure. | |
| static void | free_vm_zones (void) |
| Free the zones structure. | |
| static void | free_zone (struct vm_zone *z) |
| static int | get_date (char *s, int len) |
| Gets the current date and time, as formatted string. | |
| static int | get_folder (struct ast_channel *chan, int start) |
| get_folder: Folder menu Plays "press 1 for INBOX messages" etc. Should possibly be internationalized | |
| static int | get_folder2 (struct ast_channel *chan, char *fn, int start) |
| plays a prompt and waits for a keypress. | |
| static int | handle_subscribe (void *datap) |
| static int | handle_unsubscribe (void *datap) |
| static char * | handle_voicemail_reload (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a) |
| Reload voicemail configuration from the CLI. | |
| static char * | handle_voicemail_show_users (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a) |
| Show a list of voicemail users in the CLI. | |
| static char * | handle_voicemail_show_zones (struct ast_cli_entry *e, int cmd, struct ast_cli_args *a) |
| Show a list of voicemail zones in the CLI. | |
| static int | has_voicemail (const char *mailbox, const char *folder) |
| Determines if the given folder has messages. | |
| static int | inboxcount (const char *mailbox, int *newmsgs, int *oldmsgs) |
| static int | inboxcount2 (const char *mailbox, int *urgentmsgs, int *newmsgs, int *oldmsgs) |
| static int | inbuf (struct baseio *bio, FILE *fi) |
| utility used by inchar(), for base_encode() | |
| static int | inchar (struct baseio *bio, FILE *fi) |
| utility used by base_encode() | |
| static int | invent_message (struct ast_channel *chan, char *context, char *ext, int busy, char *ecodes) |
| static int | is_valid_dtmf (const char *key) |
| Determines if a DTMF key entered is valid. | |
| static int | last_message_index (struct ast_vm_user *vmu, char *dir) |
| Determines the highest message number in use for a given user and mailbox folder. | |
| static int | leave_voicemail (struct ast_channel *chan, char *ext, struct leave_vm_options *options) |
| Prompts the user and records a voicemail to a mailbox. | |
| static int | load_config (int reload) |
| static int | load_module (void) |
| static int | make_dir (char *dest, int len, const char *context, const char *ext, const char *folder) |
| Creates a file system path expression for a folder within the voicemail data folder and the appropriate context. | |
| static void | make_email_file (FILE *p, char *srcemail, struct ast_vm_user *vmu, int msgnum, char *context, char *mailbox, const char *fromfolder, char *cidnum, char *cidname, char *attach, char *attach2, char *format, int duration, int attach_user_voicemail, struct ast_channel *chan, const char *category, int imap, const char *flag) |
| Creates the email file to be sent to indicate a new voicemail exists for a user. | |
| static int | make_file (char *dest, const int len, const char *dir, const int num) |
| Creates a file system path expression for a folder within the voicemail data folder and the appropriate context. | |
| static int | manager_list_voicemail_users (struct mansession *s, const struct message *m) |
| Manager list voicemail users command. | |
| static void * | mb_poll_thread (void *data) |
| static const char * | mbox (int id) |
| static int | messagecount (const char *context, const char *mailbox, const char *folder) |
| static void | mwi_sub_destroy (struct mwi_sub *mwi_sub) |
| static void | mwi_sub_event_cb (const struct ast_event *event, void *userdata) |
| static void | mwi_unsub_event_cb (const struct ast_event *event, void *userdata) |
| static int | notify_new_message (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, int msgnum, long duration, char *fmt, char *cidnum, char *cidname, const char *flag) |
| Sends email notification that a user has a new voicemail waiting for them. | |
| static int | ochar (struct baseio *bio, int c, FILE *so) |
| utility used by base_encode() | |
| static int | open_mailbox (struct vm_state *vms, struct ast_vm_user *vmu, int box) |
| static int | play_message (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms) |
| static int | play_message_callerid (struct ast_channel *chan, struct vm_state *vms, char *cid, const char *context, int callback) |
| static int | play_message_category (struct ast_channel *chan, const char *category) |
| static int | play_message_datetime (struct ast_channel *chan, struct ast_vm_user *vmu, const char *origtime, const char *filename) |
| static int | play_message_duration (struct ast_channel *chan, struct vm_state *vms, const char *duration, int minduration) |
| static int | play_record_review (struct ast_channel *chan, char *playfile, char *recordfile, int maxtime, char *fmt, int outsidecaller, struct ast_vm_user *vmu, int *duration, const char *unlockdir, signed char record_gain, struct vm_state *vms, char *flag) |
| static void | poll_subscribed_mailboxes (void) |
| static void | populate_defaults (struct ast_vm_user *vmu) |
| Sets default voicemail system options to a voicemail user. | |
| static void | prep_email_sub_vars (struct ast_channel *ast, struct ast_vm_user *vmu, int msgnum, char *context, char *mailbox, const char *fromfolder, char *cidnum, char *cidname, char *dur, char *date, char *passdata, size_t passdatasize, const char *category, const char *flag) |
| static void | queue_mwi_event (const char *box, int urgent, int new, int old) |
| static char * | quote (const char *from, char *to, size_t len) |
| Wraps a character sequence in double quotes, escaping occurences of quotes within the string. | |
| static int | reload (void) |
| static void | rename_file (char *sfn, char *dfn) |
| Renames a message in a mailbox folder. | |
| static int | reset_user_pw (const char *context, const char *mailbox, const char *newpass) |
| Resets a user password to a specified password. | |
| static void | run_externnotify (char *context, char *extension, const char *flag) |
| static int | save_to_folder (struct ast_vm_user *vmu, struct vm_state *vms, int msg, int box) |
| static int | say_and_wait (struct ast_channel *chan, int num, const char *language) |
| static int | sayname (struct ast_channel *chan, const char *mailbox, const char *context) |
| static int | sendmail (char *srcemail, struct ast_vm_user *vmu, int msgnum, char *context, char *mailbox, const char *fromfolder, char *cidnum, char *cidname, char *attach, char *attach2, char *format, int duration, int attach_user_voicemail, struct ast_channel *chan, const char *category, const char *flag) |
| static int | sendpage (char *srcemail, char *pager, int msgnum, char *context, char *mailbox, const char *fromfolder, char *cidnum, char *cidname, int duration, struct ast_vm_user *vmu, const char *category, const char *flag) |
| static char * | show_users_realtime (int fd, const char *context) |
| static void | start_poll_thread (void) |
| static void | stop_poll_thread (void) |
| static char * | strip_control (const char *input, char *buf, size_t buflen) |
| static char * | substitute_escapes (const char *value) |
| static int | unload_module (void) |
| static int | vm_authenticate (struct ast_channel *chan, char *mailbox, int mailbox_size, struct ast_vm_user *res_vmu, const char *context, const char *prefix, int skipuser, int max_logins, int silent) |
| static int | vm_box_exists (struct ast_channel *chan, void *data) |
| static int | vm_browse_messages (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Top level method to invoke the language variant vm_browse_messages_XX function. | |
| static int | vm_browse_messages_en (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Default English syntax for 'You have N messages' greeting. | |
| static int | vm_browse_messages_es (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Spanish syntax for 'You have N messages' greeting. | |
| static int | vm_browse_messages_gr (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Greek syntax for 'You have N messages' greeting. | |
| static int | vm_browse_messages_he (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| static int | vm_browse_messages_it (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Italian syntax for 'You have N messages' greeting. | |
| static int | vm_browse_messages_pt (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Portuguese syntax for 'You have N messages' greeting. | |
| static int | vm_browse_messages_zh (struct ast_channel *chan, struct vm_state *vms, struct ast_vm_user *vmu) |
| Chinese (Taiwan)syntax for 'You have N messages' greeting. | |
| static void | vm_change_password (struct ast_vm_user *vmu, const char *newpassword) |
| The handler for the change password option. | |
| static void | vm_change_password_shell (struct ast_vm_user *vmu, char *newpassword) |
| static char * | vm_check_password_shell (char *command, char *buf, size_t len) |
| static int | vm_delete (char *file) |
| Removes the voicemail sound and information file. | |
| static int | vm_exec (struct ast_channel *chan, void *data) |
| static int | vm_execmain (struct ast_channel *chan, void *data) |
| static int | vm_forwardoptions (struct ast_channel *chan, struct ast_vm_user *vmu, char *curdir, int curmsg, char *vm_fmts, char *context, signed char record_gain, long *duration, struct vm_state *vms, char *flag) |
| presents the option to prepend to an existing message when forwarding it. | |
| static int | vm_instructions (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, int skipadvanced, int in_urgent) |
| static int | vm_instructions_en (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, int skipadvanced, int in_urgent) |
| static int | vm_instructions_zh (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, int skipadvanced, int in_urgent) |
| static int | vm_intro (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms) |
| static int | vm_intro_cz (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_de (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_en (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_es (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_fr (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_gr (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_he (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_it (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_multilang (struct ast_channel *chan, struct vm_state *vms, const char message_gender[]) |
| static int | vm_intro_nl (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_no (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_pl (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_pt (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_pt_BR (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_se (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_intro_zh (struct ast_channel *chan, struct vm_state *vms) |
| static int | vm_lock_path (const char *path) |
| Lock file path only return failure if ast_lock_path returns 'timeout', not if the path does not exist or any other reason. | |
| static FILE * | vm_mkftemp (char *template) |
| static int | vm_newuser (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, char *fmtc, signed char record_gain) |
| static int | vm_options (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, char *fmtc, signed char record_gain) |
| static int | vm_play_folder_name (struct ast_channel *chan, char *mbox) |
| static int | vm_play_folder_name_gr (struct ast_channel *chan, char *box) |
| static int | vm_play_folder_name_pl (struct ast_channel *chan, char *box) |
| static int | vm_play_folder_name_ua (struct ast_channel *chan, char *box) |
| static int | vm_tempgreeting (struct ast_channel *chan, struct ast_vm_user *vmu, struct vm_state *vms, char *fmtc, signed char record_gain) |
| The handler for 'record a temporary greeting'. | |
| static int | vmauthenticate (struct ast_channel *chan, void *data) |
| static struct ast_tm * | vmu_tm (const struct ast_vm_user *vmu, struct ast_tm *tm) |
| fill in *tm for current time according to the proper timezone, if any. Return tm so it can be used as a function argument. | |
| static int | wait_file (struct ast_channel *chan, struct vm_state *vms, char *file) |
| static int | wait_file2 (struct ast_channel *chan, struct vm_state *vms, char *file) |
Variables | |
| static struct ast_module_info | __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT , .description = "DAHDI Telephony w/PRI & SS7" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "a9c98e5d177805051735cb5b0b16b0a0" , .load = load_module, .unload = unload_module, .reload = reload, } |
| static char * | addesc = "Comedian Mail" |
| static unsigned char | adsifdn [4] = "\x00\x00\x00\x0F" |
| static unsigned char | adsisec [4] = "\x9B\xDB\xF7\xAC" |
| static int | adsiver = 1 |
| static char * | app = "VoiceMail" |
| static char * | app2 = "VoiceMailMain" |
| static char * | app3 = "MailboxExists" |
| static char * | app4 = "VMAuthenticate" |
| static struct ast_module_info * | ast_module_info = &__mod_info |
| static char | callcontext [AST_MAX_CONTEXT] = "" |
| static char | charset [32] = "ISO-8859-1" |
| static char | cidinternalcontexts [MAX_NUM_CID_CONTEXTS][64] |
| static struct ast_cli_entry | cli_voicemail [] |
| static char * | descrip_vm |
| static char * | descrip_vm_box_exists |
| static char * | descrip_vmain |
| static char * | descrip_vmauthenticate |
| static char | dialcontext [AST_MAX_CONTEXT] = "" |
| static char * | emailbody = NULL |
| static char | emaildateformat [32] = "%A, %B %d, %Y at %r" |
| static char * | emailsubject = NULL |
| static char | exitcontext [AST_MAX_CONTEXT] = "" |
| static char | ext_pass_check_cmd [128] |
| static char | ext_pass_cmd [128] |
| static char | externnotify [160] |
| static char | fromstring [100] |
| static struct ast_flags | globalflags = {0} |
| static char | listen_control_forward_key [12] |
| static char | listen_control_pause_key [12] |
| static char | listen_control_restart_key [12] |
| static char | listen_control_reverse_key [12] |
| static char | listen_control_stop_key [12] |
| static struct ast_custom_function | mailbox_exists_acf |
| static char | mailcmd [160] |
| static int | maxdeletedmsg |
| static int | maxgreet |
| static int | maxlogins |
| static int | maxmsg |
| static int | maxsilence |
| static int | minpassword |
| static struct ast_event_sub * | mwi_sub_sub |
| static struct ast_taskprocessor * | mwi_subscription_tps |
| static struct ast_event_sub * | mwi_unsub_sub |
| static int | my_umask |
| static char * | pagerbody = NULL |
| static char | pagerfromstring [100] |
| static char * | pagersubject = NULL |
| static ast_cond_t | poll_cond = PTHREAD_COND_INITIALIZER |
| static unsigned int | poll_freq |
| static ast_mutex_t | poll_lock = ((ast_mutex_t) PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP ) |
| static unsigned int | poll_mailboxes |
| static pthread_t | poll_thread = AST_PTHREADT_NULL |
| static unsigned char | poll_thread_run |
| static int | pwdchange = PWDCHANGE_INTERNAL |
| static int | saydurationminfo |
| static char | serveremail [80] |
| static int | silencethreshold = 128 |
| static int | skipms |
| static struct ast_smdi_interface * | smdi_iface = NULL |
| static char * | synopsis_vm = "Leave a Voicemail message" |
| static char * | synopsis_vm_box_exists |
| static char * | synopsis_vmain = "Check Voicemail messages" |
| static char * | synopsis_vmauthenticate = "Authenticate with Voicemail passwords" |
| static char | userscontext [AST_MAX_EXTENSION] = "default" |
| static struct ast_app_option | vm_app_options [128] = { [ 's' ] = { .flag = OPT_SILENT }, [ 'b' ] = { .flag = OPT_BUSY_GREETING }, [ 'u' ] = { .flag = OPT_UNAVAIL_GREETING }, [ 'g' ] = { .flag = OPT_RECORDGAIN , .arg_index = OPT_ARG_RECORDGAIN + 1 }, [ 'd' ] = { .flag = OPT_DTMFEXIT , .arg_index = OPT_ARG_DTMFEXIT + 1 }, [ 'p' ] = { .flag = OPT_PREPEND_MAILBOX }, [ 'a' ] = { .flag = OPT_AUTOPLAY , .arg_index = OPT_ARG_PLAYFOLDER + 1 }, [ 'U' ] = { .flag = OPT_MESSAGE_Urgent }, [ 'P' ] = { .flag = OPT_MESSAGE_PRIORITY }} |
| enum { ... } | vm_box |
| static char | vm_invalid_password [80] = "vm-invalid-password" |
| static char | vm_mismatch [80] = "vm-mismatch" |
| static char | vm_newpassword [80] = "vm-newpassword" |
| enum { ... } | vm_option_args |
| enum { ... } | vm_option_flags |
| static char | vm_passchanged [80] = "vm-passchanged" |
| static char | vm_password [80] = "vm-password" |
| static char | vm_reenterpassword [80] = "vm-reenterpassword" |
| static char | VM_SPOOL_DIR [PATH_MAX] |
| static char | vmfmts [80] |
| static int | vmmaxsecs |
| static int | vmminsecs |
| static double | volgain |
| static char | zonetag [80] |
Comedian Mail - Voicemail System.
Definition in file app_voicemail.c.
| #define ASTERISK_USERNAME "asterisk" |
Definition at line 190 of file app_voicemail.c.
| #define BASELINELEN 72 |
Definition at line 213 of file app_voicemail.c.
Referenced by ochar().
| #define BASEMAXINLINE 256 |
Definition at line 214 of file app_voicemail.c.
Referenced by base_encode(), and inbuf().
| #define CHUNKSIZE 65536 |
Definition at line 187 of file app_voicemail.c.
| #define COMMAND_TIMEOUT 5000 |
Definition at line 183 of file app_voicemail.c.
| #define COPY | ( | a, | |||
| b, | |||||
| c, | |||||
| d, | |||||
| e, | |||||
| f, | |||||
| g, | |||||
| h | ) | (copy_plain_file(g,h)); |
Definition at line 476 of file app_voicemail.c.
Referenced by copy_message(), and save_to_folder().
| #define DEFAULT_LISTEN_CONTROL_FORWARD_KEY "#" |
Definition at line 195 of file app_voicemail.c.
Referenced by load_config().
| #define DEFAULT_LISTEN_CONTROL_PAUSE_KEY "0" |
Definition at line 197 of file app_voicemail.c.
Referenced by load_config().
| #define DEFAULT_LISTEN_CONTROL_RESTART_KEY "2" |
Definition at line 198 of file app_voicemail.c.
Referenced by load_config().
| #define DEFAULT_LISTEN_CONTROL_REVERSE_KEY "*" |
Definition at line 196 of file app_voicemail.c.
Referenced by load_config().
| #define DEFAULT_LISTEN_CONTROL_STOP_KEY "13456789" |
Definition at line 199 of file app_voicemail.c.
Referenced by load_config().
| #define DEFAULT_POLL_FREQ 30 |
By default, poll every 30 seconds
Definition at line 613 of file app_voicemail.c.
Referenced by load_config().
| #define DELETE | ( | a, | |||
| b, | |||||
| c, | |||||
| d | ) | (vm_delete(c)) |
Definition at line 477 of file app_voicemail.c.
Referenced by close_mailbox(), notify_new_message(), play_record_review(), and vm_tempgreeting().
| #define DISPOSE | ( | a, | |||
| b | ) |
Definition at line 472 of file app_voicemail.c.
Referenced by advanced_options(), forward_message(), invent_message(), leave_voicemail(), notify_new_message(), play_message(), play_record_review(), sayname(), vm_intro(), vm_options(), and vm_tempgreeting().
| #define ENDL "\n" |
Referenced by add_email_attachment(), and make_email_file().
| #define eol "\r\n" |
Definition at line 215 of file app_voicemail.c.
Referenced by base_encode(), and ochar().
| #define ERROR_LOCK_PATH -100 |
Definition at line 239 of file app_voicemail.c.
| #define EXISTS | ( | a, | |||
| b, | |||||
| c, | |||||
| d | ) | (ast_fileexists(c,NULL,d) > 0) |
Definition at line 474 of file app_voicemail.c.
Referenced by close_mailbox(), copy_message(), and save_to_folder().
| #define HVSU_OUTPUT_FORMAT "%-10s %-5s %-25s %-10s %6s\n" |
Referenced by handle_voicemail_show_users().
| #define HVSZ_OUTPUT_FORMAT "%-15s %-20s %-45s\n" |
Referenced by handle_voicemail_show_zones().
| #define INTRO "vm-intro" |
Definition at line 206 of file app_voicemail.c.
Referenced by leave_voicemail(), play_record_review(), and vm_forwardoptions().
| #define MAX_DATETIME_FORMAT 512 |
Definition at line 217 of file app_voicemail.c.
| #define MAX_NUM_CID_CONTEXTS 10 |
Definition at line 218 of file app_voicemail.c.
| #define MAXMSG 100 |
Definition at line 208 of file app_voicemail.c.
Referenced by apply_option(), and load_config().
| #define MAXMSGLIMIT 9999 |
Definition at line 209 of file app_voicemail.c.
Referenced by apply_option(), last_message_index(), and load_config().
| #define MINPASSWORD 0 |
Default minimum mailbox password length
Definition at line 211 of file app_voicemail.c.
Referenced by load_config().
| #define PWDCHANGE_EXTERNAL (1 << 2) |
Definition at line 489 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
| #define PWDCHANGE_INTERNAL (1 << 1) |
Definition at line 488 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
| #define RENAME | ( | a, | |||
| b, | |||||
| c, | |||||
| d, | |||||
| e, | |||||
| f, | |||||
| g, | |||||
| h | ) | (rename_file(g,h)); |
Definition at line 475 of file app_voicemail.c.
Referenced by close_mailbox(), leave_voicemail(), and save_to_folder().
| #define RETRIEVE | ( | a, | |||
| b, | |||||
| c, | |||||
| d | ) |
Definition at line 471 of file app_voicemail.c.
Referenced by advanced_options(), forward_message(), invent_message(), leave_voicemail(), notify_new_message(), play_message(), sayname(), vm_intro(), vm_options(), and vm_tempgreeting().
| #define SENDMAIL "/usr/sbin/sendmail -t" |
Definition at line 204 of file app_voicemail.c.
| #define SMDI_MWI_WAIT_TIMEOUT 1000 |
Definition at line 181 of file app_voicemail.c.
Referenced by run_externnotify().
| #define STORE | ( | a, | |||
| b, | |||||
| c, | |||||
| d, | |||||
| e, | |||||
| f, | |||||
| g, | |||||
| h, | |||||
| i, | |||||
| j | ) |
Definition at line 473 of file app_voicemail.c.
Referenced by copy_message(), forward_message(), leave_voicemail(), and play_record_review().
| #define tdesc "Comedian Mail (Voicemail System)" |
Definition at line 498 of file app_voicemail.c.
| #define VALID_DTMF "1234567890*#" |
Definition at line 200 of file app_voicemail.c.
Referenced by is_valid_dtmf().
| #define VM_ALLOCED (1 << 13) |
Structure was malloc'ed, instead of placed in a return (usually static) buffer
Definition at line 233 of file app_voicemail.c.
Referenced by find_user(), find_user_realtime(), free_user(), and free_vm_users().
| #define VM_ATTACH (1 << 11) |
Attach message to voicemail notifications?
Definition at line 231 of file app_voicemail.c.
Referenced by apply_option(), forward_message(), load_config(), manager_list_voicemail_users(), notify_new_message(), and sendmail().
| #define VM_DELETE (1 << 12) |
Delete message after sending notification
Definition at line 232 of file app_voicemail.c.
Referenced by apply_option(), manager_list_voicemail_users(), and notify_new_message().
| #define VM_DIRECFORWARD (1 << 10) |
Permit caller to use the Directory app for selecting to which mailbox to forward a VM
Definition at line 230 of file app_voicemail.c.
Referenced by forward_message(), and load_config().
| #define VM_ENVELOPE (1 << 4) |
Play the envelope information (who-from, time received, etc.)
Definition at line 224 of file app_voicemail.c.
Referenced by apply_option(), load_config(), manager_list_voicemail_users(), and play_message().
| #define VM_FORCEGREET (1 << 8) |
Have new users record their greetings
Definition at line 228 of file app_voicemail.c.
Referenced by apply_option(), load_config(), vm_execmain(), and vm_newuser().
| #define VM_FORCENAME (1 << 7) |
Have new users record their name
Definition at line 227 of file app_voicemail.c.
Referenced by apply_option(), load_config(), vm_execmain(), and vm_newuser().
| #define VM_FWDURGAUTO (1 << 18) |
Autoset of Urgent flag on forwarded Urgent messages set globally
Definition at line 238 of file app_voicemail.c.
Referenced by forward_message(), and load_config().
| #define VM_MESSAGEWRAP (1 << 17) |
Wrap around from the last message to the first, and vice-versa
Definition at line 237 of file app_voicemail.c.
Referenced by apply_option(), load_config(), vm_execmain(), and vm_instructions_en().
| #define VM_MOVEHEARD (1 << 16) |
Move a "heard" message to Old after listening to it
Definition at line 236 of file app_voicemail.c.
Referenced by apply_option(), close_mailbox(), and load_config().
| #define VM_OPERATOR (1 << 1) |
Allow 0 to be pressed to go to 'o' extension
Definition at line 221 of file app_voicemail.c.
Referenced by apply_option(), leave_voicemail(), load_config(), manager_list_voicemail_users(), and play_record_review().
| #define VM_PBXSKIP (1 << 9) |
Skip the [PBX] preamble in the Subject line of emails
Definition at line 229 of file app_voicemail.c.
Referenced by load_config(), and make_email_file().
| #define VM_REVIEW (1 << 0) |
After recording, permit the caller to review the recording before saving
Definition at line 220 of file app_voicemail.c.
Referenced by apply_option(), load_config(), manager_list_voicemail_users(), and play_record_review().
| #define VM_SAYCID (1 << 2) |
Repeat the CallerID info during envelope playback
Definition at line 222 of file app_voicemail.c.
Referenced by apply_option(), load_config(), manager_list_voicemail_users(), and play_message().
| #define VM_SAYDURATION (1 << 5) |
Play the length of the message during envelope playback
Definition at line 225 of file app_voicemail.c.
Referenced by apply_option(), load_config(), and play_message().
| #define VM_SEARCH (1 << 14) |
Search all contexts for a matching mailbox
Definition at line 234 of file app_voicemail.c.
Referenced by find_or_create(), find_user(), find_user_realtime(), and load_config().
| #define VM_SKIPAFTERCMD (1 << 6) |
After deletion, assume caller wants to go to the next message
Definition at line 226 of file app_voicemail.c.
Referenced by load_config(), and vm_execmain().
| #define VM_SVMAIL (1 << 3) |
Allow the user to compose a new VM from within VoicemailMain
Definition at line 223 of file app_voicemail.c.
Referenced by apply_option(), load_config(), and vm_execmain().
| #define VM_TEMPGREETWARN (1 << 15) |
Remind user tempgreeting is set
Definition at line 235 of file app_voicemail.c.
Referenced by apply_option(), load_config(), and vm_intro().
| #define VMSTATE_MAX_MSG_ARRAY 256 |
Definition at line 416 of file app_voicemail.c.
| #define VOICEMAIL_CONFIG "voicemail.conf" |
Definition at line 189 of file app_voicemail.c.
| #define VOICEMAIL_DIR_MODE 0777 |
Definition at line 185 of file app_voicemail.c.
| #define VOICEMAIL_FILE_MODE 0666 |
Definition at line 186 of file app_voicemail.c.
Referenced by add_email_attachment(), copy(), leave_voicemail(), and vm_mkftemp().
| anonymous enum |
Definition at line 242 of file app_voicemail.c.
00242 { 00243 NEW_FOLDER, 00244 OLD_FOLDER, 00245 WORK_FOLDER, 00246 FAMILY_FOLDER, 00247 FRIENDS_FOLDER, 00248 GREETINGS_FOLDER 00249 } vm_box;
| anonymous enum |
| OPT_SILENT | |
| OPT_BUSY_GREETING | |
| OPT_UNAVAIL_GREETING | |
| OPT_RECORDGAIN | |
| OPT_PREPEND_MAILBOX | |
| OPT_AUTOPLAY | |
| OPT_DTMFEXIT | |
| OPT_MESSAGE_Urgent | |
| OPT_MESSAGE_PRIORITY |
Definition at line 251 of file app_voicemail.c.
00251 { 00252 OPT_SILENT = (1 << 0), 00253 OPT_BUSY_GREETING = (1 << 1), 00254 OPT_UNAVAIL_GREETING = (1 << 2), 00255 OPT_RECORDGAIN = (1 << 3), 00256 OPT_PREPEND_MAILBOX = (1 << 4), 00257 OPT_AUTOPLAY = (1 << 6), 00258 OPT_DTMFEXIT = (1 << 7), 00259 OPT_MESSAGE_Urgent = (1 << 8), 00260 OPT_MESSAGE_PRIORITY = (1 << 9) 00261 } vm_option_flags;
| anonymous enum |
Definition at line 263 of file app_voicemail.c.
00263 { 00264 OPT_ARG_RECORDGAIN = 0, 00265 OPT_ARG_PLAYFOLDER = 1, 00266 OPT_ARG_DTMFEXIT = 2, 00267 /* This *must* be the last value in this enum! */ 00268 OPT_ARG_ARRAY_SIZE = 3, 00269 } vm_option_args;
| static int __has_voicemail | ( | const char * | context, | |
| const char * | mailbox, | |||
| const char * | folder, | |||
| int | shortcircuit | |||
| ) | [static] |
Definition at line 4685 of file app_voicemail.c.
References ast_strlen_zero().
Referenced by has_voicemail(), inboxcount2(), and messagecount().
04686 { 04687 DIR *dir; 04688 struct dirent *de; 04689 char fn[256]; 04690 int ret = 0; 04691 04692 /* If no mailbox, return immediately */ 04693 if (ast_strlen_zero(mailbox)) 04694 return 0; 04695 04696 if (ast_strlen_zero(folder)) 04697 folder = "INBOX"; 04698 if (ast_strlen_zero(context)) 04699 context = "default"; 04700 04701 snprintf(fn, sizeof(fn), "%s%s/%s/%s", VM_SPOOL_DIR, context, mailbox, folder); 04702 04703 if (!(dir = opendir(fn))) 04704 return 0; 04705 04706 while ((de = readdir(dir))) { 04707 if (!strncasecmp(de->d_name, "msg", 3)) { 04708 if (shortcircuit) { 04709 ret = 1; 04710 break; 04711 } else if (!strncasecmp(de->d_name + 8, "txt", 3)) { 04712 if (shortcircuit) return 1; 04713 ret++; 04714 } 04715 } 04716 } 04717 04718 closedir(dir); 04719 04720 /* If we are checking INBOX, we should check Urgent as well */ 04721 if (strcmp(folder, "INBOX") == 0) { 04722 return (ret + __has_voicemail(context, mailbox, "Urgent", shortcircuit)); 04723 } else { 04724 return ret; 04725 } 04726 }
| static void __reg_module | ( | void | ) | [static] |
Definition at line 11488 of file app_voicemail.c.
| static void __unreg_module | ( | void | ) | [static] |
Definition at line 11488 of file app_voicemail.c.
| static int acf_mailbox_exists | ( | struct ast_channel * | chan, | |
| const char * | cmd, | |||
| char * | args, | |||
| char * | buf, | |||
| size_t | len | |||
| ) | [static] |
Definition at line 9659 of file app_voicemail.c.
References AST_APP_ARG, ast_copy_string(), AST_DECLARE_APP_ARGS, ast_log(), AST_NONSTANDARD_APP_ARGS, ast_strlen_zero(), find_user(), LOG_ERROR, and mbox().
09660 { 09661 struct ast_vm_user svm; 09662 AST_DECLARE_APP_ARGS(arg, 09663 AST_APP_ARG(mbox); 09664 AST_APP_ARG(context); 09665 ); 09666 09667 AST_NONSTANDARD_APP_ARGS(arg, args, '@'); 09668 09669 if (ast_strlen_zero(arg.mbox)) { 09670 ast_log(LOG_ERROR, "MAILBOX_EXISTS requires an argument (<mailbox>[@<context>])\n"); 09671 return -1; 09672 } 09673 09674 ast_copy_string(buf, find_user(&svm, ast_strlen_zero(arg.context) ? "default" : arg.context, arg.mbox) ? "1" : "0", len); 09675 return 0; 09676 }
| static int add_email_attachment | ( | FILE * | p, | |
| struct ast_vm_user * | vmu, | |||
| char * | format, | |||
| char * | attach, | |||
| char * | greeting_attachment, | |||
| char * | mailbox, | |||
| char * | bound, | |||
| char * | filename, | |||
| int | last, | |||
| int | msgnum | |||
| ) | [static] |
Definition at line 4184 of file app_voicemail.c.
References ast_debug, ast_log(), ast_safe_system(), base_encode(), ast_vm_user::context, create_dirpath(), ENDL, LOG_WARNING, ast_vm_user::mailbox, VOICEMAIL_FILE_MODE, and ast_vm_user::volgain.
Referenced by make_email_file().
04185 { 04186 char tmpdir[256], newtmp[256]; 04187 char fname[256]; 04188 char tmpcmd[256]; 04189 int tmpfd = -1; 04190 04191 /* Eww. We want formats to tell us their own MIME type */ 04192 char *ctype = (!strcasecmp(format, "ogg")) ? "application/" : "audio/x-"; 04193 04194 if (vmu->volgain < -.001 || vmu->volgain > .001) { 04195 create_dirpath(tmpdir, sizeof(tmpdir), vmu->context, vmu->mailbox, "tmp"); 04196 snprintf(newtmp, sizeof(newtmp), "%s/XXXXXX", tmpdir); 04197 tmpfd = mkstemp(newtmp); 04198 chmod(newtmp, VOICEMAIL_FILE_MODE & ~my_umask); 04199 ast_debug(3, "newtmp: %s\n", newtmp); 04200 if (tmpfd > -1) { 04201 int soxstatus; 04202 snprintf(tmpcmd, sizeof(tmpcmd), "sox -v %.4f %s.%s %s.%s", vmu->volgain, attach, format, newtmp, format); 04203 if ((soxstatus = ast_safe_system(tmpcmd)) == 0) { 04204 attach = newtmp; 04205 ast_debug(3, "VOLGAIN: Stored at: %s.%s - Level: %.4f - Mailbox: %s\n", attach, format, vmu->volgain, mailbox); 04206 } else { 04207 ast_log(LOG_WARNING, "Sox failed to reencode %s.%s: %s (have you installed support for all sox file formats?)\n", attach, format, 04208 soxstatus == 1 ? "Problem with command line options" : "An error occurred during file processing"); 04209 ast_log(LOG_WARNING, "Voicemail attachment will have no volume gain.\n"); 04210 } 04211 } 04212 } 04213 fprintf(p, "--%s" ENDL, bound); 04214 if (msgnum > -1) 04215 fprintf(p, "Content-Type: %s%s; name=\"%s\"" ENDL, ctype, format, filename); 04216 else 04217 fprintf(p, "Content-Type: %s%s; name=\"%s.%s\"" ENDL, ctype, format, attach, format); 04218 fprintf(p, "Content-Transfer-Encoding: base64" ENDL); 04219 fprintf(p, "Content-Description: Voicemail sound attachment." ENDL); 04220 if (msgnum > -1) 04221 fprintf(p, "Content-Disposition: attachment; filename=\"%s\"" ENDL ENDL, filename); 04222 else 04223 fprintf(p, "Content-Disposition: attachment; filename=\"%s.%s\"" ENDL ENDL, attach, format); 04224 snprintf(fname, sizeof(fname), "%s.%s", attach, format); 04225 base_encode(fname, p); 04226 if (last) 04227 fprintf(p, ENDL ENDL "--%s--" ENDL "." ENDL, bound); 04228 if (tmpfd > -1) { 04229 unlink(fname); 04230 close(tmpfd); 04231 unlink(newtmp); 04232 } 04233 return 0; 04234 }
| static void adsi_begin | ( | struct ast_channel * | chan, | |
| int * | useadsi | |||
| ) | [static] |
Definition at line 5606 of file app_voicemail.c.
References adsi_load_vmail(), adsifdn, adsiver, ast_adsi_available, ast_adsi_load_session, ast_log(), and AST_LOG_WARNING.
Referenced by vm_authenticate(), and vm_execmain().
05607 { 05608 int x; 05609 if (!ast_adsi_available(chan)) 05610 return; 05611 x = ast_adsi_load_session(chan, adsifdn, adsiver, 1); 05612 if (x < 0) 05613 return; 05614 if (!x) { 05615 if (adsi_load_vmail(chan, useadsi)) { 05616 ast_log(AST_LOG_WARNING, "Unable to upload voicemail scripts\n"); 05617 return; 05618 } 05619 } else 05620 *useadsi = 1; 05621 }
| static void adsi_delete | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 5795 of file app_voicemail.c.
References ADSI_KEY_APPS, ADSI_KEY_SKT, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_set_keys, ast_adsi_transmit_message, ast_adsi_voice_mode, vm_state::curmsg, vm_state::deleted, and vm_state::lastmsg.
Referenced by vm_execmain().
05796 { 05797 int bytes=0; 05798 unsigned char buf[256]; 05799 unsigned char keys[8]; 05800 05801 int x; 05802 05803 if (!ast_adsi_available(chan)) 05804 return; 05805 05806 /* New meaning for keys */ 05807 for (x=0;x<5;x++) 05808 keys[x] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 6 + x); 05809 05810 keys[6] = 0x0; 05811 keys[7] = 0x0; 05812 05813 if (!vms->curmsg) { 05814 /* No prev key, provide "Folder" instead */ 05815 keys[0] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 1); 05816 } 05817 if (vms->curmsg >= vms->lastmsg) { 05818 /* If last message ... */ 05819 if (vms->curmsg) { 05820 /* but not only message, provide "Folder" instead */ 05821 keys[3] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 1); 05822 } else { 05823 /* Otherwise if only message, leave blank */ 05824 keys[3] = 1; 05825 } 05826 } 05827 05828 /* If deleted, show "undeleted" */ 05829 if (vms->deleted[vms->curmsg]) 05830 keys[1] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 11); 05831 05832 /* Except "Exit" */ 05833 keys[5] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 5); 05834 bytes += ast_adsi_set_keys(buf + bytes, keys); 05835 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05836 05837 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05838 }
| static void adsi_folders | ( | struct ast_channel * | chan, | |
| int | start, | |||
| char * | label | |||
| ) | [static] |
Definition at line 5671 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, ADSI_KEY_APPS, ADSI_KEY_SKT, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, and ast_adsi_voice_mode.
Referenced by vm_execmain().
05672 { 05673 unsigned char buf[256]; 05674 int bytes=0; 05675 unsigned char keys[8]; 05676 int x,y; 05677 05678 if (!ast_adsi_available(chan)) 05679 return; 05680 05681 for (x=0;x<5;x++) { 05682 y = ADSI_KEY_APPS + 12 + start + x; 05683 if (y > ADSI_KEY_APPS + 12 + 4) 05684 y = 0; 05685 keys[x] = ADSI_KEY_SKT | y; 05686 } 05687 keys[5] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 17); 05688 keys[6] = 0; 05689 keys[7] = 0; 05690 05691 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 1, ADSI_JUST_CENT, 0, label, ""); 05692 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 2, ADSI_JUST_CENT, 0, " ", ""); 05693 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05694 bytes += ast_adsi_set_keys(buf + bytes, keys); 05695 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05696 05697 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05698 }
| static void adsi_goodbye | ( | struct ast_channel * | chan | ) | [static] |
Definition at line 5943 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, ADSI_JUST_LEFT, adsi_logo(), ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_line, ast_adsi_transmit_message, and ast_adsi_voice_mode.
Referenced by vm_execmain().
05944 { 05945 unsigned char buf[256]; 05946 int bytes=0; 05947 05948 if (!ast_adsi_available(chan)) 05949 return; 05950 bytes += adsi_logo(buf + bytes); 05951 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_LEFT, 0, " ", ""); 05952 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "Goodbye", ""); 05953 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05954 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05955 05956 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05957 }
| static int adsi_load_vmail | ( | struct ast_channel * | chan, | |
| int * | useadsi | |||
| ) | [static] |
Definition at line 5477 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, ADSI_JUST_LEFT, ADSI_KEY_APPS, adsi_logo(), ADSI_MSG_DISPLAY, ADSI_MSG_DOWNLOAD, adsifdn, adsisec, adsiver, ast_adsi_begin_download, ast_adsi_data_mode, ast_adsi_display, ast_adsi_download_disconnect, ast_adsi_end_download, ast_adsi_load_session, ast_adsi_load_soft_key, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, ast_debug, mbox(), and num.
Referenced by adsi_begin().
05478 { 05479 unsigned char buf[256]; 05480 int bytes=0; 05481 int x; 05482 char num[5]; 05483 05484 *useadsi = 0; 05485 bytes += ast_adsi_data_mode(buf + bytes); 05486 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05487 05488 bytes = 0; 05489 bytes += adsi_logo(buf); 05490 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Downloading Scripts", ""); 05491 #ifdef DISPLAY 05492 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, " .", ""); 05493 #endif 05494 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05495 bytes += ast_adsi_data_mode(buf + bytes); 05496 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05497 05498 if (ast_adsi_begin_download(chan, addesc, adsifdn, adsisec, adsiver)) { 05499 bytes = 0; 05500 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Load Cancelled.", ""); 05501 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "ADSI Unavailable", ""); 05502 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05503 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05504 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05505 return 0; 05506 } 05507 05508 #ifdef DISPLAY 05509 /* Add a dot */ 05510 bytes = 0; 05511 bytes += ast_adsi_logo(buf); 05512 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Downloading Scripts", ""); 05513 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, " ..", ""); 05514 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05515 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05516 #endif 05517 bytes = 0; 05518 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 0, "Listen", "Listen", "1", 1); 05519 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 1, "Folder", "Folder", "2", 1); 05520 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 2, "Advanced", "Advnced", "3", 1); 05521 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 3, "Options", "Options", "0", 1); 05522 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 4, "Help", "Help", "*", 1); 05523 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 5, "Exit", "Exit", "#", 1); 05524 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DOWNLOAD); 05525 05526 #ifdef DISPLAY 05527 /* Add another dot */ 05528 bytes = 0; 05529 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, " ...", ""); 05530 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05531 05532 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05533 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05534 #endif 05535 05536 bytes = 0; 05537 /* These buttons we load but don't use yet */ 05538 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 6, "Previous", "Prev", "4", 1); 05539 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 8, "Repeat", "Repeat", "5", 1); 05540 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 7, "Delete", "Delete", "7", 1); 05541 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 9, "Next", "Next", "6", 1); 05542 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 10, "Save", "Save", "9", 1); 05543 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 11, "Undelete", "Restore", "7", 1); 05544 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DOWNLOAD); 05545 05546 #ifdef DISPLAY 05547 /* Add another dot */ 05548 bytes = 0; 05549 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, " ....", ""); 05550 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05551 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05552 #endif 05553 05554 bytes = 0; 05555 for (x=0;x<5;x++) { 05556 snprintf(num, sizeof(num), "%d", x); 05557 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 12 + x, mbox(x), mbox(x), num, 1); 05558 } 05559 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 12 + 5, "Cancel", "Cancel", "#", 1); 05560 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DOWNLOAD); 05561 05562 #ifdef DISPLAY 05563 /* Add another dot */ 05564 bytes = 0; 05565 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, " .....", ""); 05566 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05567 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05568 #endif 05569 05570 if (ast_adsi_end_download(chan)) { 05571 bytes = 0; 05572 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Download Unsuccessful.", ""); 05573 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "ADSI Unavailable", ""); 05574 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05575 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05576 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05577 return 0; 05578 } 05579 bytes = 0; 05580 bytes += ast_adsi_download_disconnect(buf + bytes); 05581 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05582 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DOWNLOAD); 05583 05584 ast_debug(1, "Done downloading scripts...\n"); 05585 05586 #ifdef DISPLAY 05587 /* Add last dot */ 05588 bytes = 0; 05589 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, " ......", ""); 05590 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05591 #endif 05592 ast_debug(1, "Restarting session...\n"); 05593 05594 bytes = 0; 05595 /* Load the session now */ 05596 if (ast_adsi_load_session(chan, adsifdn, adsiver, 1) == 1) { 05597 *useadsi = 1; 05598 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Scripts Loaded!", ""); 05599 } else 05600 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Load Failed!", ""); 05601 05602 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05603 return 0; 05604 }
| static void adsi_login | ( | struct ast_channel * | chan | ) | [static] |
Definition at line 5623 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_DIR_FROM_LEFT, ADSI_JUST_CENT, ADSI_JUST_LEFT, ADSI_KEY_APPS, adsi_logo(), ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_input_control, ast_adsi_input_format, ast_adsi_load_soft_key, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, and ast_adsi_voice_mode.
Referenced by vm_authenticate().
05624 { 05625 unsigned char buf[256]; 05626 int bytes=0; 05627 unsigned char keys[8]; 05628 int x; 05629 if (!ast_adsi_available(chan)) 05630 return; 05631 05632 for (x=0;x<8;x++) 05633 keys[x] = 0; 05634 /* Set one key for next */ 05635 keys[3] = ADSI_KEY_APPS + 3; 05636 05637 bytes += adsi_logo(buf + bytes); 05638 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, " ", ""); 05639 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, " ", ""); 05640 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05641 bytes += ast_adsi_input_format(buf + bytes, 1, ADSI_DIR_FROM_LEFT, 0, "Mailbox: ******", ""); 05642 bytes += ast_adsi_input_control(buf + bytes, ADSI_COMM_PAGE, 4, 1, 1, ADSI_JUST_LEFT); 05643 bytes += ast_adsi_load_soft_key(buf + bytes, ADSI_KEY_APPS + 3, "Enter", "Enter", "#", 1); 05644 bytes += ast_adsi_set_keys(buf + bytes, keys); 05645 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05646 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05647 }
| static int adsi_logo | ( | unsigned char * | buf | ) | [static] |
Definition at line 5469 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, and ast_adsi_display.
Referenced by adsi_goodbye(), adsi_load_vmail(), adsi_login(), vm_newuser(), vm_options(), and vm_tempgreeting().
05470 { 05471 int bytes = 0; 05472 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 1, ADSI_JUST_CENT, 0, "Comedian Mail", ""); 05473 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 2, ADSI_JUST_CENT, 0, "(C)2002-2006 Digium, Inc.", ""); 05474 return bytes; 05475 }
| static void adsi_message | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 5700 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_LEFT, ADSI_KEY_APPS, ADSI_KEY_SKT, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, ast_callerid_parse(), ast_copy_string(), ast_strlen_zero(), vm_state::curbox, vm_state::curmsg, vm_state::deleted, vm_state::fn, vm_state::lastmsg, num, and strsep().
Referenced by play_message(), and vm_execmain().
05701 { 05702 int bytes=0; 05703 unsigned char buf[256]; 05704 char buf1[256], buf2[256]; 05705 char fn2[PATH_MAX]; 05706 05707 char cid[256]=""; 05708 char *val; 05709 char *name, *num; 05710 char datetime[21]=""; 05711 FILE *f; 05712 05713 unsigned char keys[8]; 05714 05715 int x; 05716 05717 if (!ast_adsi_available(chan)) 05718 return; 05719 05720 /* Retrieve important info */ 05721 snprintf(fn2, sizeof(fn2), "%s.txt", vms->fn); 05722 f = fopen(fn2, "r"); 05723 if (f) { 05724 while (!feof(f)) { 05725 if (!fgets((char *)buf, sizeof(buf), f)) { 05726 continue; 05727 } 05728 if (!feof(f)) { 05729 char *stringp=NULL; 05730 stringp = (char *)buf; 05731 strsep(&stringp, "="); 05732 val = strsep(&stringp, "="); 05733 if (!ast_strlen_zero(val)) { 05734 if (!strcmp((char *)buf, "callerid")) 05735 ast_copy_string(cid, val, sizeof(cid)); 05736 if (!strcmp((char *)buf, "origdate")) 05737 ast_copy_string(datetime, val, sizeof(datetime)); 05738 } 05739 } 05740 } 05741 fclose(f); 05742 } 05743 /* New meaning for keys */ 05744 for (x=0;x<5;x++) 05745 keys[x] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 6 + x); 05746 keys[6] = 0x0; 05747 keys[7] = 0x0; 05748 05749 if (!vms->curmsg) { 05750 /* No prev key, provide "Folder" instead */ 05751 keys[0] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 1); 05752 } 05753 if (vms->curmsg >= vms->lastmsg) { 05754 /* If last message ... */ 05755 if (vms->curmsg) { 05756 /* but not only message, provide "Folder" instead */ 05757 keys[3] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 1); 05758 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05759 05760 } else { 05761 /* Otherwise if only message, leave blank */ 05762 keys[3] = 1; 05763 } 05764 } 05765 05766 if (!ast_strlen_zero(cid)) { 05767 ast_callerid_parse(cid, &name, &num); 05768 if (!name) 05769 name = num; 05770 } else 05771 name = "Unknown Caller"; 05772 05773 /* If deleted, show "undeleted" */ 05774 05775 if (vms->deleted[vms->curmsg]) 05776 keys[1] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 11); 05777 05778 /* Except "Exit" */ 05779 keys[5] = ADSI_KEY_SKT | (ADSI_KEY_APPS + 5); 05780 snprintf(buf1, sizeof(buf1), "%s%s", vms->curbox, 05781 strcasecmp(vms->curbox, "INBOX") ? " Messages" : ""); 05782 snprintf(buf2, sizeof(buf2), "Message %d of %d", vms->curmsg + 1, vms->lastmsg + 1); 05783 05784 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 1, ADSI_JUST_LEFT, 0, buf1, ""); 05785 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 2, ADSI_JUST_LEFT, 0, buf2, ""); 05786 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_LEFT, 0, name, ""); 05787 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_LEFT, 0, datetime, ""); 05788 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05789 bytes += ast_adsi_set_keys(buf + bytes, keys); 05790 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05791 05792 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05793 }
| static void adsi_password | ( | struct ast_channel * | chan | ) | [static] |
Definition at line 5649 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_DIR_FROM_LEFT, ADSI_JUST_LEFT, ADSI_KEY_APPS, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_input_control, ast_adsi_input_format, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, and ast_adsi_voice_mode.
Referenced by vm_authenticate().
05650 { 05651 unsigned char buf[256]; 05652 int bytes=0; 05653 unsigned char keys[8]; 05654 int x; 05655 if (!ast_adsi_available(chan)) 05656 return; 05657 05658 for (x=0;x<8;x++) 05659 keys[x] = 0; 05660 /* Set one key for next */ 05661 keys[3] = ADSI_KEY_APPS + 3; 05662 05663 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05664 bytes += ast_adsi_input_format(buf + bytes, 1, ADSI_DIR_FROM_LEFT, 0, "Password: ******", ""); 05665 bytes += ast_adsi_input_control(buf + bytes, ADSI_COMM_PAGE, 4, 0, 1, ADSI_JUST_LEFT); 05666 bytes += ast_adsi_set_keys(buf + bytes, keys); 05667 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05668 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05669 }
| static void adsi_status | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 5840 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_LEFT, ADSI_KEY_APPS, ADSI_KEY_SKT, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, vm_state::lastmsg, vm_state::newmessages, and vm_state::oldmessages.
Referenced by vm_execmain().
05841 { 05842 unsigned char buf[256] = ""; 05843 char buf1[256] = "", buf2[256] = ""; 05844 int bytes=0; 05845 unsigned char keys[8]; 05846 int x; 05847 05848 char *newm = (vms->newmessages == 1) ? "message" : "messages"; 05849 char *oldm = (vms->oldmessages == 1) ? "message" : "messages"; 05850 if (!ast_adsi_available(chan)) 05851 return; 05852 if (vms->newmessages) { 05853 snprintf(buf1, sizeof(buf1), "You have %d new", vms->newmessages); 05854 if (vms->oldmessages) { 05855 strncat(buf1, " and", sizeof(buf1) - strlen(buf1) - 1); 05856 snprintf(buf2, sizeof(buf2), "%d old %s.", vms->oldmessages, oldm); 05857 } else { 05858 snprintf(buf2, sizeof(buf2), "%s.", newm); 05859 } 05860 } else if (vms->oldmessages) { 05861 snprintf(buf1, sizeof(buf1), "You have %d old", vms->oldmessages); 05862 snprintf(buf2, sizeof(buf2), "%s.", oldm); 05863 } else { 05864 strcpy(buf1, "You have no messages."); 05865 buf2[0] = ' '; 05866 buf2[1] = '\0'; 05867 } 05868 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 1, ADSI_JUST_LEFT, 0, buf1, ""); 05869 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 2, ADSI_JUST_LEFT, 0, buf2, ""); 05870 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05871 05872 for (x=0;x<6;x++) 05873 keys[x] = ADSI_KEY_SKT | (ADSI_KEY_APPS + x); 05874 keys[6] = 0; 05875 keys[7] = 0; 05876 05877 /* Don't let them listen if there are none */ 05878 if (vms->lastmsg < 0) 05879 keys[0] = 1; 05880 bytes += ast_adsi_set_keys(buf + bytes, keys); 05881 05882 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05883 05884 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05885 }
| static void adsi_status2 | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 5887 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_LEFT, ADSI_KEY_APPS, ADSI_KEY_SKT, ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_keys, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, vm_state::curbox, and vm_state::lastmsg.
Referenced by vm_execmain().
05888 { 05889 unsigned char buf[256] = ""; 05890 char buf1[256] = "", buf2[256] = ""; 05891 int bytes=0; 05892 unsigned char keys[8]; 05893 int x; 05894 05895 char *mess = (vms->lastmsg == 0) ? "message" : "messages"; 05896 05897 if (!ast_adsi_available(chan)) 05898 return; 05899 05900 /* Original command keys */ 05901 for (x=0;x<6;x++) 05902 keys[x] = ADSI_KEY_SKT | (ADSI_KEY_APPS + x); 05903 05904 keys[6] = 0; 05905 keys[7] = 0; 05906 05907 if ((vms->lastmsg + 1) < 1) 05908 keys[0] = 0; 05909 05910 snprintf(buf1, sizeof(buf1), "%s%s has", vms->curbox, 05911 strcasecmp(vms->curbox, "INBOX") ? " folder" : ""); 05912 05913 if (vms->lastmsg + 1) 05914 snprintf(buf2, sizeof(buf2), "%d %s.", vms->lastmsg + 1, mess); 05915 else 05916 strcpy(buf2, "no messages."); 05917 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 1, ADSI_JUST_LEFT, 0, buf1, ""); 05918 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 2, ADSI_JUST_LEFT, 0, buf2, ""); 05919 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_LEFT, 0, "", ""); 05920 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 05921 bytes += ast_adsi_set_keys(buf + bytes, keys); 05922 05923 bytes += ast_adsi_voice_mode(buf + bytes, 0); 05924 05925 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 05926 05927 }
| static int advanced_options | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| int | msg, | |||
| int | option, | |||
| signed char | record_gain | |||
| ) | [static] |
The advanced options within a message.
| chan | ||
| vmu | ||
| vms | ||
| msg | ||
| option | ||
| record_gain | Provides handling for the play message envelope, call the person back, or reply to message. |
Definition at line 11062 of file app_voicemail.c.
References ast_callerid_parse(), ast_config_destroy(), ast_config_load, ast_log(), AST_LOG_WARNING, AST_MAX_EXTENSION, ast_play_and_wait(), ast_strdupa, ast_strlen_zero(), ast_variable_retrieve(), ast_verb, ast_waitfordigit(), ast_vm_user::callback, CONFIG_FLAG_NOCACHE, ast_vm_user::context, vm_state::curdir, vm_state::curmsg, ast_vm_user::dialout, dialout(), DISPOSE, find_user(), vm_state::fn, vm_state::heard, leave_voicemail(), ast_vm_user::mailbox, make_file(), num, play_message_callerid(), play_message_datetime(), leave_vm_options::record_gain, RETRIEVE, vm_state::starting, and wait_file().
Referenced by vm_execmain().
11063 { 11064 int res = 0; 11065 char filename[PATH_MAX]; 11066 struct ast_config *msg_cfg = NULL; 11067 const char *origtime, *context; 11068 char *name, *num; 11069 int retries = 0; 11070 char *cid; 11071 struct ast_flags config_flags = { CONFIG_FLAG_NOCACHE, }; 11072 11073 vms->starting = 0; 11074 11075 make_file(vms->fn, sizeof(vms->fn), vms->curdir, msg); 11076 11077 /* Retrieve info from VM attribute file */ 11078 snprintf(filename,sizeof(filename), "%s.txt", vms->fn); 11079 RETRIEVE(vms->curdir, vms->curmsg, vmu->mailbox, vmu->context); 11080 msg_cfg = ast_config_load(filename, config_flags); 11081 DISPOSE(vms->curdir, vms->curmsg); 11082 if (!msg_cfg) { 11083 ast_log(AST_LOG_WARNING, "No message attribute file?!! (%s)\n", filename); 11084 return 0; 11085 } 11086 11087 if (!(origtime = ast_variable_retrieve(msg_cfg, "message", "origtime"))) { 11088 ast_config_destroy(msg_cfg); 11089 return 0; 11090 } 11091 11092 cid = ast_strdupa(ast_variable_retrieve(msg_cfg, "message", "callerid")); 11093 11094 context = ast_variable_retrieve(msg_cfg, "message", "context"); 11095 if (!strncasecmp("macro",context,5)) /* Macro names in contexts are useless for our needs */ 11096 context = ast_variable_retrieve(msg_cfg, "message","macrocontext"); 11097 switch (option) { 11098 case 3: /* Play message envelope */ 11099 if (!res) 11100 res = play_message_datetime(chan, vmu, origtime, filename); 11101 if (!res) 11102 res = play_message_callerid(chan, vms, cid, context, 0); 11103 11104 res = 't'; 11105 break; 11106 11107 case 2: /* Call back */ 11108 11109 if (ast_strlen_zero(cid)) 11110 break; 11111 11112 ast_callerid_parse(cid, &name, &num); 11113 while ((res > -1) && (res != 't')) { 11114 switch (res) { 11115 case '1': 11116 if (num) { 11117 /* Dial the CID number */ 11118 res = dialout(chan, vmu, num, vmu->callback); 11119 if (res) { 11120 ast_config_destroy(msg_cfg); 11121 return 9; 11122 } 11123 } else { 11124 res = '2'; 11125 } 11126 break; 11127 11128 case '2': 11129 /* Want to enter a different number, can only do this if there's a dialout context for this user */ 11130 if (!ast_strlen_zero(vmu->dialout)) { 11131 res = dialout(chan, vmu, NULL, vmu->dialout); 11132 if (res) { 11133 ast_config_destroy(msg_cfg); 11134 return 9; 11135 } 11136 } else { 11137 ast_verb(3, "Caller can not specify callback number - no dialout context available\n"); 11138 res = ast_play_and_wait(chan, "vm-sorry"); 11139 } 11140 ast_config_destroy(msg_cfg); 11141 return res; 11142 case '*': 11143 res = 't'; 11144 break; 11145 case '3': 11146 case '4': 11147 case '5': 11148 case '6': 11149 case '7': 11150 case '8': 11151 case '9': 11152 case '0': 11153 11154 res = ast_play_and_wait(chan, "vm-sorry"); 11155 retries++; 11156 break; 11157 default: 11158 if (num) { 11159 ast_verb(3, "Confirm CID number '%s' is number to use for callback\n", num); 11160 res = ast_play_and_wait(chan, "vm-num-i-have"); 11161 if (!res) 11162 res = play_message_callerid(chan, vms, num, vmu->context, 1); 11163 if (!res) 11164 res = ast_play_and_wait(chan, "vm-tocallnum"); 11165 /* Only prompt for a caller-specified number if there is a dialout context specified */ 11166 if (!ast_strlen_zero(vmu->dialout)) { 11167 if (!res) 11168 res = ast_play_and_wait(chan, "vm-calldiffnum"); 11169 } 11170 } else { 11171 res = ast_play_and_wait(chan, "vm-nonumber"); 11172 if (!ast_strlen_zero(vmu->dialout)) { 11173 if (!res) 11174 res = ast_play_and_wait(chan, "vm-toenternumber"); 11175 } 11176 } 11177 if (!res) 11178 res = ast_play_and_wait(chan, "vm-star-cancel"); 11179 if (!res) 11180 res = ast_waitfordigit(chan, 6000); 11181 if (!res) { 11182 retries++; 11183 if (retries > 3) 11184 res = 't'; 11185 } 11186 break; 11187 11188 } 11189 if (res == 't') 11190 res = 0; 11191 else if (res == '*') 11192 res = -1; 11193 } 11194 break; 11195 11196 case 1: /* Reply */ 11197 /* Send reply directly to sender */ 11198 if (ast_strlen_zero(cid)) 11199 break; 11200 11201 ast_callerid_parse(cid, &name, &num); 11202 if (!num) { 11203 ast_verb(3, "No CID number available, no reply sent\n"); 11204 if (!res) 11205 res = ast_play_and_wait(chan, "vm-nonumber"); 11206 ast_config_destroy(msg_cfg); 11207 return res; 11208 } else { 11209 struct ast_vm_user vmu2; 11210 if (find_user(&vmu2, vmu->context, num)) { 11211 struct leave_vm_options leave_options; 11212 char mailbox[AST_MAX_EXTENSION * 2 + 2]; 11213 snprintf(mailbox, sizeof(mailbox), "%s@%s", num, vmu->context); 11214 11215 ast_verb(3, "Leaving voicemail for '%s' in context '%s'\n", num, vmu->context); 11216 11217 memset(&leave_options, 0, sizeof(leave_options)); 11218 leave_options.record_gain = record_gain; 11219 res = leave_voicemail(chan, mailbox, &leave_options); 11220 if (!res) 11221 res = 't'; 11222 ast_config_destroy(msg_cfg); 11223 return res; 11224 } else { 11225 /* Sender has no mailbox, can't reply */ 11226 ast_verb(3, "No mailbox number '%s' in context '%s', no reply sent\n", num, vmu->context); 11227 ast_play_and_wait(chan, "vm-nobox"); 11228 res = 't'; 11229 ast_config_destroy(msg_cfg); 11230 return res; 11231 } 11232 } 11233 res = 0; 11234 11235 break; 11236 } 11237 11238 #ifndef IMAP_STORAGE 11239 ast_config_destroy(msg_cfg); 11240 11241 if (!res) { 11242 make_file(vms->fn, sizeof(vms->fn), vms->curdir, msg); 11243 vms->heard[msg] = 1; 11244 res = wait_file(chan, vms, vms->fn); 11245 } 11246 #endif 11247 return res; 11248 }
| static int append_mailbox | ( | const char * | context, | |
| const char * | box, | |||
| const char * | data | |||
| ) | [static] |
Definition at line 9579 of file app_voicemail.c.
References apply_options(), ast_copy_string(), ast_strdupa, ast_vm_user::email, find_or_create(), ast_vm_user::fullname, inboxcount2(), ast_vm_user::pager, ast_vm_user::password, populate_defaults(), queue_mwi_event(), s, and strsep().
Referenced by load_config().
09580 { 09581 /* Assumes lock is already held */ 09582 char *tmp; 09583 char *stringp; 09584 char *s; 09585 struct ast_vm_user *vmu; 09586 char *mailbox_full; 09587 int new = 0, old = 0, urgent = 0; 09588 09589 tmp = ast_strdupa(data); 09590 09591 if (!(vmu = find_or_create(context, box))) 09592 return -1; 09593 09594 populate_defaults(vmu); 09595 09596 stringp = tmp; 09597 if ((s = strsep(&stringp, ","))) 09598 ast_copy_string(vmu->password, s, sizeof(vmu->password)); 09599 if (stringp && (s = strsep(&stringp, ","))) 09600 ast_copy_string(vmu->fullname, s, sizeof(vmu->fullname)); 09601 if (stringp && (s = strsep(&stringp, ","))) 09602 ast_copy_string(vmu->email, s, sizeof(vmu->email)); 09603 if (stringp && (s = strsep(&stringp, ","))) 09604 ast_copy_string(vmu->pager, s, sizeof(vmu->pager)); 09605 if (stringp && (s = strsep(&stringp, ","))) 09606 apply_options(vmu, s); 09607 09608 mailbox_full = alloca(strlen(box) + strlen(context) + 1); 09609 strcpy(mailbox_full, box); 09610 strcat(mailbox_full, "@"); 09611 strcat(mailbox_full, context); 09612 09613 inboxcount2(mailbox_full, &urgent, &new, &old); 09614 queue_mwi_event(mailbox_full, urgent, new, old); 09615 09616 return 0; 09617 }
| static void apply_option | ( | struct ast_vm_user * | vmu, | |
| const char * | var, | |||
| const char * | value | |||
| ) | [static] |
Sets a a specific property value.
| vmu | The voicemail user object to work with. | |
| var | The name of the property to be set. | |
| value | The value to be set to the property. |
The property name must be one of the understood properties. See the source for details.
Definition at line 764 of file app_voicemail.c.
References apply_options(), ast_copy_string(), ast_log(), AST_LOG_WARNING, ast_set2_flag, ast_true(), ast_vm_user::attachfmt, ast_vm_user::callback, ast_vm_user::dialout, ast_vm_user::exit, ast_vm_user::language, ast_vm_user::maxdeletedmsg, MAXMSG, ast_vm_user::maxmsg, MAXMSGLIMIT, ast_vm_user::maxsecs, ast_vm_user::saydurationm, ast_vm_user::serveremail, VM_ATTACH, VM_DELETE, VM_ENVELOPE, VM_FORCEGREET, VM_FORCENAME, VM_MESSAGEWRAP, VM_MOVEHEARD, VM_OPERATOR, VM_REVIEW, VM_SAYCID, VM_SAYDURATION, VM_SVMAIL, VM_TEMPGREETWARN, ast_vm_user::volgain, and ast_vm_user::zonetag.
Referenced by apply_options(), and apply_options_full().
00765 { 00766 int x; 00767 if (!strcasecmp(var, "attach")) { 00768 ast_set2_flag(vmu, ast_true(value), VM_ATTACH); 00769 } else if (!strcasecmp(var, "attachfmt")) { 00770 ast_copy_string(vmu->attachfmt, value, sizeof(vmu->attachfmt)); 00771 } else if (!strcasecmp(var, "serveremail")) { 00772 ast_copy_string(vmu->serveremail, value, sizeof(vmu->serveremail)); 00773 } else if (!strcasecmp(var, "language")) { 00774 ast_copy_string(vmu->language, value, sizeof(vmu->language)); 00775 } else if (!strcasecmp(var, "tz")) { 00776 ast_copy_string(vmu->zonetag, value, sizeof(vmu->zonetag)); 00777 #ifdef IMAP_STORAGE 00778 } else if (!strcasecmp(var, "imapuser")) { 00779 ast_copy_string(vmu->imapuser, value, sizeof(vmu->imapuser)); 00780 } else if (!strcasecmp(var, "imappassword") || !strcasecmp(var, "imapsecret")) { 00781 ast_copy_string(vmu->imappassword, value, sizeof(vmu->imappassword)); 00782 } else if (!strcasecmp(var, "imapvmshareid")) { 00783 ast_copy_string(vmu->imapvmshareid, value, sizeof(vmu->imapvmshareid)); 00784 #endif 00785 } else if (!strcasecmp(var, "delete") || !strcasecmp(var, "deletevoicemail")) { 00786 ast_set2_flag(vmu, ast_true(value), VM_DELETE); 00787 } else if (!strcasecmp(var, "saycid")){ 00788 ast_set2_flag(vmu, ast_true(value), VM_SAYCID); 00789 } else if (!strcasecmp(var,"sendvoicemail")){ 00790 ast_set2_flag(vmu, ast_true(value), VM_SVMAIL); 00791 } else if (!strcasecmp(var, "review")){ 00792 ast_set2_flag(vmu, ast_true(value), VM_REVIEW); 00793 } else if (!strcasecmp(var, "tempgreetwarn")){ 00794 ast_set2_flag(vmu, ast_true(value), VM_TEMPGREETWARN); 00795 } else if (!strcasecmp(var, "messagewrap")){ 00796 ast_set2_flag(vmu, ast_true(value), VM_MESSAGEWRAP); 00797 } else if (!strcasecmp(var, "operator")) { 00798 ast_set2_flag(vmu, ast_true(value), VM_OPERATOR); 00799 } else if (!strcasecmp(var, "envelope")){ 00800 ast_set2_flag(vmu, ast_true(value), VM_ENVELOPE); 00801 } else if (!strcasecmp(var, "moveheard")){ 00802 ast_set2_flag(vmu, ast_true(value), VM_MOVEHEARD); 00803 } else if (!strcasecmp(var, "sayduration")){ 00804 ast_set2_flag(vmu, ast_true(value), VM_SAYDURATION); 00805 } else if (!strcasecmp(var, "saydurationm")){ 00806 if (sscanf(value, "%30d", &x) == 1) { 00807 vmu->saydurationm = x; 00808 } else { 00809 ast_log(AST_LOG_WARNING, "Invalid min duration for say duration\n"); 00810 } 00811 } else if (!strcasecmp(var, "forcename")){ 00812 ast_set2_flag(vmu, ast_true(value), VM_FORCENAME); 00813 } else if (!strcasecmp(var, "forcegreetings")){ 00814 ast_set2_flag(vmu, ast_true(value), VM_FORCEGREET); 00815 } else if (!strcasecmp(var, "callback")) { 00816 ast_copy_string(vmu->callback, value, sizeof(vmu->callback)); 00817 } else if (!strcasecmp(var, "dialout")) { 00818 ast_copy_string(vmu->dialout, value, sizeof(vmu->dialout)); 00819 } else if (!strcasecmp(var, "exitcontext")) { 00820 ast_copy_string(vmu->exit, value, sizeof(vmu->exit)); 00821 } else if (!strcasecmp(var, "maxmessage") || !strcasecmp(var, "maxsecs")) { 00822 if (vmu->maxsecs <= 0) { 00823 ast_log(AST_LOG_WARNING, "Invalid max message length of %s. Using global value %d\n", value, vmmaxsecs); 00824 vmu->maxsecs = vmmaxsecs; 00825 } else { 00826 vmu->maxsecs = atoi(value); 00827 } 00828 if (!strcasecmp(var, "maxmessage")) 00829 ast_log(AST_LOG_WARNING, "Option 'maxmessage' has been deprecated in favor of 'maxsecs'. Please make that change in your voicemail config.\n"); 00830 } else if (!strcasecmp(var, "maxmsg")) { 00831 vmu->maxmsg = atoi(value); 00832 if (vmu->maxmsg <= 0) { 00833 ast_log(AST_LOG_WARNING, "Invalid number of messages per folder maxmsg=%s. Using default value %d\n", value, MAXMSG); 00834 vmu->maxmsg = MAXMSG; 00835 } else if (vmu->maxmsg > MAXMSGLIMIT) { 00836 ast_log(AST_LOG_WARNING, "Maximum number of messages per folder is %d. Cannot accept value maxmsg=%s\n", MAXMSGLIMIT, value); 00837 vmu->maxmsg = MAXMSGLIMIT; 00838 } 00839 } else if (!strcasecmp(var, "backupdeleted")) { 00840 if (sscanf(value, "%30d", &x) == 1) 00841 vmu->maxdeletedmsg = x; 00842 else if (ast_true(value)) 00843 vmu->maxdeletedmsg = MAXMSG; 00844 else 00845 vmu->maxdeletedmsg = 0; 00846 00847 if (vmu->maxdeletedmsg < 0) { 00848 ast_log(AST_LOG_WARNING, "Invalid number of deleted messages saved per mailbox backupdeleted=%s. Using default value %d\n", value, MAXMSG); 00849 vmu->maxdeletedmsg = MAXMSG; 00850 } else if (vmu->maxdeletedmsg > MAXMSGLIMIT) { 00851 ast_log(AST_LOG_WARNING, "Maximum number of deleted messages saved per mailbox is %d. Cannot accept value backupdeleted=%s\n", MAXMSGLIMIT, value); 00852 vmu->maxdeletedmsg = MAXMSGLIMIT; 00853 } 00854 } else if (!strcasecmp(var, "volgain")) { 00855 sscanf(value, "%30lf", &vmu->volgain); 00856 } else if (!strcasecmp(var, "options")) { 00857 apply_options(vmu, value); 00858 } 00859 }
| static void apply_options | ( | struct ast_vm_user * | vmu, | |
| const char * | options | |||
| ) | [static] |
Destructively Parse options and apply.
Definition at line 974 of file app_voicemail.c.
References apply_option(), ast_strdupa, s, strsep(), and var.
Referenced by append_mailbox(), and apply_option().
00975 { 00976 char *stringp; 00977 char *s; 00978 char *var, *value; 00979 stringp = ast_strdupa(options); 00980 while ((s = strsep(&stringp, "|"))) { 00981 value = s; 00982 if ((var = strsep(&value, "=")) && value) { 00983 apply_option(vmu, var, value); 00984 } 00985 } 00986 }
| static void apply_options_full | ( | struct ast_vm_user * | retval, | |
| struct ast_variable * | var | |||
| ) | [static] |
Loads the options specific to a voicemail user.
This is called when a vm_user structure is being set up, such as from load_options.
Definition at line 993 of file app_voicemail.c.
References apply_option(), ast_copy_string(), ast_strlen_zero(), ast_vm_user::context, ast_vm_user::email, ast_vm_user::fullname, ast_variable::name, ast_variable::next, ast_vm_user::pager, ast_vm_user::password, ast_vm_user::uniqueid, and ast_variable::value.
Referenced by find_user_realtime(), and load_config().
00994 { 00995 struct ast_variable *tmp; 00996 tmp = var; 00997 while (tmp) { 00998 if (!strcasecmp(tmp->name, "vmsecret")) { 00999 ast_copy_string(retval->password, tmp->value, sizeof(retval->password)); 01000 } else if (!strcasecmp(tmp->name, "secret") || !strcasecmp(tmp->name, "password")) { /* don't overwrite vmsecret if it exists */ 01001 if (ast_strlen_zero(retval->password)) 01002 ast_copy_string(retval->password, tmp->value, sizeof(retval->password)); 01003 } else if (!strcasecmp(tmp->name, "uniqueid")) { 01004 ast_copy_string(retval->uniqueid, tmp->value, sizeof(retval->uniqueid)); 01005 } else if (!strcasecmp(tmp->name, "pager")) { 01006 ast_copy_string(retval->pager, tmp->value, sizeof(retval->pager)); 01007 } else if (!strcasecmp(tmp->name, "email")) { 01008 ast_copy_string(retval->email, tmp->value, sizeof(retval->email)); 01009 } else if (!strcasecmp(tmp->name, "fullname")) { 01010 ast_copy_string(retval->fullname, tmp->value, sizeof(retval->fullname)); 01011 } else if (!strcasecmp(tmp->name, "context")) { 01012 ast_copy_string(retval->context, tmp->value, sizeof(retval->context)); 01013 #ifdef IMAP_STORAGE 01014 } else if (!strcasecmp(tmp->name, "imapuser")) { 01015 ast_copy_string(retval->imapuser, tmp->value, sizeof(retval->imapuser)); 01016 } else if (!strcasecmp(tmp->name, "imappassword") || !strcasecmp(tmp->name, "imapsecret")) { 01017 ast_copy_string(retval->imappassword, tmp->value, sizeof(retval->imappassword)); 01018 } else if (!strcasecmp(var->name, "imapvmshareid")) { 01019 ast_copy_string(retval->imapvmshareid, var->value, sizeof(retval->imapvmshareid)); 01020 #endif 01021 } else 01022 apply_option(retval, tmp->name, tmp->value); 01023 tmp = tmp->next; 01024 } 01025 }
| static int base_encode | ( | char * | filename, | |
| FILE * | so | |||
| ) | [static] |
Performs a base 64 encode algorithm on the contents of a File.
| filename | The path to the file to be encoded. Must be readable, file is opened in read mode. | |
| so | A FILE handle to the output file to receive the base 64 encoded contents of the input file, identified by filename. |
TODO: shouldn't this (and the above 3 support functions) be put into some kind of external utility location, such as funcs/func_base64.c ?
Definition at line 3672 of file app_voicemail.c.
References ast_log(), AST_LOG_WARNING, BASEMAXINLINE, eol, errno, inchar(), baseio::iocp, and ochar().
Referenced by add_email_attachment().
03673 { 03674 static const unsigned char dtable[] = { 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 03675 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd', 'e', 'f', 03676 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '0', 03677 '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'}; 03678 int i,hiteof= 0; 03679 FILE *fi; 03680 struct baseio bio; 03681 03682 memset(&bio, 0, sizeof(bio)); 03683 bio.iocp = BASEMAXINLINE; 03684 03685 if (!(fi = fopen(filename, "rb"))) { 03686 ast_log(AST_LOG_WARNING, "Failed to open file: %s: %s\n", filename, strerror(errno)); 03687 return -1; 03688 } 03689 03690 while (!hiteof){ 03691 unsigned char igroup[3], ogroup[4]; 03692 int c,n; 03693 03694 igroup[0]= igroup[1]= igroup[2]= 0; 03695 03696 for (n= 0;n<3;n++) { 03697 if ((c = inchar(&bio, fi)) == EOF) { 03698 hiteof= 1; 03699 break; 03700 } 03701 03702 igroup[n]= (unsigned char)c; 03703 } 03704 03705 if (n> 0) { 03706 ogroup[0]= dtable[igroup[0]>>2]; 03707 ogroup[1]= dtable[((igroup[0]&3)<<4) | (igroup[1]>>4)]; 03708 ogroup[2]= dtable[((igroup[1]&0xF)<<2) | (igroup[2]>>6)]; 03709 ogroup[3]= dtable[igroup[2]&0x3F]; 03710 03711 if (n<3) { 03712 ogroup[3]= '='; 03713 03714 if (n<2) 03715 ogroup[2]= '='; 03716 } 03717 03718 for (i= 0;i<4;i++) 03719 ochar(&bio, ogroup[i], so); 03720 } 03721 } 03722 03723 fclose(fi); 03724 03725 if (fputs(eol,so)==EOF) 03726 return 0; 03727 03728 return 1; 03729 }
| static int change_password_realtime | ( | struct ast_vm_user * | vmu, | |
| const char * | password | |||
| ) | [static] |
Performs a change of the voicemail passowrd in the realtime engine.
| vmu | The voicemail user to change the password for. | |
| password | The new value to be set to the password for this user. |
This only works if the voicemail user has a unique id, and if there is a realtime engine configured. This is called from the (top level) vm_change_password.
Definition at line 952 of file app_voicemail.c.
References ast_copy_string(), ast_realtime_require_field(), ast_strlen_zero(), ast_update_realtime(), ast_vm_user::password, RQ_CHAR, SENTINEL, and ast_vm_user::uniqueid.
Referenced by vm_change_password().
00953 { 00954 int res; 00955 if (!ast_strlen_zero(vmu->uniqueid)) { 00956 if (strlen(password) > 10) { 00957 ast_realtime_require_field("voicemail", "password", RQ_CHAR, strlen(password), SENTINEL); 00958 } 00959 res = ast_update_realtime("voicemail", "uniqueid", vmu->uniqueid, "password", password, SENTINEL); 00960 if (res > 0) { 00961 ast_copy_string(vmu->password, password, sizeof(vmu->password)); 00962 res = 0; 00963 } else if (!res) { 00964 res = -1; 00965 } 00966 return res; 00967 } 00968 return -1; 00969 }
| static int check_mime | ( | const char * | str | ) | [static] |
Check if the string would need encoding within the MIME standard, to avoid confusing certain mail software that expects messages to be 7-bit clean.
Definition at line 3837 of file app_voicemail.c.
Referenced by make_email_file().
| static int check_password | ( | struct ast_vm_user * | vmu, | |
| char * | password | |||
| ) | [static] |
Check that password meets minimum required length.
| vmu | The voicemail user to change the password for. | |
| password | The password string to check |
Definition at line 914 of file app_voicemail.c.
References ast_debug, ast_log(), AST_LOG_DEBUG, AST_LOG_NOTICE, AST_LOG_WARNING, ast_strlen_zero(), buf, ast_vm_user::context, ast_vm_user::mailbox, ast_vm_user::password, and vm_check_password_shell().
Referenced by vm_newuser(), and vm_options().
00915 { 00916 /* check minimum length */ 00917 if (strlen(password) < minpassword) 00918 return 1; 00919 if (!ast_strlen_zero(ext_pass_check_cmd)) { 00920 char cmd[255], buf[255]; 00921 00922 ast_log(AST_LOG_DEBUG, "Verify password policies for %s\n", password); 00923 00924 snprintf(cmd, sizeof(cmd), "%s %s %s %s %s", ext_pass_check_cmd, vmu->mailbox, vmu->context, vmu->password, password); 00925 if (vm_check_password_shell(cmd, buf, sizeof(buf))) { 00926 ast_debug(5, "Result: %s\n", buf); 00927 if (!strncasecmp(buf, "VALID", 5)) { 00928 ast_debug(3, "Passed password check: '%s'\n", buf); 00929 return 0; 00930 } else if (!strncasecmp(buf, "FAILURE", 7)) { 00931 ast_log(AST_LOG_WARNING, "Unable to execute password validation script: '%s'.\n", buf); 00932 return 0; 00933 } else { 00934 ast_log(AST_LOG_NOTICE, "Password doesn't match policies for user %s %s\n", vmu->mailbox, password); 00935 return 1; 00936 } 00937 } 00938 } 00939 return 0; 00940 }
| static int close_mailbox | ( | struct vm_state * | vms, | |
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Definition at line 6996 of file app_voicemail.c.
References ast_check_realtime(), ast_debug, ast_log(), AST_LOG_WARNING, ast_test_flag, ast_unlock_path(), ast_vm_user::context, vm_state::curbox, vm_state::curdir, vm_state::curmsg, DELETE, vm_state::deleted, ERROR_LOCK_PATH, EXISTS, vm_state::fn, vm_state::heard, vm_state::lastmsg, ast_vm_user::mailbox, make_file(), ast_vm_user::maxdeletedmsg, ast_vm_user::maxmsg, RENAME, save_to_folder(), vm_lock_path(), and VM_MOVEHEARD.
Referenced by vm_execmain().
06997 { 06998 int x = 0; 06999 #ifndef IMAP_STORAGE 07000 int res = 0, nummsg; 07001 char fn2[PATH_MAX]; 07002 #endif 07003 07004 if (vms->lastmsg <= -1) 07005 goto done; 07006 07007 vms->curmsg = -1; 07008 #ifndef IMAP_STORAGE 07009 /* Get the deleted messages fixed */ 07010 if (vm_lock_path(vms->curdir)) 07011 return ERROR_LOCK_PATH; 07012 07013 for (x = 0; x < vmu->maxmsg; x++) { 07014 if (!vms->deleted[x] && ((strcasecmp(vms->curbox, "INBOX") && strcasecmp(vms->curbox, "Urgent")) || !vms->heard[x] || (vms->heard[x] && !ast_test_flag(vmu, VM_MOVEHEARD)))) { 07015 /* Save this message. It's not in INBOX or hasn't been heard */ 07016 make_file(vms->fn, sizeof(vms->fn), vms->curdir, x); 07017 if (!EXISTS(vms->curdir, x, vms->fn, NULL)) 07018 break; 07019 vms->curmsg++; 07020 make_file(fn2, sizeof(fn2), vms->curdir, vms->curmsg); 07021 if (strcmp(vms->fn, fn2)) { 07022 RENAME(vms->curdir, x, vmu->mailbox,vmu->context, vms->curdir, vms->curmsg, vms->fn, fn2); 07023 } 07024 } else if ((!strcasecmp(vms->curbox, "INBOX") || !strcasecmp(vms->curbox, "Urgent")) && vms->heard[x] && ast_test_flag(vmu, VM_MOVEHEARD) && !vms->deleted[x]) { 07025 /* Move to old folder before deleting */ 07026 res = save_to_folder(vmu, vms, x, 1); 07027 if (res == ERROR_LOCK_PATH) { 07028 /* If save failed do not delete the message */ 07029 ast_log(AST_LOG_WARNING, "Save failed. Not moving message: %s.\n", res == ERROR_LOCK_PATH ? "unable to lock path" : "destination folder full"); 07030 vms->deleted[x] = 0; 07031 vms->heard[x] = 0; 07032 --x; 07033 } 07034 } else if (vms->deleted[x] && vmu->maxdeletedmsg) { 07035 /* Move to deleted folder */ 07036 res = save_to_folder(vmu, vms, x, 10); 07037 if (res == ERROR_LOCK_PATH) { 07038 /* If save failed do not delete the message */ 07039 vms->deleted[x] = 0; 07040 vms->heard[x] = 0; 07041 --x; 07042 } 07043 } else if (vms->deleted[x] && ast_check_realtime("voicemail_data")) { 07044 /* If realtime storage enabled - we should explicitly delete this message, 07045 cause RENAME() will overwrite files, but will keep duplicate records in RT-storage */ 07046 make_file(vms->fn, sizeof(vms->fn), vms->curdir, x); 07047 if (EXISTS(vms->curdir, x, vms->fn, NULL)) 07048 DELETE(vms->curdir, x, vms->fn, vmu); 07049 } 07050 } 07051 07052 /* Delete ALL remaining messages */ 07053 nummsg = x - 1; 07054 for (x = vms->curmsg + 1; x <= nummsg; x++) { 07055 make_file(vms->fn, sizeof(vms->fn), vms->curdir, x); 07056 if (EXISTS(vms->curdir, x, vms->fn, NULL)) 07057 DELETE(vms->curdir, x, vms->fn, vmu); 07058 } 07059 ast_unlock_path(vms->curdir); 07060 #else 07061 if (vms->deleted) { 07062 for (x=0;x < vmu->maxmsg;x++) { 07063 if (vms->deleted[x]) { 07064 ast_debug(3,"IMAP delete of %d\n",x); 07065 DELETE(vms->curdir, x, vms->fn, vmu); 07066 } 07067 } 07068 } 07069 #endif 07070 07071 done: 07072 if (vms->deleted) 07073 memset(vms->deleted, 0, vmu->maxmsg * sizeof(int)); 07074 if (vms->heard) 07075 memset(vms->heard, 0, vmu->maxmsg * sizeof(int)); 07076 07077 return 0; 07078 }
| static char* complete_voicemail_show_users | ( | const char * | line, | |
| const char * | word, | |||
| int | pos, | |||
| int | state | |||
| ) | [static] |
Definition at line 9763 of file app_voicemail.c.
References AST_LIST_TRAVERSE, ast_strdup, and ast_vm_user::context.
Referenced by handle_voicemail_show_users().
09764 { 09765 int which = 0; 09766 int wordlen; 09767 struct ast_vm_user *vmu; 09768 const char *context = ""; 09769 09770 /* 0 - show; 1 - voicemail; 2 - users; 3 - for; 4 - <context> */ 09771 if (pos > 4) 09772 return NULL; 09773 if (pos == 3) 09774 return (state == 0) ? ast_strdup("for") : NULL; 09775 wordlen = strlen(word); 09776 AST_LIST_TRAVERSE(&users, vmu, list) { 09777 if (!strncasecmp(word, vmu->context, wordlen)) { 09778 if (context && strcmp(context, vmu->context) && ++which > state) 09779 return ast_strdup(vmu->context); 09780 /* ignore repeated contexts ? */ 09781 context = vmu->context; 09782 } 09783 } 09784 return NULL; 09785 }
| static int copy | ( | char * | infile, | |
| char * | outfile | |||
| ) | [static] |
Utility function to copy a file.
| infile | The path to the file to be copied. The file must be readable, it is opened in read only mode. | |
| outfile | The path for which to copy the file to. The directory permissions must allow the creation (or truncation) of the file, and allow for opening the file in write only mode. |
When the compiler option HARDLINK_WHEN_POSSIBLE is set, the copy operation will attempt to use the hard link facility instead of copy the file (to save disk space). If the link operation fails, it falls back to the copy operation. The copy operation copies up to 4096 bytes at once.
Definition at line 3478 of file app_voicemail.c.
References ast_log(), AST_LOG_WARNING, errno, and VOICEMAIL_FILE_MODE.
Referenced by copy_plain_file().
03479 { 03480 int ifd; 03481 int ofd; 03482 int res; 03483 int len; 03484 char buf[4096]; 03485 03486 #ifdef HARDLINK_WHEN_POSSIBLE 03487 /* Hard link if possible; saves disk space & is faster */ 03488 if (link(infile, outfile)) { 03489 #endif 03490 if ((ifd = open(infile, O_RDONLY)) < 0) { 03491 ast_log(AST_LOG_WARNING, "Unable to open %s in read-only mode: %s\n", infile, strerror(errno)); 03492 return -1; 03493 } 03494 if ((ofd = open(outfile, O_WRONLY | O_TRUNC | O_CREAT, VOICEMAIL_FILE_MODE)) < 0) { 03495 ast_log(AST_LOG_WARNING, "Unable to open %s in write-only mode: %s\n", outfile, strerror(errno)); 03496 close(ifd); 03497 return -1; 03498 } 03499 do { 03500 len = read(ifd, buf, sizeof(buf)); 03501 if (len < 0) { 03502 ast_log(AST_LOG_WARNING, "Read failed on %s: %s\n", infile, strerror(errno)); 03503 close(ifd); 03504 close(ofd); 03505 unlink(outfile); 03506 } 03507 if (len) { 03508 res = write(ofd, buf, len); 03509 if (errno == ENOMEM || errno == ENOSPC || res != len) { 03510 ast_log(AST_LOG_WARNING, "Write failed on %s (%d of %d): %s\n", outfile, res, len, strerror(errno)); 03511 close(ifd); 03512 close(ofd); 03513 unlink(outfile); 03514 } 03515 } 03516 } while (len); 03517 close(ifd); 03518 close(ofd); 03519 return 0; 03520 #ifdef HARDLINK_WHEN_POSSIBLE 03521 } else { 03522 /* Hard link succeeded */ 03523 return 0; 03524 } 03525 #endif 03526 }
| static int copy_message | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| int | imbox, | |||
| int | msgnum, | |||
| long | duration, | |||
| struct ast_vm_user * | recip, | |||
| char * | fmt, | |||
| char * | dir, | |||
| const char * | flag | |||
| ) | [static] |
Copies a message from one mailbox to another.
| chan | ||
| vmu | ||
| imbox | ||
| msgnum | ||
| duration | ||
| recip | ||
| fmt | ||
| dir | This is only used by file storage based mailboxes. |
Definition at line 4629 of file app_voicemail.c.
References ast_copy_string(), ast_log(), AST_LOG_ERROR, AST_LOG_NOTICE, ast_strlen_zero(), ast_unlock_path(), ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, ast_vm_user::context, COPY, copy_plain_file(), create_dirpath(), ERROR_LOCK_PATH, EXISTS, last_message_index(), ast_vm_user::mailbox, make_dir(), make_file(), mbox(), notify_new_message(), S_OR, STORE, vm_delete(), and vm_lock_path().
Referenced by forward_message(), and leave_voicemail().
04630 { 04631 char fromdir[PATH_MAX], todir[PATH_MAX], frompath[PATH_MAX], topath[PATH_MAX]; 04632 const char *frombox = mbox(imbox); 04633 int recipmsgnum; 04634 04635 ast_log(AST_LOG_NOTICE, "Copying message from %s@%s to %s@%s\n", vmu->mailbox, vmu->context, recip->mailbox, recip->context); 04636 04637 if (!ast_strlen_zero(flag) && !strcmp(flag, "Urgent")) { /* If urgent, copy to Urgent folder */ 04638 create_dirpath(todir, sizeof(todir), recip->context, recip->mailbox, "Urgent"); 04639 } else { 04640 create_dirpath(todir, sizeof(todir), recip->context, recip->mailbox, "INBOX"); 04641 } 04642 04643 if (!dir) 04644 make_dir(fromdir, sizeof(fromdir), vmu->context, vmu->mailbox, frombox); 04645 else 04646 ast_copy_string(fromdir, dir, sizeof(fromdir)); 04647 04648 make_file(frompath, sizeof(frompath), fromdir, msgnum); 04649 make_dir(todir, sizeof(todir), recip->context, recip->mailbox, "INBOX"); 04650 04651 if (vm_lock_path(todir)) 04652 return ERROR_LOCK_PATH; 04653 04654 recipmsgnum = last_message_index(recip, todir) + 1; 04655 if (recipmsgnum < recip->maxmsg) { 04656 make_file(topath, sizeof(topath), todir, recipmsgnum); 04657 if (EXISTS(fromdir, msgnum, frompath, chan->language)) { 04658 COPY(fromdir, msgnum, todir, recipmsgnum, recip->mailbox, recip->context, frompath, topath); 04659 } else { 04660 /* For ODBC storage, if the file we want to copy isn't yet in the database, then the SQL 04661 * copy will fail. Instead, we need to create a local copy, store it, and delete the local 04662 * copy. We don't have to #ifdef this because if file storage reaches this point, there's a 04663 * much worse problem happening and IMAP storage doesn't call this function 04664 */ 04665 copy_plain_file(frompath, topath); 04666 STORE(todir, recip->mailbox, recip->context, recipmsgnum, chan, recip, fmt, duration, NULL, NULL); 04667 vm_delete(topath); 04668 } 04669 } else { 04670 ast_log(AST_LOG_ERROR, "Recipient mailbox %s@%s is full\n", recip->mailbox, recip->context); 04671 } 04672 ast_unlock_path(todir); 04673 notify_new_message(chan, recip, NULL, recipmsgnum, duration, fmt, S_OR(chan->cid.cid_num, NULL), S_OR(chan->cid.cid_name, NULL), flag); 04674 04675 return 0; 04676 }
| static void copy_plain_file | ( | char * | frompath, | |
| char * | topath | |||
| ) | [static] |
Copies a voicemail information (envelope) file.
| frompath | ||
| topath |
Every voicemail has the data (.wav) file, and the information file. This function performs the file system copying of the information file for a voicemail, handling the internal fields and their values. This is used by the COPY macro when not using IMAP storage.
Definition at line 3537 of file app_voicemail.c.
References ast_check_realtime(), ast_filecopy(), ast_load_realtime(), ast_store_realtime(), ast_variables_destroy(), copy(), exten, ast_variable::name, ast_variable::next, SENTINEL, and ast_variable::value.
Referenced by copy_message().
03538 { 03539 char frompath2[PATH_MAX], topath2[PATH_MAX]; 03540 struct ast_variable *tmp,*var = NULL; 03541 const char *origmailbox = NULL, *context = NULL, *macrocontext = NULL, *exten = NULL, *priority = NULL, *callerchan = NULL, *callerid = NULL, *origdate = NULL, *origtime = NULL, *category = NULL, *duration = NULL; 03542 ast_filecopy(frompath, topath, NULL); 03543 snprintf(frompath2, sizeof(frompath2), "%s.txt", frompath); 03544 snprintf(topath2, sizeof(topath2), "%s.txt", topath); 03545 if (ast_check_realtime("voicemail_data")) { 03546 var = ast_load_realtime("voicemail_data", "filename", frompath, SENTINEL); 03547 /* This cycle converts ast_variable linked list, to va_list list of arguments, may be there is a better way to do it? */ 03548 for (tmp = var; tmp; tmp = tmp->next) { 03549 if (!strcasecmp(tmp->name, "origmailbox")) { 03550 origmailbox = tmp->value; 03551 } else if (!strcasecmp(tmp->name, "context")) { 03552 context = tmp->value; 03553 } else if (!strcasecmp(tmp->name, "macrocontext")) { 03554 macrocontext = tmp->value; 03555 } else if (!strcasecmp(tmp->name, "exten")) { 03556 exten = tmp->value; 03557 } else if (!strcasecmp(tmp->name, "priority")) { 03558 priority = tmp->value; 03559 } else if (!strcasecmp(tmp->name, "callerchan")) { 03560 callerchan = tmp->value; 03561 } else if (!strcasecmp(tmp->name, "callerid")) { 03562 callerid = tmp->value; 03563 } else if (!strcasecmp(tmp->name, "origdate")) { 03564 origdate = tmp->value; 03565 } else if (!strcasecmp(tmp->name, "origtime")) { 03566 origtime = tmp->value; 03567 } else if (!strcasecmp(tmp->name, "category")) { 03568 category = tmp->value; 03569 } else if (!strcasecmp(tmp->name, "duration")) { 03570 duration = tmp->value; 03571 } 03572 } 03573 ast_store_realtime("voicemail_data", "filename", topath, "origmailbox", origmailbox, "context", context, "macrocontext", macrocontext, "exten", exten, "priority", priority, "callerchan", callerchan, "callerid", callerid, "origdate", origdate, "origtime", origtime, "category", category, "duration", duration, SENTINEL); 03574 } 03575 copy(frompath2, topath2); 03576 ast_variables_destroy(var); 03577 }
| static int count_messages | ( | struct ast_vm_user * | vmu, | |
| char * | dir | |||
| ) | [static] |
Find all .txt files - even if they are not in sequence from 0000.
| vmu | ||
| dir | This method is used when mailboxes are stored on the filesystem. (not ODBC and not IMAP). |
Definition at line 3384 of file app_voicemail.c.
References ast_unlock_path(), ERROR_LOCK_PATH, and vm_lock_path().
Referenced by leave_voicemail(), manager_list_voicemail_users(), and open_mailbox().
03385 { 03386 03387 int vmcount = 0; 03388 DIR *vmdir = NULL; 03389 struct dirent *vment = NULL; 03390 03391 if (vm_lock_path(dir)) 03392 return ERROR_LOCK_PATH; 03393 03394 if ((vmdir = opendir(dir))) { 03395 while ((vment = readdir(vmdir))) { 03396 if (strlen(vment->d_name) > 7 && !strncmp(vment->d_name + 7, ".txt", 4)) { 03397 vmcount++; 03398 } 03399 } 03400 closedir(vmdir); 03401 } 03402 ast_unlock_path(dir); 03403 03404 return vmcount; 03405 }
| static int create_dirpath | ( | char * | dest, | |
| int | len, | |||
| const char * | context, | |||
| const char * | ext, | |||
| const char * | folder | |||
| ) | [static] |
basically mkdir -p $dest/$context/$ext/$folder
| dest | String. base directory. | |
| len | Length of dest. | |
| context | String. Ignored if is null or empty string. | |
| ext | String. Ignored if is null or empty string. | |
| folder | String. Ignored if is null or empty string. |
Definition at line 1295 of file app_voicemail.c.
References ast_log(), AST_LOG_WARNING, ast_mkdir(), make_dir(), and VOICEMAIL_DIR_MODE.
Referenced by add_email_attachment(), copy_message(), invent_message(), leave_voicemail(), open_mailbox(), and save_to_folder().
01296 { 01297 mode_t mode = VOICEMAIL_DIR_MODE; 01298 int res; 01299 01300 make_dir(dest, len, context, ext, folder); 01301 if ((res = ast_mkdir(dest, mode))) { 01302 ast_log(AST_LOG_WARNING, "ast_mkdir '%s' failed: %s\n", dest, strerror(res)); 01303 return -1; 01304 } 01305 return 0; 01306 }
| static int dialout | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| char * | num, | |||
| char * | outgoing_context | |||
| ) | [static] |
Definition at line 10990 of file app_voicemail.c.
References ast_copy_string(), ast_play_and_wait(), ast_readstring(), ast_strlen_zero(), ast_verb, ast_verbose, ast_waitfordigit(), ast_channel::context, ast_channel::exten, option_verbose, ast_channel::priority, and VERBOSE_PREFIX_3.
Referenced by advanced_options(), and vm_execmain().
10991 { 10992 int cmd = 0; 10993 char destination[80] = ""; 10994 int retries = 0; 10995 10996 if (!num) { 10997 ast_verb(3, "Destination number will be entered manually\n"); 10998 while (retries < 3 && cmd != 't') { 10999 destination[1] = '\0'; 11000 destination[0] = cmd = ast_play_and_wait(chan,"vm-enter-num-to-call"); 11001 if (!cmd) 11002 destination[0] = cmd = ast_play_and_wait(chan, "vm-then-pound"); 11003 if (!cmd) 11004 destination[0] = cmd = ast_play_and_wait(chan, "vm-star-cancel"); 11005 if (!cmd) { 11006 cmd = ast_waitfordigit(chan, 6000); 11007 if (cmd) 11008 destination[0] = cmd; 11009 } 11010 if (!cmd) { 11011 retries++; 11012 } else { 11013 11014 if (cmd < 0) 11015 return 0; 11016 if (cmd == '*') { 11017 ast_verb(3, "User hit '*' to cancel outgoing call\n"); 11018 return 0; 11019 } 11020 if ((cmd = ast_readstring(chan,destination + strlen(destination),sizeof(destination)-1,6000,10000,"#")) < 0) 11021 retries++; 11022 else 11023 cmd = 't'; 11024 } 11025 } 11026 if (retries >= 3) { 11027 return 0; 11028 } 11029 11030 } else { 11031 if (option_verbose > 2) 11032 ast_verbose( VERBOSE_PREFIX_3 "Destination number is CID number '%s'\n", num); 11033 ast_copy_string(destination, num, sizeof(destination)); 11034 } 11035 11036 if (!ast_strlen_zero(destination)) { 11037 if (destination[strlen(destination) -1 ] == '*') 11038 return 0; 11039 if (option_verbose > 2) 11040 ast_verbose( VERBOSE_PREFIX_3 "Placing outgoing call to extension '%s' in context '%s' from context '%s'\n", destination, outgoing_context, chan->context); 11041 ast_copy_string(chan->exten, destination, sizeof(chan->exten)); 11042 ast_copy_string(chan->context, outgoing_context, sizeof(chan->context)); 11043 chan->priority = 0; 11044 return 9; 11045 } 11046 return 0; 11047 }
| static char* encode_mime_str | ( | const char * | start, | |
| char * | end, | |||
| size_t | endsize, | |||
| size_t | preamble, | |||
| size_t | postamble | |||
| ) | [static] |
Encode a string according to the MIME rules for encoding strings that are not 7-bit clean or contain control characters.
Additionally, if the encoded string would exceed the MIME limit of 76 characters per line, then the encoding will be broken up into multiple sections, separated by a space character, in order to facilitate breaking up the associated header across multiple lines.
| start | A string to be encoded | |
| end | An expandable buffer for holding the result | |
| preamble | The length of the first line already used for this string, to ensure that each line maintains a maximum length of 76 chars. | |
| postamble | the length of any additional characters appended to the line, used to ensure proper field wrapping. |
| The | encoded string. |
Definition at line 3863 of file app_voicemail.c.
References charset.
Referenced by make_email_file().
03864 { 03865 char tmp[80]; 03866 int first_section = 1; 03867 size_t endlen = 0, tmplen = 0; 03868 *end = '\0'; 03869 03870 tmplen = snprintf(tmp, sizeof(tmp), "=?%s?Q?", charset); 03871 for (; *start; start++) { 03872 int need_encoding = 0; 03873 if (*start < 33 || *start > 126 || strchr("()<>@,:;/\"[]?.=_", *start)) { 03874 need_encoding = 1; 03875 } 03876 if ((first_section && need_encoding && preamble + tmplen > 70) || 03877 (first_section && !need_encoding && preamble + tmplen > 72) || 03878 (!first_section && need_encoding && tmplen > 70) || 03879 (!first_section && !need_encoding && tmplen > 72)) { 03880 /* Start new line */ 03881 endlen += snprintf(end + endlen, endsize - endlen, "%s%s?=", first_section ? "" : " ", tmp); 03882 tmplen = snprintf(tmp, sizeof(tmp), "=?%s?Q?", charset); 03883 first_section = 0; 03884 } 03885 if (need_encoding && *start == ' ') { 03886 tmplen += snprintf(tmp + tmplen, sizeof(tmp) - tmplen, "_"); 03887 } else if (need_encoding) { 03888 tmplen += snprintf(tmp + tmplen, sizeof(tmp) - tmplen, "=%hhX", *start); 03889 } else { 03890 tmplen += snprintf(tmp + tmplen, sizeof(tmp) - tmplen, "%c", *start); 03891 } 03892 } 03893 snprintf(end + endlen, endsize - endlen, "%s%s?=%s", first_section ? "" : " ", tmp, endlen + postamble > 74 ? " " : ""); 03894 return end; 03895 }
| static struct ast_vm_user* find_or_create | ( | const char * | context, | |
| const char * | box | |||
| ) | [static, read] |
Definition at line 9547 of file app_voicemail.c.
References ast_calloc, ast_copy_string(), AST_LIST_INSERT_TAIL, AST_LIST_TRAVERSE, ast_log(), ast_test_flag, ast_vm_user::context, globalflags, LOG_WARNING, ast_vm_user::mailbox, and VM_SEARCH.
Referenced by append_mailbox(), and load_config().
09548 { 09549 struct ast_vm_user *vmu; 09550 09551 AST_LIST_TRAVERSE(&users, vmu, list) { 09552 if (ast_test_flag((&globalflags), VM_SEARCH) && !strcasecmp(box, vmu->mailbox)) { 09553 if (strcasecmp(vmu->context, context)) { 09554 ast_log(LOG_WARNING, "\nIt has been detected that you have defined mailbox '%s' in separate\ 09555 \n\tcontexts and that you have the 'searchcontexts' option on. This type of\ 09556 \n\tconfiguration creates an ambiguity that you likely do not want. Please\ 09557 \n\tamend your voicemail.conf file to avoid this situation.\n", box); 09558 } 09559 ast_log(LOG_WARNING, "Ignoring duplicated mailbox %s\n", box); 09560 return NULL; 09561 } 09562 if (!strcasecmp(context, vmu->context) && !strcasecmp(box, vmu->mailbox)) { 09563 ast_log(LOG_WARNING, "Ignoring duplicated mailbox %s in context %s\n", box, context); 09564 return NULL; 09565 } 09566 } 09567 09568 if (!(vmu = ast_calloc(1, sizeof(*vmu)))) 09569 return NULL; 09570 09571 ast_copy_string(vmu->context, context, sizeof(vmu->context)); 09572 ast_copy_string(vmu->mailbox, box, sizeof(vmu->mailbox)); 09573 09574 AST_LIST_INSERT_TAIL(&users, vmu, list); 09575 09576 return vmu; 09577 }
| static struct ast_vm_user* find_user | ( | struct ast_vm_user * | ivm, | |
| const char * | context, | |||
| const char * | mailbox | |||
| ) | [static, read] |
Finds a voicemail user from the users file or the realtime engine.
| ivm | ||
| context | ||
| mailbox |
Definition at line 1096 of file app_voicemail.c.
References AST_LIST_LOCK, AST_LIST_NEXT, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_malloc, ast_set2_flag, ast_test_flag, find_user_realtime(), globalflags, VM_ALLOCED, and VM_SEARCH.
Referenced by acf_mailbox_exists(), advanced_options(), forward_message(), leave_voicemail(), vm_authenticate(), vm_box_exists(), and vm_execmain().
01097 { 01098 /* This function could be made to generate one from a database, too */ 01099 struct ast_vm_user *vmu=NULL, *cur; 01100 AST_LIST_LOCK(&users); 01101 01102 if (!context && !ast_test_flag((&globalflags), VM_SEARCH)) 01103 context = "default"; 01104 01105 AST_LIST_TRAVERSE(&users, cur, list) { 01106 if (ast_test_flag((&globalflags), VM_SEARCH) && !strcasecmp(mailbox, cur->mailbox)) 01107 break; 01108 if (context && (!strcasecmp(context, cur->context)) && (!strcasecmp(mailbox, cur->mailbox))) 01109 break; 01110 } 01111 if (cur) { 01112 /* Make a copy, so that on a reload, we have no race */ 01113 if ((vmu = (ivm ? ivm : ast_malloc(sizeof(*vmu))))) { 01114 memcpy(vmu, cur, sizeof(*vmu)); 01115 ast_set2_flag(vmu, !ivm, VM_ALLOCED); 01116 AST_LIST_NEXT(vmu, list) = NULL; 01117 } 01118 } else 01119 vmu = find_user_realtime(ivm, context, mailbox); 01120 AST_LIST_UNLOCK(&users); 01121 return vmu; 01122 }
| static struct ast_vm_user* find_user_realtime | ( | struct ast_vm_user * | ivm, | |
| const char * | context, | |||
| const char * | mailbox | |||
| ) | [static, read] |
Finds a voicemail user from the realtime engine.
| ivm | ||
| context | ||
| mailbox | This is called as a fall through case when the normal find_user() was not able to find a user. That is, the default it so look in the usual voicemail users file first. |
Definition at line 1059 of file app_voicemail.c.
References apply_options_full(), ast_calloc, ast_copy_string(), ast_free, ast_load_realtime(), ast_set_flag, ast_test_flag, ast_variables_destroy(), globalflags, ast_vm_user::mailbox, populate_defaults(), SENTINEL, var, VM_ALLOCED, and VM_SEARCH.
Referenced by find_user().
01060 { 01061 struct ast_variable *var; 01062 struct ast_vm_user *retval; 01063 01064 if ((retval = (ivm ? ivm : ast_calloc(1, sizeof(*retval))))) { 01065 if (!ivm) 01066 ast_set_flag(retval, VM_ALLOCED); 01067 else 01068 memset(retval, 0, sizeof(*retval)); 01069 if (mailbox) 01070 ast_copy_string(retval->mailbox, mailbox, sizeof(retval->mailbox)); 01071 populate_defaults(retval); 01072 if (!context && ast_test_flag((&globalflags), VM_SEARCH)) 01073 var = ast_load_realtime("voicemail", "mailbox", mailbox, SENTINEL); 01074 else 01075 var = ast_load_realtime("voicemail", "mailbox", mailbox, "context", context, SENTINEL); 01076 if (var) { 01077 apply_options_full(retval, var); 01078 ast_variables_destroy(var); 01079 } else { 01080 if (!ivm) 01081 ast_free(retval); 01082 retval = NULL; 01083 } 01084 } 01085 return retval; 01086 }
| static int forward_message | ( | struct ast_channel * | chan, | |
| char * | context, | |||
| struct vm_state * | vms, | |||
| struct ast_vm_user * | sender, | |||
| char * | fmt, | |||
| int | is_new_message, | |||
| signed char | record_gain, | |||
| int | urgent | |||
| ) | [static] |
Sends a voicemail message to a mailbox recipient.
| ast_channel | ||
| context | ||
| vms | ||
| sender | ||
| fmt | ||
| is_new_message | Used to indicate the mode for which this method was invoked. Will be 0 when called to forward an existing message (option 8) Will be 1 when called to leave a message (option 3->5) | |
| record_gain |
Reads the destination mailbox(es) from keypad input for CID, or if use_directory feature is enabled, the Directory.
When in the leave message mode (is_new_message == 1):
When in the forward message mode (is_new_message == 0):
Definition at line 6297 of file app_voicemail.c.
References ast_clear_flag, ast_copy_string(), ast_fileexists(), AST_LIST_EMPTY, AST_LIST_HEAD_NOLOCK_STATIC, AST_LIST_INSERT_HEAD, AST_LIST_REMOVE_CURRENT, AST_LIST_REMOVE_HEAD, AST_LIST_TRAVERSE_SAFE_BEGIN, AST_LIST_TRAVERSE_SAFE_END, ast_log(), AST_LOG_ERROR, AST_LOG_WARNING, AST_MAX_EXTENSION, ast_play_and_wait(), ast_readstring(), ast_say_digit_str(), ast_stream_and_wait(), ast_streamfile(), ast_strlen_zero(), ast_test_flag, ast_waitfordigit(), ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, ast_vm_user::context, ast_channel::context, copy_message(), vm_state::curbox, vm_state::curdir, vm_state::curmsg, DISPOSE, ast_channel::exten, find_user(), vm_state::fn, free_user(), globalflags, leave_voicemail(), LOG_NOTICE, ast_vm_user::mailbox, pbx_exec(), pbx_findapp(), ast_channel::priority, leave_vm_options::record_gain, RETRIEVE, run_externnotify(), s, S_OR, sendmail(), STORE, strsep(), vm_state::username, VM_ATTACH, VM_DIRECFORWARD, vm_forwardoptions(), and VM_FWDURGAUTO.
Referenced by vm_execmain().
06298 { 06299 #ifdef IMAP_STORAGE 06300 int todircount=0; 06301 struct vm_state *dstvms; 06302 #endif 06303 char username[70]=""; 06304 char fn[PATH_MAX]; /* for playback of name greeting */ 06305 char ecodes[16] = "#"; 06306 int res = 0, cmd = 0; 06307 struct ast_vm_user *receiver = NULL, *vmtmp; 06308 AST_LIST_HEAD_NOLOCK_STATIC(extensions, ast_vm_user); 06309 char *stringp; 06310 const char *s; 06311 int saved_messages = 0, found = 0; 06312 int valid_extensions = 0; 06313 char *dir; 06314 int curmsg; 06315 char urgent_str[7] = ""; 06316 char tmptxtfile[PATH_MAX]; 06317 06318 if (ast_test_flag((&globalflags), VM_FWDURGAUTO)) { 06319 ast_copy_string(urgent_str, urgent ? "Urgent" : "", sizeof(urgent_str)); 06320 } 06321 06322 if (vms == NULL) return -1; 06323 dir = vms->curdir; 06324 curmsg = vms->curmsg; 06325 06326 tmptxtfile[0] = '\0'; 06327 while (!res && !valid_extensions) { 06328 int use_directory = 0; 06329 if (ast_test_flag((&globalflags), VM_DIRECFORWARD)) { 06330 int done = 0; 06331 int retries = 0; 06332 cmd=0; 06333 while ((cmd >= 0) && !done ){ 06334 if (cmd) 06335 retries = 0; 06336 switch (cmd) { 06337 case '1': 06338 use_directory = 0; 06339 done = 1; 06340 break; 06341 case '2': 06342 use_directory = 1; 06343 done=1; 06344 break; 06345 case '*': 06346 cmd = 't'; 06347 done = 1; 06348 break; 06349 default: 06350 /* Press 1 to enter an extension press 2 to use the directory */ 06351 cmd = ast_play_and_wait(chan,"vm-forward"); 06352 if (!cmd) 06353 cmd = ast_waitfordigit(chan,3000); 06354 if (!cmd) 06355 retries++; 06356 if (retries > 3) { 06357 cmd = 't'; 06358 done = 1; 06359 } 06360 06361 } 06362 } 06363 if (cmd < 0 || cmd == 't') 06364 break; 06365 } 06366 06367 if (use_directory) { 06368 /* use app_directory */ 06369 06370 char old_context[sizeof(chan->context)]; 06371 char old_exten[sizeof(chan->exten)]; 06372 int old_priority; 06373 struct ast_app* directory_app; 06374 06375 directory_app = pbx_findapp("Directory"); 06376 if (directory_app) { 06377 char vmcontext[256]; 06378 /* make backup copies */ 06379 memcpy(old_context, chan->context, sizeof(chan->context)); 06380 memcpy(old_exten, chan->exten, sizeof(chan->exten)); 06381 old_priority = chan->priority; 06382 06383 /* call the the Directory, changes the channel */ 06384 snprintf(vmcontext, sizeof(vmcontext), "%s,,v", context ? context : "default"); 06385 res = pbx_exec(chan, directory_app, vmcontext); 06386 06387 ast_copy_string(username, chan->exten, sizeof(username)); 06388 06389 /* restore the old context, exten, and priority */ 06390 memcpy(chan->context, old_context, sizeof(chan->context)); 06391 memcpy(chan->exten, old_exten, sizeof(chan->exten)); 06392 chan->priority = old_priority; 06393 } else { 06394 ast_log(AST_LOG_WARNING, "Could not find the Directory application, disabling directory_forward\n"); 06395 ast_clear_flag((&globalflags), VM_DIRECFORWARD); 06396 } 06397 } else { 06398 /* Ask for an extension */ 06399 res = ast_streamfile(chan, "vm-extension", chan->language); /* "extension" */ 06400 if (res) 06401 break; 06402 if ((res = ast_readstring(chan, username, sizeof(username) - 1, 2000, 10000, "#") < 0)) 06403 break; 06404 } 06405 06406 /* start all over if no username */ 06407 if (ast_strlen_zero(username)) 06408 continue; 06409 stringp = username; 06410 s = strsep(&stringp, "*"); 06411 /* start optimistic */ 06412 valid_extensions = 1; 06413 while (s) { 06414 if ((is_new_message == 1 || strcmp(s, sender->mailbox)) && (receiver = find_user(NULL, context, s))) { 06415 AST_LIST_INSERT_HEAD(&extensions, receiver, list); 06416 found++; 06417 } else { 06418 /* XXX Optimization for the future. When we encounter a single bad extension, 06419 * bailing out on all of the extensions may not be the way to go. We should 06420 * probably just bail on that single extension, then allow the user to enter 06421 * several more. XXX 06422 */ 06423 while ((receiver = AST_LIST_REMOVE_HEAD(&extensions, list))) { 06424 free_user(receiver); 06425 } 06426 ast_log(LOG_NOTICE, "'%s' is not a valid mailbox\n", s); 06427 valid_extensions = 0; 06428 break; 06429 } 06430 06431 /* play name if available, else play extension number */ 06432 snprintf(fn, sizeof(fn), "%s%s/%s/greet", VM_SPOOL_DIR, receiver->context, s); 06433 RETRIEVE(fn, -1, s, receiver->context); 06434 if (ast_fileexists(fn, NULL, NULL) > 0) { 06435 res = ast_stream_and_wait(chan, fn, ecodes); 06436 if (res) { 06437 DISPOSE(fn, -1); 06438 return res; 06439 } 06440 } else { 06441 res = ast_say_digit_str(chan, s, ecodes, chan->language); 06442 } 06443 DISPOSE(fn, -1); 06444 06445 s = strsep(&stringp, "*"); 06446 } 06447 /* break from the loop of reading the extensions */ 06448 if (valid_extensions) 06449 break; 06450 /* "I am sorry, that's not a valid extension. Please try again." */ 06451 res = ast_play_and_wait(chan, "pbx-invalid"); 06452 } 06453 /* check if we're clear to proceed */ 06454 if (AST_LIST_EMPTY(&extensions) || !valid_extensions) 06455 return res; 06456 if (is_new_message == 1) { 06457 struct leave_vm_options leave_options; 06458 char mailbox[AST_MAX_EXTENSION * 2 + 2]; 06459 snprintf(mailbox, sizeof(mailbox), "%s@%s", username, context); 06460 06461 /* Send VoiceMail */ 06462 memset(&leave_options, 0, sizeof(leave_options)); 06463 leave_options.record_gain = record_gain; 06464 cmd = leave_voicemail(chan, mailbox, &leave_options); 06465 } else { 06466 /* Forward VoiceMail */ 06467 long duration = 0; 06468 struct vm_state vmstmp; 06469 memcpy(&vmstmp, vms, sizeof(vmstmp)); 06470 06471 RETRIEVE(dir, curmsg, sender->mailbox, sender->context); 06472 06473 cmd = vm_forwardoptions(chan, sender, vmstmp.curdir, curmsg, vmfmts, S_OR(context, "default"), record_gain, &duration, &vmstmp, urgent_str); 06474 if (!cmd) { 06475 AST_LIST_TRAVERSE_SAFE_BEGIN(&extensions, vmtmp, list) { 06476 #ifdef IMAP_STORAGE 06477 int attach_user_voicemail; 06478 char *myserveremail = serveremail; 06479 06480 /* get destination mailbox */ 06481 dstvms = get_vm_state_by_mailbox(vmtmp->mailbox, vmtmp->context, 0); 06482 if (!dstvms) { 06483 dstvms = create_vm_state_from_user(vmtmp); 06484 } 06485 if (dstvms) { 06486 init_mailstream(dstvms, 0); 06487 if (!dstvms->mailstream) { 06488 ast_log(AST_LOG_ERROR, "IMAP mailstream for %s is NULL\n", vmtmp->mailbox); 06489 } else { 06490 STORE(vmstmp.curdir, vmtmp->mailbox, vmtmp->context, dstvms->curmsg, chan, vmtmp, fmt, duration, dstvms, urgent_str); 06491 run_externnotify(vmtmp->context, vmtmp->mailbox, urgent_str); 06492 } 06493 } else { 06494 ast_log(AST_LOG_ERROR, "Could not find state information for mailbox %s\n", vmtmp->mailbox); 06495 } 06496 if (!ast_strlen_zero(vmtmp->serveremail)) 06497 myserveremail = vmtmp->serveremail; 06498 attach_user_voicemail = ast_test_flag(vmtmp, VM_ATTACH); 06499 /* NULL category for IMAP storage */ 06500 sendmail(myserveremail, vmtmp, todircount, vmtmp->context, vmtmp->mailbox, dstvms->curbox, S_OR(chan->cid.cid_num, NULL), S_OR(chan->cid.cid_name, NULL), vmstmp.fn, vmstmp.introfn, fmt, duration, attach_user_voicemail, chan, NULL, urgent_str); 06501 #else 06502 copy_message(chan, sender, 0, curmsg, duration, vmtmp, fmt, dir, urgent_str); 06503 #endif 06504 saved_messages++; 06505 AST_LIST_REMOVE_CURRENT(list); 06506 free_user(vmtmp); 06507 if (res) 06508 break; 06509 } 06510 AST_LIST_TRAVERSE_SAFE_END; 06511 if (saved_messages > 0) { 06512 /* give confirmation that the message was saved */ 06513 /* commented out since we can't forward batches yet 06514 if (saved_messages == 1) 06515 res = ast_play_and_wait(chan, "vm-message"); 06516 else 06517 res = ast_play_and_wait(chan, "vm-messages"); 06518 if (!res) 06519 res = ast_play_and_wait(chan, "vm-saved"); */ 06520 #ifdef IMAP_STORAGE 06521 /* If forwarded with intro, DON'T PLAY THIS MESSAGE AGAIN! */ 06522 if (ast_strlen_zero(vmstmp.introfn)) 06523 #endif 06524 res = ast_play_and_wait(chan, "vm-msgsaved"); 06525 } 06526 } 06527 DISPOSE(dir, curmsg); 06528 } 06529 06530 /* If anything failed above, we still have this list to free */ 06531 while ((vmtmp = AST_LIST_REMOVE_HEAD(&extensions, list))) 06532 free_user(vmtmp); 06533 return res ? res : cmd; 06534 }
| static void free_user | ( | struct ast_vm_user * | vmu | ) | [static] |
Definition at line 1331 of file app_voicemail.c.
References ast_free, ast_test_flag, and VM_ALLOCED.
Referenced by forward_message(), free_vm_users(), leave_voicemail(), and vm_execmain().
01332 { 01333 if (ast_test_flag(vmu, VM_ALLOCED)) 01334 ast_free(vmu); 01335 }
| static void free_vm_users | ( | void | ) | [static] |
Free the users structure.
Definition at line 10215 of file app_voicemail.c.
References AST_LIST_LOCK, AST_LIST_REMOVE_HEAD, AST_LIST_UNLOCK, ast_set_flag, free_user(), and VM_ALLOCED.
Referenced by load_config(), and unload_module().
10216 { 10217 struct ast_vm_user *current; 10218 AST_LIST_LOCK(&users); 10219 while ((current = AST_LIST_REMOVE_HEAD(&users, list))) { 10220 ast_set_flag(current, VM_ALLOCED); 10221 free_user(current); 10222 } 10223 AST_LIST_UNLOCK(&users); 10224 }
| static void free_vm_zones | ( | void | ) | [static] |
Free the zones structure.
Definition at line 10227 of file app_voicemail.c.
References AST_LIST_LOCK, AST_LIST_REMOVE_HEAD, AST_LIST_UNLOCK, and free_zone().
Referenced by load_config(), and unload_module().
10228 { 10229 struct vm_zone *zcur; 10230 AST_LIST_LOCK(&zones); 10231 while ((zcur = AST_LIST_REMOVE_HEAD(&zones, list))) 10232 free_zone(zcur); 10233 AST_LIST_UNLOCK(&zones); 10234 }
| static void free_zone | ( | struct vm_zone * | z | ) | [static] |
Definition at line 4404 of file app_voicemail.c.
References ast_free.
Referenced by free_vm_zones().
04405 { 04406 ast_free(z); 04407 }
| static int get_date | ( | char * | s, | |
| int | len | |||
| ) | [static] |
Gets the current date and time, as formatted string.
| s | The buffer to hold the output formatted date. | |
| len | the length of the buffer. Used to prevent buffer overflow in ast_strftime. |
The date format string used is "%a %b %e %r UTC %Y".
Definition at line 4360 of file app_voicemail.c.
References ast_localtime(), ast_strftime(), and ast_tvnow().
Referenced by leave_voicemail().
04361 { 04362 struct ast_tm tm; 04363 struct timeval t = ast_tvnow(); 04364 04365 ast_localtime(&t, &tm, "UTC"); 04366 04367 return ast_strftime(s, len, "%a %b %e %r UTC %Y", &tm); 04368 }
| static int get_folder | ( | struct ast_channel * | chan, | |
| int | start | |||
| ) | [static] |
get_folder: Folder menu Plays "press 1 for INBOX messages" etc. Should possibly be internationalized
Definition at line 5963 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), ast_waitfordigit(), mbox(), and vm_play_folder_name().
Referenced by get_folder2().
05964 { 05965 int x; 05966 int d; 05967 char fn[PATH_MAX]; 05968 d = ast_play_and_wait(chan, "vm-press"); /* "Press" */ 05969 if (d) 05970 return d; 05971 for (x = start; x< 5; x++) { /* For all folders */ 05972 if ((d = ast_say_number(chan, x, AST_DIGIT_ANY, chan->language, NULL))) 05973 return d; 05974 d = ast_play_and_wait(chan, "vm-for"); /* "for" */ 05975 if (d) 05976 return d; 05977 snprintf(fn, sizeof(fn), "vm-%s", mbox(x)); /* Folder name */ 05978 d = vm_play_folder_name(chan, fn); 05979 if (d) 05980 return d; 05981 d = ast_waitfordigit(chan, 500); 05982 if (d) 05983 return d; 05984 } 05985 d = ast_play_and_wait(chan, "vm-tocancel"); /* "or pound to cancel" */ 05986 if (d) 05987 return d; 05988 d = ast_waitfordigit(chan, 4000); 05989 return d; 05990 }
| static int get_folder2 | ( | struct ast_channel * | chan, | |
| char * | fn, | |||
| int | start | |||
| ) | [static] |
plays a prompt and waits for a keypress.
| chan | ||
| fn | the name of the voice prompt file to be played. For example, 'vm-changeto', 'vm-savefolder' | |
| start | Does not appear to be used at this time. |
This is used by the main menu option to move a message to a folder or to save a message into a folder. After playing the message identified by the fn parameter value, it calls get_folder(), which plays the prompting for the number inputs that correspond to the available folders.
Definition at line 6004 of file app_voicemail.c.
References ast_play_and_wait(), and get_folder().
Referenced by vm_execmain().
06005 { 06006 int res = 0; 06007 res = ast_play_and_wait(chan, fn); /* Folder name */ 06008 while (((res < '0') || (res > '9')) && 06009 (res != '#') && (res >= 0)) { 06010 res = get_folder(chan, 0); 06011 } 06012 return res; 06013 }
| static int handle_subscribe | ( | void * | datap | ) | [static] |
Definition at line 9999 of file app_voicemail.c.
References ast_calloc, ast_free, AST_RWLIST_INSERT_TAIL, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, ast_strlen_zero(), mwi_sub_task::context, mwi_sub::mailbox, mwi_sub_task::mailbox, mwi_sub_task::uniqueid, and mwi_sub::uniqueid.
Referenced by mwi_sub_event_cb().
10000 { 10001 unsigned int len; 10002 struct mwi_sub *mwi_sub; 10003 struct mwi_sub_task *p = datap; 10004 10005 len = sizeof(*mwi_sub); 10006 if (!ast_strlen_zero(p->mailbox)) 10007 len += strlen(p->mailbox); 10008 10009 if (!ast_strlen_zero(p->context)) 10010 len += strlen(p->context) + 1; /* Allow for seperator */ 10011 10012 if (!(mwi_sub = ast_calloc(1, len))) 10013 return -1; 10014 10015 mwi_sub->uniqueid = p->uniqueid; 10016 if (!ast_strlen_zero(p->mailbox)) 10017 strcpy(mwi_sub->mailbox, p->mailbox); 10018 10019 if (!ast_strlen_zero(p->context)) { 10020 strcat(mwi_sub->mailbox, "@"); 10021 strcat(mwi_sub->mailbox, p->context); 10022 } 10023 10024 AST_RWLIST_WRLOCK(&mwi_subs); 10025 AST_RWLIST_INSERT_TAIL(&mwi_subs, mwi_sub, entry); 10026 AST_RWLIST_UNLOCK(&mwi_subs); 10027 ast_free((void *) p->mailbox); 10028 ast_free((void *) p->context); 10029 ast_free(p); 10030 return 0; 10031 }
| static int handle_unsubscribe | ( | void * | datap | ) | [static] |
Definition at line 9977 of file app_voicemail.c.
References ast_free, AST_LIST_REMOVE_CURRENT, AST_RWLIST_TRAVERSE_SAFE_BEGIN, AST_RWLIST_TRAVERSE_SAFE_END, AST_RWLIST_UNLOCK, AST_RWLIST_WRLOCK, mwi_sub::entry, mwi_sub_destroy(), and mwi_sub::uniqueid.
Referenced by mwi_unsub_event_cb().
09978 { 09979 struct mwi_sub *mwi_sub; 09980 uint32_t *uniqueid = datap; 09981 09982 AST_RWLIST_WRLOCK(&mwi_subs); 09983 AST_RWLIST_TRAVERSE_SAFE_BEGIN(&mwi_subs, mwi_sub, entry) { 09984 if (mwi_sub->uniqueid == *uniqueid) { 09985 AST_LIST_REMOVE_CURRENT(entry); 09986 break; 09987 } 09988 } 09989 AST_RWLIST_TRAVERSE_SAFE_END 09990 AST_RWLIST_UNLOCK(&mwi_subs); 09991 09992 if (mwi_sub) 09993 mwi_sub_destroy(mwi_sub); 09994 09995 ast_free(uniqueid); 09996 return 0; 09997 }
| static char* handle_voicemail_reload | ( | struct ast_cli_entry * | e, | |
| int | cmd, | |||
| struct ast_cli_args * | a | |||
| ) | [static] |
Reload voicemail configuration from the CLI.
Definition at line 9898 of file app_voicemail.c.
References ast_cli_args::argc, ast_cli(), CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, load_config(), and ast_cli_entry::usage.
09899 { 09900 switch (cmd) { 09901 case CLI_INIT: 09902 e->command = "voicemail reload"; 09903 e->usage = 09904 "Usage: voicemail reload\n" 09905 " Reload voicemail configuration\n"; 09906 return NULL; 09907 case CLI_GENERATE: 09908 return NULL; 09909 } 09910 09911 if (a->argc != 2) 09912 return CLI_SHOWUSAGE; 09913 09914 ast_cli(a->fd, "Reloading voicemail configuration...\n"); 09915 load_config(1); 09916 09917 return CLI_SUCCESS; 09918 }
| static char* handle_voicemail_show_users | ( | struct ast_cli_entry * | e, | |
| int | cmd, | |||
| struct ast_cli_args * | a | |||
| ) | [static] |
Show a list of voicemail users in the CLI.
Definition at line 9788 of file app_voicemail.c.
References ast_cli_args::argc, ast_cli_args::argv, ast_check_realtime(), ast_cli(), AST_LIST_EMPTY, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_strlen_zero(), CLI_FAILURE, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, complete_voicemail_show_users(), ast_vm_user::context, ast_cli_args::fd, ast_vm_user::fullname, HVSU_OUTPUT_FORMAT, inboxcount(), ast_cli_args::line, ast_vm_user::mailbox, ast_cli_args::n, ast_cli_args::pos, show_users_realtime(), ast_cli_entry::usage, ast_cli_args::word, and ast_vm_user::zonetag.
09789 { 09790 struct ast_vm_user *vmu; 09791 #define HVSU_OUTPUT_FORMAT "%-10s %-5s %-25s %-10s %6s\n" 09792 const char *context = NULL; 09793 int users_counter = 0; 09794 09795 switch (cmd) { 09796 case CLI_INIT: 09797 e->command = "voicemail show users"; 09798 e->usage = 09799 "Usage: voicemail show users [for <context>]\n" 09800 " Lists all mailboxes currently set up\n"; 09801 return NULL; 09802 case CLI_GENERATE: 09803 return complete_voicemail_show_users(a->line, a->word, a->pos, a->n); 09804 } 09805 09806 if ((a->argc < 3) || (a->argc > 5) || (a->argc == 4)) 09807 return CLI_SHOWUSAGE; 09808 if (a->argc == 5) { 09809 if (strcmp(a->argv[3],"for")) 09810 return CLI_SHOWUSAGE; 09811 context = a->argv[4]; 09812 } 09813 09814 if (ast_check_realtime("voicemail")) { 09815 if (!context) { 09816 ast_cli(a->fd, "You must specify a specific context to show users from realtime!\n"); 09817 return CLI_SHOWUSAGE; 09818 } 09819 return show_users_realtime(a->fd, context); 09820 } 09821 09822 AST_LIST_LOCK(&users); 09823 if (AST_LIST_EMPTY(&users)) { 09824 ast_cli(a->fd, "There are no voicemail users currently defined\n"); 09825 AST_LIST_UNLOCK(&users); 09826 return CLI_FAILURE; 09827 } 09828 if (a->argc == 3) 09829 ast_cli(a->fd, HVSU_OUTPUT_FORMAT, "Context", "Mbox", "User", "Zone", "NewMsg"); 09830 else { 09831 int count = 0; 09832 AST_LIST_TRAVERSE(&users, vmu, list) { 09833 if (!strcmp(context, vmu->context)) 09834 count++; 09835 } 09836 if (count) { 09837 ast_cli(a->fd, HVSU_OUTPUT_FORMAT, "Context", "Mbox", "User", "Zone", "NewMsg"); 09838 } else { 09839 ast_cli(a->fd, "No such voicemail context \"%s\"\n", context); 09840 AST_LIST_UNLOCK(&users); 09841 return CLI_FAILURE; 09842 } 09843 } 09844 AST_LIST_TRAVERSE(&users, vmu, list) { 09845 int newmsgs = 0, oldmsgs = 0; 09846 char count[12], tmp[256] = ""; 09847 09848 if ((a->argc == 3) || ((a->argc == 5) && !strcmp(context, vmu->context))) { 09849 snprintf(tmp, sizeof(tmp), "%s@%s", vmu->mailbox, ast_strlen_zero(vmu->context) ? "default" : vmu->context); 09850 inboxcount(tmp, &newmsgs, &oldmsgs); 09851 snprintf(count, sizeof(count), "%d", newmsgs); 09852 ast_cli(a->fd, HVSU_OUTPUT_FORMAT, vmu->context, vmu->mailbox, vmu->fullname, vmu->zonetag, count); 09853 users_counter++; 09854 } 09855 } 09856 AST_LIST_UNLOCK(&users); 09857 ast_cli(a->fd, "%d voicemail users configured.\n", users_counter); 09858 return CLI_SUCCESS; 09859 }
| static char* handle_voicemail_show_zones | ( | struct ast_cli_entry * | e, | |
| int | cmd, | |||
| struct ast_cli_args * | a | |||
| ) | [static] |
Show a list of voicemail zones in the CLI.
Definition at line 9862 of file app_voicemail.c.
References ast_cli_args::argc, ast_cli(), AST_LIST_EMPTY, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, CLI_FAILURE, CLI_GENERATE, CLI_INIT, CLI_SHOWUSAGE, CLI_SUCCESS, ast_cli_entry::command, ast_cli_args::fd, HVSZ_OUTPUT_FORMAT, vm_zone::msg_format, vm_zone::name, vm_zone::timezone, and ast_cli_entry::usage.
09863 { 09864 struct vm_zone *zone; 09865 #define HVSZ_OUTPUT_FORMAT "%-15s %-20s %-45s\n" 09866 char *res = CLI_SUCCESS; 09867 09868 switch (cmd) { 09869 case CLI_INIT: 09870 e->command = "voicemail show zones"; 09871 e->usage = 09872 "Usage: voicemail show zones\n" 09873 " Lists zone message formats\n"; 09874 return NULL; 09875 case CLI_GENERATE: 09876 return NULL; 09877 } 09878 09879 if (a->argc != 3) 09880 return CLI_SHOWUSAGE; 09881 09882 AST_LIST_LOCK(&zones); 09883 if (!AST_LIST_EMPTY(&zones)) { 09884 ast_cli(a->fd, HVSZ_OUTPUT_FORMAT, "Zone", "Timezone", "Message Format"); 09885 AST_LIST_TRAVERSE(&zones, zone, list) { 09886 ast_cli(a->fd, HVSZ_OUTPUT_FORMAT, zone->name, zone->timezone, zone->msg_format); 09887 } 09888 } else { 09889 ast_cli(a->fd, "There are no voicemail zones currently defined\n"); 09890 res = CLI_FAILURE; 09891 } 09892 AST_LIST_UNLOCK(&zones); 09893 09894 return res; 09895 }
| static int has_voicemail | ( | const char * | mailbox, | |
| const char * | folder | |||
| ) | [static] |
Determines if the given folder has messages.
| mailbox | The @ delimited string for user. If no context is found, uses 'default' for the context. | |
| folder | the folder to look in |
This function is used when the mailbox is stored in a filesystem back end. This invokes the messagecount(). Here we are interested in the presence of messages (> 0) only, not the actual count.
Definition at line 4737 of file app_voicemail.c.
References __has_voicemail(), ast_copy_string(), and strsep().
Referenced by load_module(), and vm_execmain().
04738 { 04739 char tmp[256], *tmp2 = tmp, *box, *context; 04740 ast_copy_string(tmp, mailbox, sizeof(tmp)); 04741 while ((box = strsep(&tmp2, ","))) { 04742 if ((context = strchr(box, '@'))) 04743 *context++ = '\0'; 04744 else 04745 context = "default"; 04746 if (__has_voicemail(context, box, folder, 1)) 04747 return 1; 04748 } 04749 return 0; 04750 }
| static int inboxcount | ( | const char * | mailbox, | |
| int * | newmsgs, | |||
| int * | oldmsgs | |||
| ) | [static] |
Definition at line 4809 of file app_voicemail.c.
References inboxcount2().
Referenced by handle_voicemail_show_users(), leave_voicemail(), load_module(), and manager_list_voicemail_users().
04810 { 04811 return inboxcount2(mailbox, NULL, newmsgs, oldmsgs); 04812 }
| static int inboxcount2 | ( | const char * | mailbox, | |
| int * | urgentmsgs, | |||
| int * | newmsgs, | |||
| int * | oldmsgs | |||
| ) | [static] |
Definition at line 4753 of file app_voicemail.c.
References __has_voicemail(), ast_copy_string(), ast_strlen_zero(), and strsep().
Referenced by append_mailbox(), inboxcount(), load_module(), poll_subscribed_mailboxes(), and run_externnotify().
04754 { 04755 char tmp[256]; 04756 char *context; 04757 04758 /* If no mailbox, return immediately */ 04759 if (ast_strlen_zero(mailbox)) 04760 return 0; 04761 04762 if (newmsgs) 04763 *newmsgs = 0; 04764 if (oldmsgs) 04765 *oldmsgs = 0; 04766 if (urgentmsgs) 04767 *urgentmsgs = 0; 04768 04769 if (strchr(mailbox, ',')) { 04770 int tmpnew, tmpold, tmpurgent; 04771 char *mb, *cur; 04772 04773 ast_copy_string(tmp, mailbox, sizeof(tmp)); 04774 mb = tmp; 04775 while ((cur = strsep(&mb, ", "))) { 04776 if (!ast_strlen_zero(cur)) { 04777 if (inboxcount2(cur, urgentmsgs ? &tmpurgent : NULL, newmsgs ? &tmpnew : NULL, oldmsgs ? &tmpold : NULL)) 04778 return -1; 04779 else { 04780 if (newmsgs) 04781 *newmsgs += tmpnew; 04782 if (oldmsgs) 04783 *oldmsgs += tmpold; 04784 if (urgentmsgs) 04785 *urgentmsgs += tmpurgent; 04786 } 04787 } 04788 } 04789 return 0; 04790 } 04791 04792 ast_copy_string(tmp, mailbox, sizeof(tmp)); 04793 04794 if ((context = strchr(tmp, '@'))) 04795 *context++ = '\0'; 04796 else 04797 context = "default"; 04798 04799 if (newmsgs) 04800 *newmsgs = __has_voicemail(context, tmp, "INBOX", 0); 04801 if (oldmsgs) 04802 *oldmsgs = __has_voicemail(context, tmp, "Old", 0); 04803 if (urgentmsgs) 04804 *urgentmsgs = __has_voicemail(context, tmp, "Urgent", 0); 04805 04806 return 0; 04807 }
| static int inbuf | ( | struct baseio * | bio, | |
| FILE * | fi | |||
| ) | [static] |
utility used by inchar(), for base_encode()
Definition at line 3609 of file app_voicemail.c.
References baseio::ateof, BASEMAXINLINE, baseio::iobuf, baseio::iocp, and baseio::iolen.
Referenced by ast_eivr_getvariable(), ast_eivr_setvariable(), inchar(), and sip_addheader().
| static int inchar | ( | struct baseio * | bio, | |
| FILE * | fi | |||
| ) | [static] |
utility used by base_encode()
Definition at line 3633 of file app_voicemail.c.
References inbuf(), baseio::iobuf, baseio::iocp, and baseio::iolen.
Referenced by base_encode().
| static int invent_message | ( | struct ast_channel * | chan, | |
| char * | context, | |||
| char * | ext, | |||
| int | busy, | |||
| char * | ecodes | |||
| ) | [static] |
Definition at line 4370 of file app_voicemail.c.
References ast_fileexists(), ast_log(), AST_LOG_WARNING, ast_say_digit_str(), ast_stream_and_wait(), create_dirpath(), DISPOSE, and RETRIEVE.
Referenced by leave_voicemail().
04371 { 04372 int res; 04373 char fn[PATH_MAX]; 04374 char dest[PATH_MAX]; 04375 04376 snprintf(fn, sizeof(fn), "%s%s/%s/greet", VM_SPOOL_DIR, context, ext); 04377 04378 if ((res = create_dirpath(dest, sizeof(dest), context, ext, ""))) { 04379 ast_log(AST_LOG_WARNING, "Failed to make directory(%s)\n", fn); 04380 return -1; 04381 } 04382 04383 RETRIEVE(fn, -1, ext, context); 04384 if (ast_fileexists(fn, NULL, NULL) > 0) { 04385 res = ast_stream_and_wait(chan, fn, ecodes); 04386 if (res) { 04387 DISPOSE(fn, -1); 04388 return res; 04389 } 04390 } else { 04391 /* Dispose just in case */ 04392 DISPOSE(fn, -1); 04393 res = ast_stream_and_wait(chan, "vm-theperson", ecodes); 04394 if (res) 04395 return res; 04396 res = ast_say_digit_str(chan, ext, ecodes, chan->language); 04397 if (res) 04398 return res; 04399 } 04400 res = ast_stream_and_wait(chan, busy ? "vm-isonphone" : "vm-isunavail", ecodes); 04401 return res; 04402 }
| static int is_valid_dtmf | ( | const char * | key | ) | [static] |
Determines if a DTMF key entered is valid.
| key | The character to be compared. expects a single character. Though is capable of handling a string, this is internally copies using ast_strdupa. |
Tests the character entered against the set of valid DTMF characters.
Definition at line 1034 of file app_voicemail.c.
References ast_log(), AST_LOG_WARNING, ast_strdupa, and VALID_DTMF.
Referenced by load_config().
01035 { 01036 int i; 01037 char *local_key = ast_strdupa(key); 01038 01039 for (i = 0; i < strlen(key); ++i) { 01040 if (!strchr(VALID_DTMF, *local_key)) { 01041 ast_log(AST_LOG_WARNING, "Invalid DTMF key \"%c\" used in voicemail configuration file\n", *local_key); 01042 return 0; 01043 } 01044 local_key++; 01045 } 01046 return 1; 01047 }
| static int last_message_index | ( | struct ast_vm_user * | vmu, | |
| char * | dir | |||
| ) | [static] |
Determines the highest message number in use for a given user and mailbox folder.
| vmu | ||
| dir | the folder the mailbox folder to look for messages. Used to construct the SQL where clause. |
This method is used when mailboxes are stored on the filesystem. (not ODBC and not IMAP). Typical use to set the msgnum would be to take the value returned from this method and add one to it.
Definition at line 3438 of file app_voicemail.c.
References map, ast_vm_user::maxmsg, and MAXMSGLIMIT.
Referenced by copy_message(), leave_voicemail(), open_mailbox(), and save_to_folder().
03439 { 03440 int x; 03441 unsigned char map[MAXMSGLIMIT] = ""; 03442 DIR *msgdir; 03443 struct dirent *msgdirent; 03444 int msgdirint; 03445 03446 /* Reading the entire directory into a file map scales better than 03447 * doing a stat repeatedly on a predicted sequence. I suspect this 03448 * is partially due to stat(2) internally doing a readdir(2) itself to 03449 * find each file. */ 03450 msgdir = opendir(dir); 03451 while ((msgdirent = readdir(msgdir))) { 03452 if (sscanf(msgdirent->d_name, "msg%30d", &msgdirint) == 1 && msgdirint < MAXMSGLIMIT) 03453 map[msgdirint] = 1; 03454 } 03455 closedir(msgdir); 03456 03457 for (x = 0; x < vmu->maxmsg; x++) { 03458 if (map[x] == 0) 03459 break; 03460 } 03461 03462 return x - 1; 03463 }
| static int leave_voicemail | ( | struct ast_channel * | chan, | |
| char * | ext, | |||
| struct leave_vm_options * | options | |||
| ) | [static] |
Prompts the user and records a voicemail to a mailbox.
| chan | ||
| ext | ||
| options | OPT_BUSY_GREETING, OPT_UNAVAIL_GREETING |
Definition at line 4879 of file app_voicemail.c.
References ast_callerid_merge(), ast_canmatch_extension(), ast_channel_lock, ast_channel_unlock, ast_check_realtime(), ast_copy_string(), ast_debug, ast_destroy_realtime(), ast_exists_extension(), ast_filedelete(), ast_fileexists(), ast_filerename(), ast_free, ast_log(), AST_LOG_ERROR, AST_LOG_NOTICE, AST_LOG_WARNING, ast_mutex_lock(), ast_mutex_unlock(), ast_play_and_wait(), ast_set_flag, ast_stopstream(), ast_store_realtime(), ast_str_buffer, ast_str_create(), ast_str_set(), ast_strdupa, ast_stream_and_wait(), ast_streamfile(), ast_strlen_zero(), ast_test_flag, ast_unlock_path(), ast_update_realtime(), ast_verbose, ast_waitstream(), ast_channel::cid, ast_callerid::cid_name, ast_callerid::cid_num, ast_channel::context, ast_vm_user::context, copy_message(), count_messages(), create_dirpath(), DISPOSE, errno, ast_vm_user::exit, leave_vm_options::exitcontext, exten, ast_channel::exten, find_user(), free_user(), get_date(), inboxcount(), INTRO, invent_message(), last_message_index(), ast_channel::macrocontext, ast_vm_user::mailbox, make_file(), ast_vm_user::maxmsg, ast_vm_user::maxsecs, vm_state::newmessages, notify_new_message(), OPT_BUSY_GREETING, OPT_DTMFEXIT, OPT_MESSAGE_PRIORITY, OPT_MESSAGE_Urgent, OPT_SILENT, OPT_UNAVAIL_GREETING, option_verbose, pbx_builtin_getvar_helper(), pbx_builtin_setvar_helper(), play_record_review(), ast_channel::priority, leave_vm_options::record_gain, RENAME, RETRIEVE, S_OR, SENTINEL, STORE, strsep(), transfer, VERBOSE_PREFIX_3, vm_lock_path(), VM_OPERATOR, and VOICEMAIL_FILE_MODE.
Referenced by advanced_options(), forward_message(), and vm_exec().
04880 { 04881 #ifdef IMAP_STORAGE 04882 int newmsgs, oldmsgs; 04883 #else 04884 char urgdir[PATH_MAX]; 04885 #endif 04886 char txtfile[PATH_MAX]; 04887 char tmptxtfile[PATH_MAX]; 04888 struct vm_state *vms = NULL; 04889 char callerid[256]; 04890 FILE *txt; 04891 char date[256]; 04892 int txtdes; 04893 int res = 0; 04894 int msgnum; 04895 int duration = 0; 04896 int ausemacro = 0; 04897 int ousemacro = 0; 04898 int ouseexten = 0; 04899 int rtmsgid = 0; 04900 char tmpid[16]; 04901 char tmpdur[16]; 04902 char priority[16]; 04903 char origtime[16]; 04904 char dir[PATH_MAX]; 04905 char tmpdir[PATH_MAX]; 04906 char fn[PATH_MAX]; 04907 char prefile[PATH_MAX] = ""; 04908 char tempfile[PATH_MAX] = ""; 04909 char ext_context[256] = ""; 04910 char fmt[80]; 04911 char *context; 04912 char ecodes[17] = "#"; 04913 struct ast_str *tmp = ast_str_create(16); 04914 char *tmpptr; 04915 struct ast_vm_user *vmu; 04916 struct ast_vm_user svm; 04917 const char *category = NULL; 04918 const char *code; 04919 const char *alldtmf = "0123456789ABCD*#"; 04920 char flag[80]; 04921 04922 ast_str_set(&tmp, 0, "%s", ext); 04923 ext = ast_str_buffer(tmp); 04924 if ((context = strchr(ext, '@'))) { 04925 *context++ = '\0'; 04926 tmpptr = strchr(context, '&'); 04927 } else { 04928 tmpptr = strchr(ext, '&'); 04929 } 04930 04931 if (tmpptr) 04932 *tmpptr++ = '\0'; 04933 04934 ast_channel_lock(chan); 04935 if ((category = pbx_builtin_getvar_helper(chan, "VM_CATEGORY"))) { 04936 category = ast_strdupa(category); 04937 } 04938 ast_channel_unlock(chan); 04939 04940 if (ast_test_flag(options, OPT_MESSAGE_Urgent)) { 04941 ast_copy_string(flag, "Urgent", sizeof(flag)); 04942 } else if (ast_test_flag(options, OPT_MESSAGE_PRIORITY)) { 04943 ast_copy_string(flag, "PRIORITY", sizeof(flag)); 04944 } else { 04945 flag[0] = '\0'; 04946 } 04947 04948 ast_debug(3, "Before find_user\n"); 04949 if (!(vmu = find_user(&svm, context, ext))) { 04950 ast_log(AST_LOG_WARNING, "No entry in voicemail config file for '%s'\n", ext); 04951 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 04952 ast_free(tmp); 04953 return res; 04954 } 04955 /* Setup pre-file if appropriate */ 04956 if (strcmp(vmu->context, "default")) 04957 snprintf(ext_context, sizeof(ext_context), "%s@%s", ext, vmu->context); 04958 else 04959 ast_copy_string(ext_context, vmu->mailbox, sizeof(ext_context)); 04960 04961 /* Set the path to the prefile. Will be one of 04962 VM_SPOOL_DIRcontext/ext/busy 04963 VM_SPOOL_DIRcontext/ext/unavail 04964 Depending on the flag set in options. 04965 */ 04966 if (ast_test_flag(options, OPT_BUSY_GREETING)) { 04967 snprintf(prefile, sizeof(prefile), "%s%s/%s/busy", VM_SPOOL_DIR, vmu->context, ext); 04968 } else if (ast_test_flag(options, OPT_UNAVAIL_GREETING)) { 04969 snprintf(prefile, sizeof(prefile), "%s%s/%s/unavail", VM_SPOOL_DIR, vmu->context, ext); 04970 } 04971 /* Set the path to the tmpfile as 04972 VM_SPOOL_DIR/context/ext/temp 04973 and attempt to create the folder structure. 04974 */ 04975 snprintf(tempfile, sizeof(tempfile), "%s%s/%s/temp", VM_SPOOL_DIR, vmu->context, ext); 04976 if ((res = create_dirpath(tmpdir, sizeof(tmpdir), vmu->context, ext, "tmp"))) { 04977 ast_log(AST_LOG_WARNING, "Failed to make directory (%s)\n", tempfile); 04978 ast_free(tmp); 04979 return -1; 04980 } 04981 RETRIEVE(tempfile, -1, vmu->mailbox, vmu->context); 04982 if (ast_fileexists(tempfile, NULL, NULL) > 0) 04983 ast_copy_string(prefile, tempfile, sizeof(prefile)); 04984 04985 DISPOSE(tempfile, -1); 04986 /* It's easier just to try to make it than to check for its existence */ 04987 create_dirpath(dir, sizeof(dir), vmu->context, ext, "INBOX"); 04988 04989 /* Check current or macro-calling context for special extensions */ 04990 if (ast_test_flag(vmu, VM_OPERATOR)) { 04991 if (!ast_strlen_zero(vmu->exit)) { 04992 if (ast_exists_extension(chan, vmu->exit, "o", 1, chan->cid.cid_num)) { 04993 strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); 04994 ouseexten = 1; 04995 } 04996 } else if (ast_exists_extension(chan, chan->context, "o", 1, chan->cid.cid_num)) { 04997 strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); 04998 ouseexten = 1; 04999 } else if (!ast_strlen_zero(chan->macrocontext) && ast_exists_extension(chan, chan->macrocontext, "o", 1, chan->cid.cid_num)) { 05000 strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); 05001 ousemacro = 1; 05002 } 05003 } 05004 05005 if (!ast_strlen_zero(vmu->exit)) { 05006 if (ast_exists_extension(chan, vmu->exit, "a", 1, chan->cid.cid_num)) 05007 strncat(ecodes, "*", sizeof(ecodes) - strlen(ecodes) - 1); 05008 } else if (ast_exists_extension(chan, chan->context, "a", 1, chan->cid.cid_num)) 05009 strncat(ecodes, "*", sizeof(ecodes) - strlen(ecodes) - 1); 05010 else if (!ast_strlen_zero(chan->macrocontext) && ast_exists_extension(chan, chan->macrocontext, "a", 1, chan->cid.cid_num)) { 05011 strncat(ecodes, "*", sizeof(ecodes) - strlen(ecodes) - 1); 05012 ausemacro = 1; 05013 } 05014 05015 if (ast_test_flag(options, OPT_DTMFEXIT)) { 05016 for (code = alldtmf; *code; code++) { 05017 char e[2] = ""; 05018 e[0] = *code; 05019 if (strchr(ecodes, e[0]) == NULL && ast_canmatch_extension(chan, chan->context, e, 1, chan->cid.cid_num)) 05020 strncat(ecodes, e, sizeof(ecodes) - strlen(ecodes) - 1); 05021 } 05022 } 05023 05024 /* Play the beginning intro if desired */ 05025 if (!ast_strlen_zero(prefile)) { 05026 #ifdef ODBC_STORAGE 05027 int success = 05028 #endif 05029 RETRIEVE(prefile, -1, ext, context); 05030 if (ast_fileexists(prefile, NULL, NULL) > 0) { 05031 if (ast_streamfile(chan, prefile, chan->language) > -1) 05032 res = ast_waitstream(chan, ecodes); 05033 #ifdef ODBC_STORAGE 05034 if (success == -1) { 05035 /* We couldn't retrieve the file from the database, but we found it on the file system. Let's put it in the database. */ 05036 ast_debug(1, "Greeting not retrieved from database, but found in file storage. Inserting into database\n"); 05037 store_file(prefile, vmu->mailbox, vmu->context, -1); 05038 } 05039 #endif 05040 } else { 05041 ast_debug(1, "%s doesn't exist, doing what we can\n", prefile); 05042 res = invent_message(chan, vmu->context, ext, ast_test_flag(options, OPT_BUSY_GREETING), ecodes); 05043 } 05044 DISPOSE(prefile, -1); 05045 if (res < 0) { 05046 ast_debug(1, "Hang up during prefile playback\n"); 05047 free_user(vmu); 05048 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 05049 ast_free(tmp); 05050 return -1; 05051 } 05052 } 05053 if (res == '#') { 05054 /* On a '#' we skip the instructions */ 05055 ast_set_flag(options, OPT_SILENT); 05056 res = 0; 05057 } 05058 if (!res && !ast_test_flag(options, OPT_SILENT)) { 05059 res = ast_stream_and_wait(chan, INTRO, ecodes); 05060 if (res == '#') { 05061 ast_set_flag(options, OPT_SILENT); 05062 res = 0; 05063 } 05064 } 05065 if (res > 0) 05066 ast_stopstream(chan); 05067 /* Check for a '*' here in case the caller wants to escape from voicemail to something 05068 other than the operator -- an automated attendant or mailbox login for example */ 05069 if (res == '*') { 05070 chan->exten[0] = 'a'; 05071 chan->exten[1] = '\0'; 05072 if (!ast_strlen_zero(vmu->exit)) { 05073 ast_copy_string(chan->context, vmu->exit, sizeof(chan->context)); 05074 } else if (ausemacro && !ast_strlen_zero(chan->macrocontext)) { 05075 ast_copy_string(chan->context, chan->macrocontext, sizeof(chan->context)); 05076 } 05077 chan->priority = 0; 05078 free_user(vmu); 05079 pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); 05080 ast_free(tmp); 05081 return 0; 05082 } 05083 05084 /* Check for a '0' here */ 05085 if (ast_test_flag(vmu, VM_OPERATOR) && res == '0') { 05086 transfer: 05087 if (ouseexten || ousemacro) { 05088 chan->exten[0] = 'o'; 05089 chan->exten[1] = '\0'; 05090 if (!ast_strlen_zero(vmu->exit)) { 05091 ast_copy_string(chan->context, vmu->exit, sizeof(chan->context)); 05092 } else if (ousemacro && !ast_strlen_zero(chan->macrocontext)) { 05093 ast_copy_string(chan->context, chan->macrocontext, sizeof(chan->context)); 05094 } 05095 ast_play_and_wait(chan, "transfer"); 05096 chan->priority = 0; 05097 free_user(vmu); 05098 pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); 05099 } 05100 ast_free(tmp); 05101 return 0; 05102 } 05103 05104 /* Allow all other digits to exit Voicemail and return to the dialplan */ 05105 if (ast_test_flag(options, OPT_DTMFEXIT) && res > 0) { 05106 if (!ast_strlen_zero(options->exitcontext)) 05107 ast_copy_string(chan->context, options->exitcontext, sizeof(chan->context)); 05108 free_user(vmu); 05109 pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); 05110 ast_free(tmp); 05111 return res; 05112 } 05113 05114 if (res < 0) { 05115 free_user(vmu); 05116 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 05117 ast_free(tmp); 05118 return -1; 05119 } 05120 /* The meat of recording the message... All the announcements and beeps have been played*/ 05121 ast_copy_string(fmt, vmfmts, sizeof(fmt)); 05122 if (!ast_strlen_zero(fmt)) { 05123 msgnum = 0; 05124 05125 #ifdef IMAP_STORAGE 05126 /* Is ext a mailbox? */ 05127 /* must open stream for this user to get info! */ 05128 res = inboxcount(ext_context, &newmsgs, &oldmsgs); 05129 if (res < 0) { 05130 ast_log(AST_LOG_NOTICE, "Can not leave voicemail, unable to count messages\n"); 05131 ast_free(tmp); 05132 return -1; 05133 } 05134 if (!(vms = get_vm_state_by_mailbox(ext, context, 0))) { 05135 /* It is possible under certain circumstances that inboxcount did not 05136 * create a vm_state when it was needed. This is a catchall which will 05137 * rarely be used. 05138 */ 05139 if (!(vms = create_vm_state_from_user(vmu))) { 05140 ast_log(AST_LOG_ERROR, "Couldn't allocate necessary space\n"); 05141 ast_free(tmp); 05142 return -1; 05143 } 05144 } 05145 vms->newmessages++; 05146 05147 /* here is a big difference! We add one to it later */ 05148 msgnum = newmsgs + oldmsgs; 05149 ast_debug(3, "Messagecount set to %d\n",msgnum); 05150 snprintf(fn, sizeof(fn), "%s/imap/msg%s%04d", VM_SPOOL_DIR, vmu->mailbox, msgnum); 05151 /* set variable for compatibility */ 05152 pbx_builtin_setvar_helper(chan, "VM_MESSAGEFILE", "IMAP_STORAGE"); 05153 05154 /* Check if mailbox is full */ 05155 check_quota(vms, imapfolder); 05156 if (vms->quota_limit && vms->quota_usage >= vms->quota_limit) { 05157 ast_debug(1, "*** QUOTA EXCEEDED!! %u >= %u\n", vms->quota_usage, vms->quota_limit); 05158 ast_play_and_wait(chan, "vm-mailboxfull"); 05159 ast_free(tmp); 05160 return -1; 05161 } 05162 05163 /* Check if we have exceeded maxmsg */ 05164 if (msgnum >= vmu->maxmsg) { 05165 ast_log(AST_LOG_WARNING, "Unable to leave message since we will exceed the maximum number of messages allowed (%u > %u)\n", msgnum, vmu->maxmsg); 05166 ast_play_and_wait(chan, "vm-mailboxfull"); 05167 ast_free(tmp); 05168 return -1; 05169 } 05170 #else 05171 if (count_messages(vmu, dir) >= vmu->maxmsg) { 05172 res = ast_streamfile(chan, "vm-mailboxfull", chan->language); 05173 if (!res) 05174 res = ast_waitstream(chan, ""); 05175 ast_log(AST_LOG_WARNING, "No more messages possible\n"); 05176 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 05177 goto leave_vm_out; 05178 } 05179 05180 #endif 05181 snprintf(tmptxtfile, sizeof(tmptxtfile), "%s/XXXXXX", tmpdir); 05182 txtdes = mkstemp(tmptxtfile); 05183 chmod(tmptxtfile, VOICEMAIL_FILE_MODE & ~my_umask); 05184 if (txtdes < 0) { 05185 res = ast_streamfile(chan, "vm-mailboxfull", chan->language); 05186 if (!res) 05187 res = ast_waitstream(chan, ""); 05188 ast_log(AST_LOG_ERROR, "Unable to create message file: %s\n", strerror(errno)); 05189 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 05190 goto leave_vm_out; 05191 } 05192 05193 /* Now play the beep once we have the message number for our next message. */ 05194 if (res >= 0) { 05195 /* Unless we're *really* silent, try to send the beep */ 05196 res = ast_stream_and_wait(chan, "beep", ""); 05197 } 05198 05199 /* Store information in real-time storage */ 05200 if (ast_check_realtime("voicemail_data")) { 05201 snprintf(priority, sizeof(priority), "%d", chan->priority); 05202 snprintf(origtime, sizeof(origtime), "%ld", (long)time(NULL)); 05203 get_date(date, sizeof(date)); 05204 rtmsgid = ast_store_realtime("voicemail_data", "origmailbox", ext, "context", chan->context, "macrocontext", chan->macrocontext, "exten", chan->exten, "priority", priority, "callerchan", chan->name, "callerid", ast_callerid_merge(callerid, sizeof(callerid), chan->cid.cid_name, chan->cid.cid_num, "Unknown"), "origdate", date, "origtime", origtime, "category", S_OR(category,""), SENTINEL); 05205 } 05206 05207 /* Store information */ 05208 txt = fdopen(txtdes, "w+"); 05209 if (txt) { 05210 get_date(date, sizeof(date)); 05211 fprintf(txt, 05212 ";\n" 05213 "; Message Information file\n" 05214 ";\n" 05215 "[message]\n" 05216 "origmailbox=%s\n" 05217 "context=%s\n" 05218 "macrocontext=%s\n" 05219 "exten=%s\n" 05220 "priority=%d\n" 05221 "callerchan=%s\n" 05222 "callerid=%s\n" 05223 "origdate=%s\n" 05224 "origtime=%ld\n" 05225 "category=%s\n", 05226 ext, 05227 chan->context, 05228 chan->macrocontext, 05229 chan->exten, 05230 chan->priority, 05231 chan->name, 05232 ast_callerid_merge(callerid, sizeof(callerid), S_OR(chan->cid.cid_name, NULL), S_OR(chan->cid.cid_num, NULL), "Unknown"), 05233 date, (long)time(NULL), 05234 category ? category : ""); 05235 } else 05236 ast_log(AST_LOG_WARNING, "Error opening text file for output\n"); 05237 res = play_record_review(chan, NULL, tmptxtfile, vmu->maxsecs, fmt, 1, vmu, &duration, NULL, options->record_gain, vms, flag); 05238 05239 if (txt) { 05240 fprintf(txt, "flag=%s\n", flag); 05241 if (duration < vmminsecs) { 05242 fclose(txt); 05243 if (option_verbose > 2) 05244 ast_verbose( VERBOSE_PREFIX_3 "Recording was %d seconds long but needs to be at least %d - abandoning\n", duration, vmminsecs); 05245 ast_filedelete(tmptxtfile, NULL); 05246 unlink(tmptxtfile); 05247 if (ast_check_realtime("voicemail_data")) { 05248 snprintf(tmpid, sizeof(tmpid), "%d", rtmsgid); 05249 ast_destroy_realtime("voicemail_data", "id", tmpid, SENTINEL); 05250 } 05251 } else { 05252 fprintf(txt, "duration=%d\n", duration); 05253 fclose(txt); 05254 if (vm_lock_path(dir)) { 05255 ast_log(AST_LOG_ERROR, "Couldn't lock directory %s. Voicemail will be lost.\n", dir); 05256 /* Delete files */ 05257 ast_filedelete(tmptxtfile, NULL); 05258 unlink(tmptxtfile); 05259 } else if (ast_fileexists(tmptxtfile, NULL, NULL) <= 0) { 05260 ast_debug(1, "The recorded media file is gone, so we should remove the .txt file too!\n"); 05261 unlink(tmptxtfile); 05262 ast_unlock_path(dir); 05263 if (ast_check_realtime("voicemail_data")) { 05264 snprintf(tmpid, sizeof(tmpid), "%d", rtmsgid); 05265 ast_destroy_realtime("voicemail_data", "id", tmpid, SENTINEL); 05266 } 05267 } else { 05268 #ifndef IMAP_STORAGE 05269 msgnum = last_message_index(vmu, dir) + 1; 05270 #endif 05271 make_file(fn, sizeof(fn), dir, msgnum); 05272 05273 /* assign a variable with the name of the voicemail file */ 05274 #ifndef IMAP_STORAGE 05275 pbx_builtin_setvar_helper(chan, "VM_MESSAGEFILE", fn); 05276 #else 05277 pbx_builtin_setvar_helper(chan, "VM_MESSAGEFILE", "IMAP_STORAGE"); 05278 #endif 05279 05280 snprintf(txtfile, sizeof(txtfile), "%s.txt", fn); 05281 ast_filerename(tmptxtfile, fn, NULL); 05282 rename(tmptxtfile, txtfile); 05283 05284 /* Properly set permissions on voicemail text descriptor file. 05285 Unfortunately mkstemp() makes this file 0600 on most unix systems. */ 05286 if (chmod(txtfile, VOICEMAIL_FILE_MODE) < 0) 05287 ast_log(AST_LOG_ERROR, "Couldn't set permissions on voicemail text file %s: %s", txtfile, strerror(errno)); 05288 05289 ast_unlock_path(dir); 05290 if (ast_check_realtime("voicemail_data")) { 05291 snprintf(tmpid, sizeof(tmpid), "%d", rtmsgid); 05292 snprintf(tmpdur, sizeof(tmpdur), "%d", duration); 05293 ast_update_realtime("voicemail_data", "id", tmpid, "filename", fn, "duration", tmpdur, SENTINEL); 05294 } 05295 /* We must store the file first, before copying the message, because 05296 * ODBC storage does the entire copy with SQL. 05297 */ 05298 if (ast_fileexists(fn, NULL, NULL) > 0) { 05299 STORE(dir, vmu->mailbox, vmu->context, msgnum, chan, vmu, fmt, duration, vms, flag); 05300 } 05301 05302 /* Are there to be more recipients of this message? */ 05303 while (tmpptr) { 05304 struct ast_vm_user recipu, *recip; 05305 char *exten, *cntx; 05306 05307 exten = strsep(&tmpptr, "&"); 05308 cntx = strchr(exten, '@'); 05309 if (cntx) { 05310 *cntx = '\0'; 05311 cntx++; 05312 } 05313 if ((recip = find_user(&recipu, cntx, exten))) { 05314 copy_message(chan, vmu, 0, msgnum, duration, recip, fmt, dir, flag); 05315 free_user(recip); 05316 } 05317 } 05318 #ifndef IMAP_STORAGE 05319 if (!ast_strlen_zero(flag) && !strcmp(flag, "Urgent")) { /* If this is an Urgent message */ 05320 /* Move the message from INBOX to Urgent folder if this is urgent! */ 05321 char sfn[PATH_MAX]; 05322 char dfn[PATH_MAX]; 05323 int x; 05324 /* It's easier just to try to make it than to check for its existence */ 05325 create_dirpath(urgdir, sizeof(urgdir), vmu->context, ext, "Urgent"); 05326 ast_debug(5, "Created an Urgent message, moving file from %s to %s.\n",sfn,dfn); 05327 x = last_message_index(vmu, urgdir) + 1; 05328 make_file(sfn, sizeof(sfn), dir, msgnum); 05329 make_file(dfn, sizeof(dfn), urgdir, x); 05330 RENAME(dir, msgnum, vmu->mailbox, vmu->context, urgdir, x, sfn, dfn); 05331 } 05332 #endif 05333 /* Notification needs to happen after the copy, though. */ 05334 if (ast_fileexists(fn, NULL, NULL)) { 05335 #ifdef IMAP_STORAGE 05336 notify_new_message(chan, vmu, vms, msgnum, duration, fmt, S_OR(chan->cid.cid_num, NULL), S_OR(chan->cid.cid_name, NULL), flag); 05337 #else 05338 notify_new_message(chan, vmu, NULL, msgnum, duration, fmt, S_OR(chan->cid.cid_num, NULL), S_OR(chan->cid.cid_name, NULL), flag); 05339 #endif 05340 } 05341 05342 /* Disposal needs to happen after the optional move and copy */ 05343 if (ast_fileexists(fn, NULL, NULL)) { 05344 DISPOSE(dir, msgnum); 05345 } 05346 } 05347 } 05348 } 05349 if (res == '0') { 05350 goto transfer; 05351 } else if (res > 0) 05352 res = 0; 05353 05354 if (duration < vmminsecs) 05355 /* XXX We should really give a prompt too short/option start again, with leave_vm_out called only after a timeout XXX */ 05356 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 05357 else 05358 pbx_builtin_setvar_helper(chan, "VMSTATUS", "SUCCESS"); 05359 } else 05360 ast_log(AST_LOG_WARNING, "No format for saving voicemail?\n"); 05361 leave_vm_out: 05362 free_user(vmu); 05363 05364 #ifdef IMAP_STORAGE 05365 /* expunge message - use UID Expunge if supported on IMAP server*/ 05366 ast_debug(3, "*** Checking if we can expunge, expungeonhangup set to %d\n",expungeonhangup); 05367 if (expungeonhangup == 1) { 05368 ast_mutex_lock(&vms->lock); 05369 #ifdef HAVE_IMAP_TK2006 05370 if (LEVELUIDPLUS (vms->mailstream)) { 05371 mail_expunge_full(vms->mailstream,NIL,EX_UID); 05372 } else 05373 #endif 05374 mail_expunge(vms->mailstream); 05375 ast_mutex_unlock(&vms->lock); 05376 } 05377 #endif 05378 05379 ast_free(tmp); 05380 return res; 05381 }
| static int load_config | ( | int | reload | ) | [static] |
Definition at line 10281 of file app_voicemail.c.
References adsifdn, adsisec, adsiver, append_mailbox(), apply_options_full(), ast_category_browse(), ast_clear_flag, ast_config_destroy(), ast_config_load, ast_config_option(), ast_copy_string(), ast_debug, ast_dsp_get_threshold_from_settings(), ast_false(), ast_free, AST_LIST_INSERT_HEAD, AST_LIST_LOCK, AST_LIST_UNLOCK, ast_log(), AST_LOG_DEBUG, AST_LOG_ERROR, AST_LOG_WARNING, ast_malloc, AST_PTHREADT_NULL, ast_set2_flag, ast_smdi_interface_find(), ast_strdup, ast_strdupa, ast_strlen_zero(), ast_true(), ast_unload_realtime(), ast_variable_browse(), ast_variable_retrieve(), ASTERISK_USERNAME, callcontext, charset, cidinternalcontexts, CONFIG_FLAG_FILEUNCHANGED, CONFIG_STATUS_FILEUNCHANGED, ast_vm_user::context, DEFAULT_LISTEN_CONTROL_FORWARD_KEY, DEFAULT_LISTEN_CONTROL_PAUSE_KEY, DEFAULT_LISTEN_CONTROL_RESTART_KEY, DEFAULT_LISTEN_CONTROL_REVERSE_KEY, DEFAULT_LISTEN_CONTROL_STOP_KEY, DEFAULT_POLL_FREQ, dialcontext, emailbody, emaildateformat, emailsubject, exitcontext, find_or_create(), free_vm_users(), free_vm_zones(), fromstring, globalflags, is_valid_dtmf(), ast_variable::lineno, listen_control_forward_key, listen_control_pause_key, listen_control_restart_key, listen_control_reverse_key, listen_control_stop_key, MAX_NUM_CID_CONTEXTS, MAXMSG, MAXMSGLIMIT, MINPASSWORD, vm_zone::msg_format, vm_zone::name, ast_variable::name, ast_variable::next, pagerbody, pagerfromstring, pagersubject, populate_defaults(), PWDCHANGE_EXTERNAL, PWDCHANGE_INTERNAL, saydurationminfo, SENDMAIL, start_poll_thread(), stop_poll_thread(), strsep(), substitute_escapes(), THRESHOLD_SILENCE, vm_zone::timezone, ast_variable::value, VM_ATTACH, VM_DIRECFORWARD, VM_ENVELOPE, VM_FORCEGREET, VM_FORCENAME, VM_FWDURGAUTO, vm_invalid_password, VM_MESSAGEWRAP, vm_mismatch, VM_MOVEHEARD, vm_newpassword, VM_OPERATOR, vm_passchanged, vm_password, VM_PBXSKIP, vm_reenterpassword, VM_REVIEW, VM_SAYCID, VM_SAYDURATION, VM_SEARCH, VM_SKIPAFTERCMD, VM_SVMAIL, VM_TEMPGREETWARN, and VOICEMAIL_CONFIG.
Referenced by handle_voicemail_reload(), load_module(), and reload().
10282 { 10283 struct ast_vm_user *current; 10284 struct ast_config *cfg, *ucfg; 10285 char *cat; 10286 struct ast_variable *var; 10287 const char *val; 10288 char *q, *stringp; 10289 int x; 10290 int tmpadsi[4]; 10291 struct ast_flags config_flags = { reload ? CONFIG_FLAG_FILEUNCHANGED : 0 }; 10292 10293 ast_unload_realtime("voicemail"); 10294 ast_unload_realtime("voicemail_data"); 10295 10296 if ((cfg = ast_config_load(VOICEMAIL_CONFIG, config_flags)) == CONFIG_STATUS_FILEUNCHANGED) { 10297 if ((ucfg = ast_config_load("users.conf", config_flags)) == CONFIG_STATUS_FILEUNCHANGED) 10298 return 0; 10299 ast_clear_flag(&config_flags, CONFIG_FLAG_FILEUNCHANGED); 10300 cfg = ast_config_load(VOICEMAIL_CONFIG, config_flags); 10301 } else { 10302 ast_clear_flag(&config_flags, CONFIG_FLAG_FILEUNCHANGED); 10303 ucfg = ast_config_load("users.conf", config_flags); 10304 } 10305 #ifdef IMAP_STORAGE 10306 ast_copy_string(imapparentfolder, "\0", sizeof(imapparentfolder)); 10307 #endif 10308 /* set audio control prompts */ 10309 strcpy(listen_control_forward_key,DEFAULT_LISTEN_CONTROL_FORWARD_KEY); 10310 strcpy(listen_control_reverse_key,DEFAULT_LISTEN_CONTROL_REVERSE_KEY); 10311 strcpy(listen_control_pause_key,DEFAULT_LISTEN_CONTROL_PAUSE_KEY); 10312 strcpy(listen_control_restart_key,DEFAULT_LISTEN_CONTROL_RESTART_KEY); 10313 strcpy(listen_control_stop_key,DEFAULT_LISTEN_CONTROL_STOP_KEY); 10314 10315 /* Free all the users structure */ 10316 free_vm_users(); 10317 10318 /* Free all the zones structure */ 10319 free_vm_zones(); 10320 10321 AST_LIST_LOCK(&users); 10322 10323 memset(ext_pass_cmd, 0, sizeof(ext_pass_cmd)); 10324 memset(ext_pass_check_cmd, 0, sizeof(ext_pass_check_cmd)); 10325 10326 if (cfg) { 10327 /* General settings */ 10328 10329 if (!(val = ast_variable_retrieve(cfg, "general", "userscontext"))) 10330 val = "default"; 10331 ast_copy_string(userscontext, val, sizeof(userscontext)); 10332 /* Attach voice message to mail message ? */ 10333 if (!(val = ast_variable_retrieve(cfg, "general", "attach"))) 10334 val = "yes"; 10335 ast_set2_flag((&globalflags), ast_true(val), VM_ATTACH); 10336 10337 if (!(val = ast_variable_retrieve(cfg, "general", "searchcontexts"))) 10338 val = "no"; 10339 ast_set2_flag((&globalflags), ast_true(val), VM_SEARCH); 10340 10341 volgain = 0.0; 10342 if ((val = ast_variable_retrieve(cfg, "general", "volgain"))) 10343 sscanf(val, "%30lf", &volgain); 10344 10345 #ifdef ODBC_STORAGE 10346 strcpy(odbc_database, "asterisk"); 10347 if ((val = ast_variable_retrieve(cfg, "general", "odbcstorage"))) { 10348 ast_copy_string(odbc_database, val, sizeof(odbc_database)); 10349 } 10350 strcpy(odbc_table, "voicemessages"); 10351 if ((val = ast_variable_retrieve(cfg, "general", "odbctable"))) { 10352 ast_copy_string(odbc_table, val, sizeof(odbc_table)); 10353 } 10354 #endif 10355 /* Mail command */ 10356 strcpy(mailcmd, SENDMAIL); 10357 if ((val = ast_variable_retrieve(cfg, "general", "mailcmd"))) 10358 ast_copy_string(mailcmd, val, sizeof(mailcmd)); /* User setting */ 10359 10360 maxsilence = 0; 10361 if ((val = ast_variable_retrieve(cfg, "general", "maxsilence"))) { 10362 maxsilence = atoi(val); 10363 if (maxsilence > 0) 10364 maxsilence *= 1000; 10365 } 10366 10367 if (!(val = ast_variable_retrieve(cfg, "general", "maxmsg"))) { 10368 maxmsg = MAXMSG; 10369 } else { 10370 maxmsg = atoi(val); 10371 if (maxmsg <= 0) { 10372 ast_log(AST_LOG_WARNING, "Invalid number of messages per folder '%s'. Using default value %i\n", val, MAXMSG); 10373 maxmsg = MAXMSG; 10374 } else if (maxmsg > MAXMSGLIMIT) { 10375 ast_log(AST_LOG_WARNING, "Maximum number of messages per folder is %i. Cannot accept value '%s'\n", MAXMSGLIMIT, val); 10376 maxmsg = MAXMSGLIMIT; 10377 } 10378 } 10379 10380 if (!(val = ast_variable_retrieve(cfg, "general", "backupdeleted"))) { 10381 maxdeletedmsg = 0; 10382 } else { 10383 if (sscanf(val, "%30d", &x) == 1) 10384 maxdeletedmsg = x; 10385 else if (ast_true(val)) 10386 maxdeletedmsg = MAXMSG; 10387 else 10388 maxdeletedmsg = 0; 10389 10390 if (maxdeletedmsg < 0) { 10391 ast_log(AST_LOG_WARNING, "Invalid number of deleted messages saved per mailbox '%s'. Using default value %i\n", val, MAXMSG); 10392 maxdeletedmsg = MAXMSG; 10393 } else if (maxdeletedmsg > MAXMSGLIMIT) { 10394 ast_log(AST_LOG_WARNING, "Maximum number of deleted messages saved per mailbox is %i. Cannot accept value '%s'\n", MAXMSGLIMIT, val); 10395 maxdeletedmsg = MAXMSGLIMIT; 10396 } 10397 } 10398 10399 /* Load date format config for voicemail mail */ 10400 if ((val = ast_variable_retrieve(cfg, "general", "emaildateformat"))) { 10401 ast_copy_string(emaildateformat, val, sizeof(emaildateformat)); 10402 } 10403 10404 /* External password changing command */ 10405 if ((val = ast_variable_retrieve(cfg, "general", "externpass"))) { 10406 ast_copy_string(ext_pass_cmd,val,sizeof(ext_pass_cmd)); 10407 pwdchange = PWDCHANGE_EXTERNAL; 10408 } else if ((val = ast_variable_retrieve(cfg, "general", "externpassnotify"))) { 10409 ast_copy_string(ext_pass_cmd,val,sizeof(ext_pass_cmd)); 10410 pwdchange = PWDCHANGE_EXTERNAL | PWDCHANGE_INTERNAL; 10411 } 10412 10413 /* External password validation command */ 10414 if ((val = ast_variable_retrieve(cfg, "general", "externpasscheck"))) { 10415 ast_copy_string(ext_pass_check_cmd, val, sizeof(ext_pass_check_cmd)); 10416 ast_log(AST_LOG_DEBUG, "found externpasscheck: %s\n", ext_pass_check_cmd); 10417 } 10418 10419 #ifdef IMAP_STORAGE 10420 /* IMAP server address */ 10421 if ((val = ast_variable_retrieve(cfg, "general", "imapserver"))) { 10422 ast_copy_string(imapserver, val, sizeof(imapserver)); 10423 } else { 10424 ast_copy_string(imapserver,"localhost", sizeof(imapserver)); 10425 } 10426 /* IMAP server port */ 10427 if ((val = ast_variable_retrieve(cfg, "general", "imapport"))) { 10428 ast_copy_string(imapport, val, sizeof(imapport)); 10429 } else { 10430 ast_copy_string(imapport,"143", sizeof(imapport)); 10431 } 10432 /* IMAP server flags */ 10433 if ((val = ast_variable_retrieve(cfg, "general", "imapflags"))) { 10434 ast_copy_string(imapflags, val, sizeof(imapflags)); 10435 } 10436 /* IMAP server master username */ 10437 if ((val = ast_variable_retrieve(cfg, "general", "authuser"))) { 10438 ast_copy_string(authuser, val, sizeof(authuser)); 10439 } 10440 /* IMAP server master password */ 10441 if ((val = ast_variable_retrieve(cfg, "general", "authpassword"))) { 10442 ast_copy_string(authpassword, val, sizeof(authpassword)); 10443 } 10444 /* Expunge on exit */ 10445 if ((val = ast_variable_retrieve(cfg, "general", "expungeonhangup"))) { 10446 if (ast_false(val)) 10447 expungeonhangup = 0; 10448 else 10449 expungeonhangup = 1; 10450 } else { 10451 expungeonhangup = 1; 10452 } 10453 /* IMAP voicemail folder */ 10454 if ((val = ast_variable_retrieve(cfg, "general", "imapfolder"))) { 10455 ast_copy_string(imapfolder, val, sizeof(imapfolder)); 10456 } else { 10457 ast_copy_string(imapfolder,"INBOX", sizeof(imapfolder)); 10458 } 10459 if ((val = ast_variable_retrieve(cfg, "general", "imapparentfolder"))) { 10460 ast_copy_string(imapparentfolder, val, sizeof(imapparentfolder)); 10461 } 10462 if ((val = ast_variable_retrieve(cfg, "general", "imapgreetings"))) { 10463 imapgreetings = ast_true(val); 10464 } else { 10465 imapgreetings = 0; 10466 } 10467 if ((val = ast_variable_retrieve(cfg, "general", "greetingfolder"))) { 10468 ast_copy_string(greetingfolder, val, sizeof(greetingfolder)); 10469 } else { 10470 ast_copy_string(greetingfolder, imapfolder, sizeof(greetingfolder)); 10471 } 10472 10473 /* There is some very unorthodox casting done here. This is due 10474 * to the way c-client handles the argument passed in. It expects a 10475 * void pointer and casts the pointer directly to a long without 10476 * first dereferencing it. */ 10477 if ((val = ast_variable_retrieve(cfg, "general", "imapreadtimeout"))) { 10478 mail_parameters(NIL, SET_READTIMEOUT, (void *) (atol(val))); 10479 } else { 10480 mail_parameters(NIL, SET_READTIMEOUT, (void *) 60L); 10481 } 10482 10483 if ((val = ast_variable_retrieve(cfg, "general", "imapwritetimeout"))) { 10484 mail_parameters(NIL, SET_WRITETIMEOUT, (void *) (atol(val))); 10485 } else { 10486 mail_parameters(NIL, SET_WRITETIMEOUT, (void *) 60L); 10487 } 10488 10489 if ((val = ast_variable_retrieve(cfg, "general", "imapopentimeout"))) { 10490 mail_parameters(NIL, SET_OPENTIMEOUT, (void *) (atol(val))); 10491 } else { 10492 mail_parameters(NIL, SET_OPENTIMEOUT, (void *) 60L); 10493 } 10494 10495 if ((val = ast_variable_retrieve(cfg, "general", "imapclosetimeout"))) { 10496 mail_parameters(NIL, SET_CLOSETIMEOUT, (void *) (atol(val))); 10497 } else { 10498 mail_parameters(NIL, SET_CLOSETIMEOUT, (void *) 60L); 10499 } 10500 10501 #endif 10502 /* External voicemail notify application */ 10503 if ((val = ast_variable_retrieve(cfg, "general", "externnotify"))) { 10504 ast_copy_string(externnotify, val, sizeof(externnotify)); 10505 ast_debug(1, "found externnotify: %s\n", externnotify); 10506 } else { 10507 externnotify[0] = '\0'; 10508 } 10509 10510 /* SMDI voicemail notification */ 10511 if ((val = ast_variable_retrieve(cfg, "general", "smdienable")) && ast_true(val)) { 10512 ast_debug(1, "Enabled SMDI voicemail notification\n"); 10513 if ((val = ast_variable_retrieve(cfg, "general", "smdiport"))) { 10514 smdi_iface = ast_smdi_interface_find ? ast_smdi_interface_find(val) : NULL; 10515 } else { 10516 ast_debug(1, "No SMDI interface set, trying default (/dev/ttyS0)\n"); 10517 smdi_iface = ast_smdi_interface_find ? ast_smdi_interface_find("/dev/ttyS0") : NULL; 10518 } 10519 if (!smdi_iface) { 10520 ast_log(AST_LOG_ERROR, "No valid SMDI interface specfied, disabling SMDI voicemail notification\n"); 10521 } 10522 } 10523 10524 /* Silence treshold */ 10525 silencethreshold = ast_dsp_get_threshold_from_settings(THRESHOLD_SILENCE); 10526 if ((val = ast_variable_retrieve(cfg, "general", "silencethreshold"))) 10527 silencethreshold = atoi(val); 10528 10529 if (!(val = ast_variable_retrieve(cfg, "general", "serveremail"))) 10530 val = ASTERISK_USERNAME; 10531 ast_copy_string(serveremail, val, sizeof(serveremail)); 10532 10533 vmmaxsecs = 0; 10534 if ((val = ast_variable_retrieve(cfg, "general", "maxsecs"))) { 10535 if (sscanf(val, "%30d", &x) == 1) { 10536 vmmaxsecs = x; 10537 } else { 10538 ast_log(AST_LOG_WARNING, "Invalid max message time length\n"); 10539 } 10540 } else if ((val = ast_variable_retrieve(cfg, "general", "maxmessage"))) { 10541 static int maxmessage_deprecate = 0; 10542 if (maxmessage_deprecate == 0) { 10543 maxmessage_deprecate = 1; 10544 ast_log(AST_LOG_WARNING, "Setting 'maxmessage' has been deprecated in favor of 'maxsecs'.\n"); 10545 } 10546 if (sscanf(val, "%30d", &x) == 1) { 10547 vmmaxsecs = x; 10548 } else { 10549 ast_log(AST_LOG_WARNING, "Invalid max message time length\n"); 10550 } 10551 } 10552 10553 vmminsecs = 0; 10554 if ((val = ast_variable_retrieve(cfg, "general", "minsecs"))) { 10555 if (sscanf(val, "%30d", &x) == 1) { 10556 vmminsecs = x; 10557 if (maxsilence / 1000 >= vmminsecs) { 10558 ast_log(AST_LOG_WARNING, "maxsilence should be less than minmessage or you may get empty messages\n"); 10559 } 10560 } else { 10561 ast_log(AST_LOG_WARNING, "Invalid min message time length\n"); 10562 } 10563 } else if ((val = ast_variable_retrieve(cfg, "general", "minmessage"))) { 10564 static int maxmessage_deprecate = 0; 10565 if (maxmessage_deprecate == 0) { 10566 maxmessage_deprecate = 1; 10567 ast_log(AST_LOG_WARNING, "Setting 'minmessage' has been deprecated in favor of 'minsecs'.\n"); 10568 } 10569 if (sscanf(val, "%30d", &x) == 1) { 10570 vmminsecs = x; 10571 if (maxsilence / 1000 >= vmminsecs) { 10572 ast_log(AST_LOG_WARNING, "maxsilence should be less than minmessage or you may get empty messages\n"); 10573 } 10574 } else { 10575 ast_log(AST_LOG_WARNING, "Invalid min message time length\n"); 10576 } 10577 } 10578 10579 val = ast_variable_retrieve(cfg, "general", "format"); 10580 if (!val) 10581 val = "wav"; 10582 ast_copy_string(vmfmts, val, sizeof(vmfmts)); 10583 10584 skipms = 3000; 10585 if ((val = ast_variable_retrieve(cfg, "general", "maxgreet"))) { 10586 if (sscanf(val, "%30d", &x) == 1) { 10587 maxgreet = x; 10588 } else { 10589 ast_log(AST_LOG_WARNING, "Invalid max message greeting length\n"); 10590 } 10591 } 10592 10593 if ((val = ast_variable_retrieve(cfg, "general", "skipms"))) { 10594 if (sscanf(val, "%30d", &x) == 1) { 10595 skipms = x; 10596 } else { 10597 ast_log(AST_LOG_WARNING, "Invalid skipms value\n"); 10598 } 10599 } 10600 10601 maxlogins = 3; 10602 if ((val = ast_variable_retrieve(cfg, "general", "maxlogins"))) { 10603 if (sscanf(val, "%30d", &x) == 1) { 10604 maxlogins = x; 10605 } else { 10606 ast_log(AST_LOG_WARNING, "Invalid max failed login attempts\n"); 10607 } 10608 } 10609 10610 minpassword = MINPASSWORD; 10611 if ((val = ast_variable_retrieve(cfg, "general", "minpassword"))) { 10612 if (sscanf(val, "%30d", &x) == 1) { 10613 minpassword = x; 10614 } else { 10615 ast_log(AST_LOG_WARNING, "Invalid minimum password length. Default to %d\n", minpassword); 10616 } 10617 } 10618 10619 /* Force new user to record name ? */ 10620 if (!(val = ast_variable_retrieve(cfg, "general", "forcename"))) 10621 val = "no"; 10622 ast_set2_flag((&globalflags), ast_true(val), VM_FORCENAME); 10623 10624 /* Force new user to record greetings ? */ 10625 if (!(val = ast_variable_retrieve(cfg, "general", "forcegreetings"))) 10626 val = "no"; 10627 ast_set2_flag((&globalflags), ast_true(val), VM_FORCEGREET); 10628 10629 if ((val = ast_variable_retrieve(cfg, "general", "cidinternalcontexts"))) { 10630 ast_debug(1, "VM_CID Internal context string: %s\n", val); 10631 stringp = ast_strdupa(val); 10632 for (x = 0 ; x < MAX_NUM_CID_CONTEXTS ; x++){ 10633 if (!ast_strlen_zero(stringp)) { 10634 q = strsep(&stringp, ","); 10635 while ((*q == ' ')||(*q == '\t')) /* Eat white space between contexts */ 10636 q++; 10637 ast_copy_string(cidinternalcontexts[x], q, sizeof(cidinternalcontexts[x])); 10638 ast_debug(1,"VM_CID Internal context %d: %s\n", x, cidinternalcontexts[x]); 10639 } else { 10640 cidinternalcontexts[x][0] = '\0'; 10641 } 10642 } 10643 } 10644 if (!(val = ast_variable_retrieve(cfg, "general", "review"))){ 10645 ast_debug(1,"VM Review Option disabled globally\n"); 10646 val = "no"; 10647 } 10648 ast_set2_flag((&globalflags), ast_true(val), VM_REVIEW); 10649 10650 /* Temporary greeting reminder */ 10651 if (!(val = ast_variable_retrieve(cfg, "general", "tempgreetwarn"))) { 10652 ast_debug(1, "VM Temporary Greeting Reminder Option disabled globally\n"); 10653 val = "no"; 10654 } else { 10655 ast_debug(1, "VM Temporary Greeting Reminder Option enabled globally\n"); 10656 } 10657 ast_set2_flag((&globalflags), ast_true(val), VM_TEMPGREETWARN); 10658 if (!(val = ast_variable_retrieve(cfg, "general", "messagewrap"))){ 10659 ast_debug(1, "VM next message wrap disabled globally\n"); 10660 val = "no"; 10661 } 10662 ast_set2_flag((&globalflags), ast_true(val), VM_MESSAGEWRAP); 10663 10664 if (!(val = ast_variable_retrieve(cfg, "general", "operator"))){ 10665 ast_debug(1,"VM Operator break disabled globally\n"); 10666 val = "no"; 10667 } 10668 ast_set2_flag((&globalflags), ast_true(val), VM_OPERATOR); 10669 10670 if (!(val = ast_variable_retrieve(cfg, "general", "saycid"))) { 10671 ast_debug(1,"VM CID Info before msg disabled globally\n"); 10672 val = "no"; 10673 } 10674 ast_set2_flag((&globalflags), ast_true(val), VM_SAYCID); 10675 10676 if (!(val = ast_variable_retrieve(cfg,"general", "sendvoicemail"))){ 10677 ast_debug(1,"Send Voicemail msg disabled globally\n"); 10678 val = "no"; 10679 } 10680 ast_set2_flag((&globalflags), ast_true(val), VM_SVMAIL); 10681 10682 if (!(val = ast_variable_retrieve(cfg, "general", "envelope"))) { 10683 ast_debug(1,"ENVELOPE before msg enabled globally\n"); 10684 val = "yes"; 10685 } 10686 ast_set2_flag((&globalflags), ast_true(val), VM_ENVELOPE); 10687 10688 if (!(val = ast_variable_retrieve(cfg, "general", "moveheard"))) { 10689 ast_debug(1,"Move Heard enabled globally\n"); 10690 val = "yes"; 10691 } 10692 ast_set2_flag((&globalflags), ast_true(val), VM_MOVEHEARD); 10693 10694 if (!(val = ast_variable_retrieve(cfg, "general", "forward_urgent_auto"))) { 10695 ast_debug(1,"Autoset of Urgent flag on forwarded Urgent messages disabled globally\n"); 10696 val = "no"; 10697 } 10698 ast_set2_flag((&globalflags), ast_true(val), VM_FWDURGAUTO); 10699 10700 if (!(val = ast_variable_retrieve(cfg, "general", "sayduration"))) { 10701 ast_debug(1,"Duration info before msg enabled globally\n"); 10702 val = "yes"; 10703 } 10704 ast_set2_flag((&globalflags), ast_true(val), VM_SAYDURATION); 10705 10706 saydurationminfo = 2; 10707 if ((val = ast_variable_retrieve(cfg, "general", "saydurationm"))) { 10708 if (sscanf(val, "%30d", &x) == 1) { 10709 saydurationminfo = x; 10710 } else { 10711 ast_log(AST_LOG_WARNING, "Invalid min duration for say duration\n"); 10712 } 10713 } 10714 10715 if (!(val = ast_variable_retrieve(cfg, "general", "nextaftercmd"))) { 10716 ast_debug(1,"We are not going to skip to the next msg after save/delete\n"); 10717 val = "no"; 10718 } 10719 ast_set2_flag((&globalflags), ast_true(val), VM_SKIPAFTERCMD); 10720 10721 if ((val = ast_variable_retrieve(cfg, "general", "dialout"))) { 10722 ast_copy_string(dialcontext, val, sizeof(dialcontext)); 10723 ast_debug(1, "found dialout context: %s\n", dialcontext); 10724 } else { 10725 dialcontext[0] = '\0'; 10726 } 10727 10728 if ((val = ast_variable_retrieve(cfg, "general", "callback"))) { 10729 ast_copy_string(callcontext, val, sizeof(callcontext)); 10730 ast_debug(1, "found callback context: %s\n", callcontext); 10731 } else { 10732 callcontext[0] = '\0'; 10733 } 10734 10735 if ((val = ast_variable_retrieve(cfg, "general", "exitcontext"))) { 10736 ast_copy_string(exitcontext, val, sizeof(exitcontext)); 10737 ast_debug(1, "found operator context: %s\n", exitcontext); 10738 } else { 10739 exitcontext[0] = '\0'; 10740 } 10741 10742 /* load password sounds configuration */ 10743 if ((val = ast_variable_retrieve(cfg, "general", "vm-password"))) 10744 ast_copy_string(vm_password, val, sizeof(vm_password)); 10745 if ((val = ast_variable_retrieve(cfg, "general", "vm-newpassword"))) 10746 ast_copy_string(vm_newpassword, val, sizeof(vm_newpassword)); 10747 if ((val = ast_variable_retrieve(cfg, "general", "vm-invalid-password"))) 10748 ast_copy_string(vm_invalid_password, val, sizeof(vm_invalid_password)); 10749 if ((val = ast_variable_retrieve(cfg, "general", "vm-passchanged"))) 10750 ast_copy_string(vm_passchanged, val, sizeof(vm_passchanged)); 10751 if ((val = ast_variable_retrieve(cfg, "general", "vm-reenterpassword"))) 10752 ast_copy_string(vm_reenterpassword, val, sizeof(vm_reenterpassword)); 10753 if ((val = ast_variable_retrieve(cfg, "general", "vm-mismatch"))) 10754 ast_copy_string(vm_mismatch, val, sizeof(vm_mismatch)); 10755 /* load configurable audio prompts */ 10756 if ((val = ast_variable_retrieve(cfg, "general", "listen-control-forward-key")) && is_valid_dtmf(val)) 10757 ast_copy_string(listen_control_forward_key, val, sizeof(listen_control_forward_key)); 10758 if ((val = ast_variable_retrieve(cfg, "general", "listen-control-reverse-key")) && is_valid_dtmf(val)) 10759 ast_copy_string(listen_control_reverse_key, val, sizeof(listen_control_reverse_key)); 10760 if ((val = ast_variable_retrieve(cfg, "general", "listen-control-pause-key")) && is_valid_dtmf(val)) 10761 ast_copy_string(listen_control_pause_key, val, sizeof(listen_control_pause_key)); 10762 if ((val = ast_variable_retrieve(cfg, "general", "listen-control-restart-key")) && is_valid_dtmf(val)) 10763 ast_copy_string(listen_control_restart_key, val, sizeof(listen_control_restart_key)); 10764 if ((val = ast_variable_retrieve(cfg, "general", "listen-control-stop-key")) && is_valid_dtmf(val)) 10765 ast_copy_string(listen_control_stop_key, val, sizeof(listen_control_stop_key)); 10766 10767 if (!(val = ast_variable_retrieve(cfg, "general", "usedirectory"))) 10768 val = "no"; 10769 ast_set2_flag((&globalflags), ast_true(val), VM_DIRECFORWARD); 10770 10771 poll_freq = DEFAULT_POLL_FREQ; 10772 if ((val = ast_variable_retrieve(cfg, "general", "pollfreq"))) { 10773 if (sscanf(val, "%30u", &poll_freq) != 1) { 10774 poll_freq = DEFAULT_POLL_FREQ; 10775 ast_log(AST_LOG_ERROR, "'%s' is not a valid value for the pollfreq option!\n", val); 10776 } 10777 } 10778 10779 poll_mailboxes = 0; 10780 if ((val = ast_variable_retrieve(cfg, "general", "pollmailboxes"))) 10781 poll_mailboxes = ast_true(val); 10782 10783 if (ucfg) { 10784 for (cat = ast_category_browse(ucfg, NULL); cat ; cat = ast_category_browse(ucfg, cat)) { 10785 if (!ast_true(ast_config_option(ucfg, cat, "hasvoicemail"))) 10786 continue; 10787 if ((current = find_or_create(userscontext, cat))) { 10788 populate_defaults(current); 10789 apply_options_full(current, ast_variable_browse(ucfg, cat)); 10790 ast_copy_string(current->context, userscontext, sizeof(current->context)); 10791 } 10792 } 10793 ast_config_destroy(ucfg); 10794 } 10795 cat = ast_category_browse(cfg, NULL); 10796 while (cat) { 10797 if (strcasecmp(cat, "general")) { 10798 var = ast_variable_browse(cfg, cat); 10799 if (strcasecmp(cat, "zonemessages")) { 10800 /* Process mailboxes in this context */ 10801 while (var) { 10802 append_mailbox(cat, var->name, var->value); 10803 var = var->next; 10804 } 10805 } else { 10806 /* Timezones in this context */ 10807 while (var) { 10808 struct vm_zone *z; 10809 if ((z = ast_malloc(sizeof(*z)))) { 10810 char *msg_format, *tzone; 10811 msg_format = ast_strdupa(var->value); 10812 tzone = strsep(&msg_format, "|"); 10813 if (msg_format) { 10814 ast_copy_string(z->name, var->name, sizeof(z->name)); 10815 ast_copy_string(z->timezone, tzone, sizeof(z->timezone)); 10816 ast_copy_string(z->msg_format, msg_format, sizeof(z->msg_format)); 10817 AST_LIST_LOCK(&zones); 10818 AST_LIST_INSERT_HEAD(&zones, z, list); 10819 AST_LIST_UNLOCK(&zones); 10820 } else { 10821 ast_log(AST_LOG_WARNING, "Invalid timezone definition at line %d\n", var->lineno); 10822 ast_free(z); 10823 } 10824 } else { 10825 AST_LIST_UNLOCK(&users); 10826 ast_config_destroy(cfg); 10827 return -1; 10828 } 10829 var = var->next; 10830 } 10831 } 10832 } 10833 cat = ast_category_browse(cfg, cat); 10834 } 10835 memset(fromstring, 0, sizeof(fromstring)); 10836 memset(pagerfromstring, 0, sizeof(pagerfromstring)); 10837 strcpy(charset, "ISO-8859-1"); 10838 if (emailbody) { 10839 ast_free(emailbody); 10840 emailbody = NULL; 10841 } 10842 if (emailsubject) { 10843 ast_free(emailsubject); 10844 emailsubject = NULL; 10845 } 10846 if (pagerbody) { 10847 ast_free(pagerbody); 10848 pagerbody = NULL; 10849 } 10850 if (pagersubject) { 10851 ast_free(pagersubject); 10852 pagersubject = NULL; 10853 } 10854 if ((val = ast_variable_retrieve(cfg, "general", "pbxskip"))) 10855 ast_set2_flag((&globalflags), ast_true(val), VM_PBXSKIP); 10856 if ((val = ast_variable_retrieve(cfg, "general", "fromstring"))) 10857 ast_copy_string(fromstring, val, sizeof(fromstring)); 10858 if ((val = ast_variable_retrieve(cfg, "general", "pagerfromstring"))) 10859 ast_copy_string(pagerfromstring, val, sizeof(pagerfromstring)); 10860 if ((val = ast_variable_retrieve(cfg, "general", "charset"))) 10861 ast_copy_string(charset, val, sizeof(charset)); 10862 if ((val = ast_variable_retrieve(cfg, "general", "adsifdn"))) { 10863 sscanf(val, "%2x%2x%2x%2x", &tmpadsi[0], &tmpadsi[1], &tmpadsi[2], &tmpadsi[3]); 10864 for (x = 0; x < 4; x++) { 10865 memcpy(&adsifdn[x], &tmpadsi[x], 1); 10866 } 10867 } 10868 if ((val = ast_variable_retrieve(cfg, "general", "adsisec"))) { 10869 sscanf(val, "%2x%2x%2x%2x", &tmpadsi[0], &tmpadsi[1], &tmpadsi[2], &tmpadsi[3]); 10870 for (x = 0; x < 4; x++) { 10871 memcpy(&adsisec[x], &tmpadsi[x], 1); 10872 } 10873 } 10874 if ((val = ast_variable_retrieve(cfg, "general", "adsiver"))) { 10875 if (atoi(val)) { 10876 adsiver = atoi(val); 10877 } 10878 } 10879 if ((val = ast_variable_retrieve(cfg, "general", "tz"))) { 10880 ast_copy_string(zonetag, val, sizeof(zonetag)); 10881 } 10882 if ((val = ast_variable_retrieve(cfg, "general", "emailsubject"))) { 10883 emailsubject = ast_strdup(val); 10884 } 10885 if ((val = ast_variable_retrieve(cfg, "general", "emailbody"))) { 10886 emailbody = substitute_escapes(val); 10887 } 10888 if ((val = ast_variable_retrieve(cfg, "general", "pagersubject"))) { 10889 pagersubject = ast_strdup(val); 10890 } 10891 if ((val = ast_variable_retrieve(cfg, "general", "pagerbody"))) { 10892 pagerbody = substitute_escapes(val); 10893 } 10894 AST_LIST_UNLOCK(&users); 10895 ast_config_destroy(cfg); 10896 10897 if (poll_mailboxes && poll_thread == AST_PTHREADT_NULL) 10898 start_poll_thread(); 10899 if (!poll_mailboxes && poll_thread != AST_PTHREADT_NULL) 10900 stop_poll_thread();; 10901 10902 return 0; 10903 } else { 10904 AST_LIST_UNLOCK(&users); 10905 ast_log(AST_LOG_WARNING, "Failed to load configuration file.\n"); 10906 if (ucfg) 10907 ast_config_destroy(ucfg); 10908 return 0; 10909 } 10910 }
| static int load_module | ( | void | ) | [static] |
Definition at line 10956 of file app_voicemail.c.
References ast_cli_register_multiple(), ast_config_AST_SPOOL_DIR, ast_custom_function_register, ast_install_vm_functions(), ast_log(), AST_LOG_WARNING, ast_manager_register, ast_realtime_require_field(), ast_register_application, ast_taskprocessor_get(), cli_voicemail, EVENT_FLAG_CALL, EVENT_FLAG_REPORTING, has_voicemail(), inboxcount(), inboxcount2(), load_config(), mailbox_exists_acf, manager_list_voicemail_users(), messagecount(), mwi_subscription_tps, RQ_CHAR, RQ_UINTEGER3, sayname(), SENTINEL, vm_box_exists(), vm_exec(), vm_execmain(), and vmauthenticate().
10957 { 10958 int res; 10959 my_umask = umask(0); 10960 umask(my_umask); 10961 10962 /* compute the location of the voicemail spool directory */ 10963 snprintf(VM_SPOOL_DIR, sizeof(VM_SPOOL_DIR), "%s/voicemail/", ast_config_AST_SPOOL_DIR); 10964 10965 if (!(mwi_subscription_tps = ast_taskprocessor_get("app_voicemail", 0))) { 10966 ast_log(AST_LOG_WARNING, "failed to reference mwi subscription taskprocessor. MWI will not work\n"); 10967 } 10968 10969 if ((res = load_config(0))) 10970 return res; 10971 10972 res = ast_register_application(app, vm_exec, synopsis_vm, descrip_vm); 10973 res |= ast_register_application(app2, vm_execmain, synopsis_vmain, descrip_vmain); 10974 res |= ast_register_application(app3, vm_box_exists, synopsis_vm_box_exists, descrip_vm_box_exists); 10975 res |= ast_register_application(app4, vmauthenticate, synopsis_vmauthenticate, descrip_vmauthenticate); 10976 res |= ast_custom_function_register(&mailbox_exists_acf); 10977 res |= ast_manager_register("VoicemailUsersList", EVENT_FLAG_CALL | EVENT_FLAG_REPORTING, manager_list_voicemail_users, "List All Voicemail User Information"); 10978 if (res) 10979 return res; 10980 10981 ast_cli_register_multiple(cli_voicemail, sizeof(cli_voicemail) / sizeof(struct ast_cli_entry)); 10982 10983 ast_install_vm_functions(has_voicemail, inboxcount, inboxcount2, messagecount, sayname); 10984 ast_realtime_require_field("voicemail", "uniqueid", RQ_UINTEGER3, 11, "password", RQ_CHAR, 10, SENTINEL); 10985 ast_realtime_require_field("voicemail_data", "filename", RQ_CHAR, 30, "duration", RQ_UINTEGER3, 5, SENTINEL); 10986 10987 return res; 10988 }
| static int make_dir | ( | char * | dest, | |
| int | len, | |||
| const char * | context, | |||
| const char * | ext, | |||
| const char * | folder | |||
| ) | [static] |
Creates a file system path expression for a folder within the voicemail data folder and the appropriate context.
| dest | The variable to hold the output generated path expression. This buffer should be of size PATH_MAX. | |
| len | The length of the path string that was written out. |
The path is constructed as VM_SPOOL_DIRcontext/ext/folder
Definition at line 1251 of file app_voicemail.c.
Referenced by copy_message(), create_dirpath(), make_email_file(), manager_list_voicemail_users(), notify_new_message(), and prep_email_sub_vars().
01252 { 01253 return snprintf(dest, len, "%s%s/%s/%s", VM_SPOOL_DIR, context, ext, folder); 01254 }
| static void make_email_file | ( | FILE * | p, | |
| char * | srcemail, | |||
| struct ast_vm_user * | vmu, | |||
| int | msgnum, | |||
| char * | context, | |||
| char * | mailbox, | |||
| const char * | fromfolder, | |||
| char * | cidnum, | |||
| char * | cidname, | |||
| char * | attach, | |||
| char * | attach2, | |||
| char * | format, | |||
| int | duration, | |||
| int | attach_user_voicemail, | |||
| struct ast_channel * | chan, | |||
| const char * | category, | |||
| int | imap, | |||
| const char * | flag | |||
| ) | [static] |
Creates the email file to be sent to indicate a new voicemail exists for a user.
| p | The output file to generate the email contents into. | |
| srcemail | The email address to send the email to, presumably the email address for the owner of the mailbox. | |
| vmu | The voicemail user who is sending the voicemail. | |
| msgnum | The message index in the mailbox folder. | |
| context | ||
| mailbox | The voicemail box to read the voicemail to be notified in this email. | |
| cidnum | The caller ID number. | |
| cidname | The caller ID name. | |
| attach | the name of the sound file to be attached to the email, if attach_user_voicemail == 1. | |
| format | The message sound file format. i.e. .wav | |
| duration | The time of the message content, in seconds. | |
| attach_user_voicemail | if 1, the sound file is attached to the email. | |
| chan | ||
| category | ||
| imap | if == 1, indicates the target folder for the email notification to be sent to will be an IMAP mailstore. This causes additional mailbox headers to be set, which would facilitate searching for the email in the destination IMAP folder. |
The email body, and base 64 encoded attachement (if any) are stored to the file identified by *p. This method does not actually send the email. That is done by invoking the configure 'mailcmd' and piping this generated file into it, or with the sendemail() function.
Definition at line 3917 of file app_voicemail.c.
References add_email_attachment(), ast_channel_alloc, ast_channel_free(), ast_config_destroy(), ast_config_load, ast_copy_string(), ast_debug, ast_localtime(), ast_log(), AST_LOG_WARNING, ast_random(), AST_STATE_DOWN, ast_strdupa, ast_strftime(), ast_strlen_zero(), ast_test_flag, ast_variable_retrieve(), charset, check_mime(), CONFIG_FLAG_NOCACHE, ast_vm_user::context, ast_vm_user::email, emailbody, emaildateformat, emailsubject, encode_mime_str(), ENDL, fromstring, ast_vm_user::fullname, globalflags, ast_vm_user::mailbox, make_dir(), make_file(), MAXHOSTNAMELEN, pbx_substitute_variables_helper(), prep_email_sub_vars(), ast_channel::priority, quote(), strip_control(), VM_PBXSKIP, and vmu_tm().
Referenced by sendmail().
03918 { 03919 char date[256]; 03920 char host[MAXHOSTNAMELEN] = ""; 03921 char who[256]; 03922 char bound[256]; 03923 char dur[256]; 03924 struct ast_tm tm; 03925 char enc_cidnum[256] = "", enc_cidname[256] = ""; 03926 char *passdata = NULL, *passdata2; 03927 size_t len_passdata = 0, len_passdata2, tmplen; 03928 char *greeting_attachment; 03929 char filename[256]; 03930 03931 #ifdef IMAP_STORAGE 03932 #define ENDL "\r\n" 03933 #else 03934 #define ENDL "\n" 03935 #endif 03936 03937 /* One alloca for multiple fields */ 03938 len_passdata2 = strlen(vmu->fullname); 03939 if (emailsubject && (tmplen = strlen(emailsubject)) > len_passdata2) { 03940 len_passdata2 = tmplen; 03941 } 03942 if ((tmplen = strlen(fromstring)) > len_passdata2) { 03943 len_passdata2 = tmplen; 03944 } 03945 len_passdata2 = len_passdata2 * 3 + 200; 03946 passdata2 = alloca(len_passdata2); 03947 03948 if (cidnum) { 03949 strip_control(cidnum, enc_cidnum, sizeof(enc_cidnum)); 03950 } 03951 if (cidname) { 03952 strip_control(cidname, enc_cidname, sizeof(enc_cidname)); 03953 } 03954 gethostname(host, sizeof(host) - 1); 03955 03956 if (strchr(srcemail, '@')) 03957 ast_copy_string(who, srcemail, sizeof(who)); 03958 else 03959 snprintf(who, sizeof(who), "%s@%s", srcemail, host); 03960 03961 greeting_attachment = strrchr(ast_strdupa(attach), '/'); 03962 if (greeting_attachment) 03963 *greeting_attachment++ = '\0'; 03964 03965 snprintf(dur, sizeof(dur), "%d:%02d", duration / 60, duration % 60); 03966 ast_strftime(date, sizeof(date), "%a, %d %b %Y %H:%M:%S %z", vmu_tm(vmu, &tm)); 03967 fprintf(p, "Date: %s" ENDL, date); 03968 03969 /* Set date format for voicemail mail */ 03970 ast_strftime(date, sizeof(date), emaildateformat, &tm); 03971 03972 if (!ast_strlen_zero(fromstring)) { 03973 struct ast_channel *ast; 03974 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 03975 char *ptr; 03976 memset(passdata2, 0, len_passdata2); 03977 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, enc_cidnum, enc_cidname, dur, date, passdata2, len_passdata2, category, flag); 03978 pbx_substitute_variables_helper(ast, fromstring, passdata2, len_passdata2); 03979 len_passdata = strlen(passdata2) * 3 + 300; 03980 passdata = alloca(len_passdata); 03981 if (check_mime(passdata2)) { 03982 int first_line = 1; 03983 encode_mime_str(passdata2, passdata, len_passdata, strlen("From: "), strlen(who) + 3); 03984 while ((ptr = strchr(passdata, ' '))) { 03985 *ptr = '\0'; 03986 fprintf(p, "%s %s" ENDL, first_line ? "From:" : "", passdata); 03987 first_line = 0; 03988 passdata = ptr + 1; 03989 } 03990 fprintf(p, "%s %s <%s>" ENDL, first_line ? "From:" : "", passdata, who); 03991 } else { 03992 fprintf(p, "From: %s <%s>" ENDL, quote(passdata2, passdata, len_passdata), who); 03993 } 03994 ast_channel_free(ast); 03995 } else { 03996 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 03997 } 03998 } else { 03999 fprintf(p, "From: Asterisk PBX <%s>" ENDL, who); 04000 } 04001 04002 if (check_mime(vmu->fullname)) { 04003 int first_line = 1; 04004 char *ptr; 04005 encode_mime_str(vmu->fullname, passdata2, len_passdata2, strlen("To: "), strlen(vmu->email) + 3); 04006 while ((ptr = strchr(passdata2, ' '))) { 04007 *ptr = '\0'; 04008 fprintf(p, "%s %s" ENDL, first_line ? "To:" : "", passdata2); 04009 first_line = 0; 04010 passdata2 = ptr + 1; 04011 } 04012 fprintf(p, "%s %s <%s>" ENDL, first_line ? "To:" : "", passdata2, vmu->email); 04013 } else { 04014 fprintf(p, "To: %s <%s>" ENDL, quote(vmu->fullname, passdata2, len_passdata2), vmu->email); 04015 } 04016 if (!ast_strlen_zero(emailsubject)) { 04017 struct ast_channel *ast; 04018 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 04019 int vmlen = strlen(emailsubject) * 3 + 200; 04020 /* Only allocate more space if the previous was not large enough */ 04021 if (vmlen > len_passdata) { 04022 passdata = alloca(vmlen); 04023 len_passdata = vmlen; 04024 } 04025 04026 memset(passdata, 0, len_passdata); 04027 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, cidnum, cidname, dur, date, passdata, len_passdata, category, flag); 04028 pbx_substitute_variables_helper(ast, emailsubject, passdata, len_passdata); 04029 if (check_mime(passdata)) { 04030 int first_line = 1; 04031 char *ptr; 04032 encode_mime_str(passdata, passdata2, len_passdata2, strlen("Subject: "), 0); 04033 while ((ptr = strchr(passdata2, ' '))) { 04034 *ptr = '\0'; 04035 fprintf(p, "%s %s" ENDL, first_line ? "Subject:" : "", passdata2); 04036 first_line = 0; 04037 passdata2 = ptr + 1; 04038 } 04039 fprintf(p, "%s %s" ENDL, first_line ? "Subject:" : "", passdata2); 04040 } else { 04041 fprintf(p, "Subject: %s" ENDL, passdata); 04042 } 04043 ast_channel_free(ast); 04044 } else { 04045 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 04046 } 04047 } else if (ast_test_flag((&globalflags), VM_PBXSKIP)) { 04048 if (ast_strlen_zero(flag)) { 04049 fprintf(p, "Subject: New message %d in mailbox %s" ENDL, msgnum + 1, mailbox); 04050 } else { 04051 fprintf(p, "Subject: New %s message %d in mailbox %s" ENDL, flag, msgnum + 1, mailbox); 04052 } 04053 } else { 04054 if (ast_strlen_zero(flag)) { 04055 fprintf(p, "Subject: [PBX]: New message %d in mailbox %s" ENDL, msgnum + 1, mailbox); 04056 } else { 04057 fprintf(p, "Subject: [PBX]: New %s message %d in mailbox %s" ENDL, flag, msgnum + 1, mailbox); 04058 } 04059 } 04060 04061 fprintf(p, "Message-ID: <Asterisk-%d-%d-%s-%d@%s>" ENDL, msgnum + 1, (unsigned int)ast_random(), mailbox, (int)getpid(), host); 04062 if (imap) { 04063 /* additional information needed for IMAP searching */ 04064 fprintf(p, "X-Asterisk-VM-Message-Num: %d" ENDL, msgnum + 1); 04065 /* fprintf(p, "X-Asterisk-VM-Orig-Mailbox: %s" ENDL, ext); */ 04066 fprintf(p, "X-Asterisk-VM-Server-Name: %s" ENDL, fromstring); 04067 fprintf(p, "X-Asterisk-VM-Context: %s" ENDL, context); 04068 #ifdef IMAP_STORAGE 04069 fprintf(p, "X-Asterisk-VM-Extension: %s" ENDL, (!ast_strlen_zero(vmu->imapvmshareid) ? vmu->imapvmshareid : mailbox)); 04070 #else 04071 fprintf(p, "X-Asterisk-VM-Extension: %s" ENDL, mailbox); 04072 #endif 04073 /* flag added for Urgent */ 04074 fprintf(p, "X-Asterisk-VM-Flag: %s" ENDL, flag); 04075 fprintf(p, "X-Asterisk-VM-Priority: %d" ENDL, chan->priority); 04076 fprintf(p, "X-Asterisk-VM-Caller-channel: %s" ENDL, chan->name); 04077 fprintf(p, "X-Asterisk-VM-Caller-ID-Num: %s" ENDL, enc_cidnum); 04078 fprintf(p, "X-Asterisk-VM-Caller-ID-Name: %s" ENDL, enc_cidname); 04079 fprintf(p, "X-Asterisk-VM-Duration: %d" ENDL, duration); 04080 if (!ast_strlen_zero(category)) { 04081 fprintf(p, "X-Asterisk-VM-Category: %s" ENDL, category); 04082 } else { 04083 fprintf(p, "X-Asterisk-VM-Category: " ENDL); 04084 } 04085 fprintf(p, "X-Asterisk-VM-Message-Type: %s" ENDL, msgnum > -1 ? "Message" : greeting_attachment); 04086 fprintf(p, "X-Asterisk-VM-Orig-date: %s" ENDL, date); 04087 fprintf(p, "X-Asterisk-VM-Orig-time: %ld" ENDL, (long)time(NULL)); 04088 } 04089 if (!ast_strlen_zero(cidnum)) { 04090 fprintf(p, "X-Asterisk-CallerID: %s" ENDL, enc_cidnum); 04091 } 04092 if (!ast_strlen_zero(cidname)) { 04093 fprintf(p, "X-Asterisk-CallerIDName: %s" ENDL, enc_cidname); 04094 } 04095 fprintf(p, "MIME-Version: 1.0" ENDL); 04096 if (attach_user_voicemail) { 04097 /* Something unique. */ 04098 snprintf(bound, sizeof(bound), "----voicemail_%d%s%d%d", msgnum + 1, mailbox, (int)getpid(), (unsigned int)ast_random()); 04099 04100 fprintf(p, "Content-Type: multipart/mixed; boundary=\"%s\"" ENDL, bound); 04101 fprintf(p, ENDL ENDL "This is a multi-part message in MIME format." ENDL ENDL); 04102 fprintf(p, "--%s" ENDL, bound); 04103 } 04104 fprintf(p, "Content-Type: text/plain; charset=%s" ENDL "Content-Transfer-Encoding: 8bit" ENDL ENDL, charset); 04105 if (emailbody) { 04106 struct ast_channel *ast; 04107 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 04108 char *passdata; 04109 int vmlen = strlen(emailbody)*3 + 200; 04110 passdata = alloca(vmlen); 04111 memset(passdata, 0, vmlen); 04112 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, cidnum, cidname, dur, date, passdata, vmlen, category, flag); 04113 pbx_substitute_variables_helper(ast, emailbody, passdata, vmlen); 04114 fprintf(p, "%s" ENDL, passdata); 04115 ast_channel_free(ast); 04116 } else 04117 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 04118 } else if (msgnum > -1) { 04119 if (strcmp(vmu->mailbox, mailbox)) { 04120 /* Forwarded type */ 04121 struct ast_config *msg_cfg; 04122 const char *v; 04123 int inttime; 04124 char fromdir[256], fromfile[256], origdate[80] = "", origcallerid[80] = ""; 04125 struct ast_flags config_flags = { CONFIG_FLAG_NOCACHE }; 04126 /* Retrieve info from VM attribute file */ 04127 make_dir(fromdir, sizeof(fromdir), vmu->context, vmu->mailbox, fromfolder); 04128 make_file(fromfile, sizeof(fromfile), fromdir, msgnum); 04129 if (strlen(fromfile) < sizeof(fromfile) - 5) { 04130 strcat(fromfile, ".txt"); 04131 } 04132 if ((msg_cfg = ast_config_load(fromfile, config_flags))) { 04133 if ((v = ast_variable_retrieve(msg_cfg, "message", "callerid"))) { 04134 ast_copy_string(origcallerid, v, sizeof(origcallerid)); 04135 } 04136 04137 /* You might be tempted to do origdate, except that a) it's in the wrong 04138 * format, and b) it's missing for IMAP recordings. */ 04139 if ((v = ast_variable_retrieve(msg_cfg, "message", "origtime")) && sscanf(v, "%30d", &inttime) == 1) { 04140 struct timeval tv = { inttime, }; 04141 struct ast_tm tm; 04142 ast_localtime(&tv, &tm, NULL); 04143 ast_strftime(origdate, sizeof(origdate), emaildateformat, &tm); 04144 } 04145 fprintf(p, "Dear %s:" ENDL ENDL "\tJust wanted to let you know you were just forwarded" 04146 " a %s long message (number %d)" ENDL "in mailbox %s from %s, on %s" ENDL 04147 "(originally sent by %s on %s)" ENDL "so you might want to check it when you get a" 04148 " chance. Thanks!" ENDL ENDL "\t\t\t\t--Asterisk" ENDL ENDL, vmu->fullname, dur, 04149 msgnum + 1, mailbox, (cidname ? cidname : (cidnum ? cidnum : "an unknown caller")), 04150 date, origcallerid, origdate); 04151 ast_config_destroy(msg_cfg); 04152 } else { 04153 goto plain_message; 04154 } 04155 } else { 04156 plain_message: 04157 fprintf(p, "Dear %s:" ENDL ENDL "\tJust wanted to let you know you were just left a " 04158 "%s long message (number %d)" ENDL "in mailbox %s from %s, on %s so you might" ENDL 04159 "want to check it when you get a chance. Thanks!" ENDL ENDL "\t\t\t\t--Asterisk" 04160 ENDL ENDL, vmu->fullname, dur, msgnum + 1, mailbox, 04161 (cidname ? cidname : (cidnum ? cidnum : "an unknown caller")), date); 04162 } 04163 } else { 04164 fprintf(p, "This message is to let you know that your greeting was changed on %s." ENDL 04165 "Please do not delete this message, lest your greeting vanish with it." ENDL ENDL, date); 04166 } 04167 04168 if (imap || attach_user_voicemail) { 04169 if (!ast_strlen_zero(attach2)) { 04170 snprintf(filename, sizeof(filename), "msg%04d.%s", msgnum, format); 04171 ast_debug(5, "creating second attachment filename %s\n", filename); 04172 add_email_attachment(p, vmu, format, attach, greeting_attachment, mailbox, bound, filename, 0, msgnum); 04173 snprintf(filename, sizeof(filename), "msgintro%04d.%s", msgnum, format); 04174 ast_debug(5, "creating attachment filename %s\n", filename); 04175 add_email_attachment(p, vmu, format, attach2, greeting_attachment, mailbox, bound, filename, 1, msgnum); 04176 } else { 04177 snprintf(filename, sizeof(filename), "msg%04d.%s", msgnum, format); 04178 ast_debug(5, "creating attachment filename %s, no second attachment.\n", filename); 04179 add_email_attachment(p, vmu, format, attach, greeting_attachment, mailbox, bound, filename, 1, msgnum); 04180 } 04181 } 04182 }
| static int make_file | ( | char * | dest, | |
| const int | len, | |||
| const char * | dir, | |||
| const int | num | |||
| ) | [static] |
Creates a file system path expression for a folder within the voicemail data folder and the appropriate context.
| dest | The variable to hold the output generated path expression. This buffer should be of size PATH_MAX. | |
| len | The length of the path string that was written out. |
The path is constructed as VM_SPOOL_DIRcontext/ext/folder
Definition at line 1266 of file app_voicemail.c.
Referenced by advanced_options(), close_mailbox(), copy_message(), leave_voicemail(), make_email_file(), notify_new_message(), play_message(), prep_email_sub_vars(), save_to_folder(), vm_execmain(), and vm_forwardoptions().
| static int manager_list_voicemail_users | ( | struct mansession * | s, | |
| const struct message * | m | |||
| ) | [static] |
Manager list voicemail users command.
Definition at line 10114 of file app_voicemail.c.
References AST_LIST_EMPTY, AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_strlen_zero(), ast_test_flag, astman_append(), astman_get_header(), astman_send_ack(), ast_vm_user::attachfmt, ast_vm_user::callback, ast_vm_user::context, count_messages(), ast_vm_user::dialout, ast_vm_user::email, ast_vm_user::exit, ast_vm_user::fullname, inboxcount(), ast_vm_user::language, ast_vm_user::mailbox, ast_vm_user::mailcmd, make_dir(), ast_vm_user::maxmsg, ast_vm_user::maxsecs, ast_vm_user::pager, RESULT_SUCCESS, ast_vm_user::saydurationm, ast_vm_user::serveremail, ast_vm_user::uniqueid, VM_ATTACH, VM_DELETE, VM_ENVELOPE, VM_OPERATOR, VM_REVIEW, VM_SAYCID, ast_vm_user::volgain, and ast_vm_user::zonetag.
Referenced by load_module().
10115 { 10116 struct ast_vm_user *vmu = NULL; 10117 const char *id = astman_get_header(m, "ActionID"); 10118 char actionid[128] = ""; 10119 10120 if (!ast_strlen_zero(id)) 10121 snprintf(actionid, sizeof(actionid), "ActionID: %s\r\n", id); 10122 10123 AST_LIST_LOCK(&users); 10124 10125 if (AST_LIST_EMPTY(&users)) { 10126 astman_send_ack(s, m, "There are no voicemail users currently defined."); 10127 AST_LIST_UNLOCK(&users); 10128 return RESULT_SUCCESS; 10129 } 10130 10131 astman_send_ack(s, m, "Voicemail user list will follow"); 10132 10133 AST_LIST_TRAVERSE(&users, vmu, list) { 10134 char dirname[256]; 10135 10136 #ifdef IMAP_STORAGE 10137 int new, old; 10138 inboxcount(vmu->mailbox, &new, &old); 10139 #endif 10140 10141 make_dir(dirname, sizeof(dirname), vmu->context, vmu->mailbox, "INBOX"); 10142 astman_append(s, 10143 "%s" 10144 "Event: VoicemailUserEntry\r\n" 10145 "VMContext: %s\r\n" 10146 "VoiceMailbox: %s\r\n" 10147 "Fullname: %s\r\n" 10148 "Email: %s\r\n" 10149 "Pager: %s\r\n" 10150 "ServerEmail: %s\r\n" 10151 "MailCommand: %s\r\n" 10152 "Language: %s\r\n" 10153 "TimeZone: %s\r\n" 10154 "Callback: %s\r\n" 10155 "Dialout: %s\r\n" 10156 "UniqueID: %s\r\n" 10157 "ExitContext: %s\r\n" 10158 "SayDurationMinimum: %d\r\n" 10159 "SayEnvelope: %s\r\n" 10160 "SayCID: %s\r\n" 10161 "AttachMessage: %s\r\n" 10162 "AttachmentFormat: %s\r\n" 10163 "DeleteMessage: %s\r\n" 10164 "VolumeGain: %.2f\r\n" 10165 "CanReview: %s\r\n" 10166 "CallOperator: %s\r\n" 10167 "MaxMessageCount: %d\r\n" 10168 "MaxMessageLength: %d\r\n" 10169 "NewMessageCount: %d\r\n" 10170 #ifdef IMAP_STORAGE 10171 "OldMessageCount: %d\r\n" 10172 "IMAPUser: %s\r\n" 10173 #endif 10174 "\r\n", 10175 actionid, 10176 vmu->context, 10177 vmu->mailbox, 10178 vmu->fullname, 10179 vmu->email, 10180 vmu->pager, 10181 vmu->serveremail, 10182 vmu->mailcmd, 10183 vmu->language, 10184 vmu->zonetag, 10185 vmu->callback, 10186 vmu->dialout, 10187 vmu->uniqueid, 10188 vmu->exit, 10189 vmu->saydurationm, 10190 ast_test_flag(vmu, VM_ENVELOPE) ? "Yes" : "No", 10191 ast_test_flag(vmu, VM_SAYCID) ? "Yes" : "No", 10192 ast_test_flag(vmu, VM_ATTACH) ? "Yes" : "No", 10193 vmu->attachfmt, 10194 ast_test_flag(vmu, VM_DELETE) ? "Yes" : "No", 10195 vmu->volgain, 10196 ast_test_flag(vmu, VM_REVIEW) ? "Yes" : "No", 10197 ast_test_flag(vmu, VM_OPERATOR) ? "Yes" : "No", 10198 vmu->maxmsg, 10199 vmu->maxsecs, 10200 #ifdef IMAP_STORAGE 10201 new, old, vmu->imapuser 10202 #else 10203 count_messages(vmu, dirname) 10204 #endif 10205 ); 10206 } 10207 astman_append(s, "Event: VoicemailUserEntryComplete\r\n%s\r\n", actionid); 10208 10209 AST_LIST_UNLOCK(&users); 10210 10211 return RESULT_SUCCESS; 10212 }
| static void* mb_poll_thread | ( | void * | data | ) | [static] |
Definition at line 9949 of file app_voicemail.c.
References ast_cond_timedwait(), ast_mutex_lock(), ast_mutex_unlock(), ast_samp2tv(), ast_tvadd(), ast_tvnow(), poll_lock, and poll_subscribed_mailboxes().
Referenced by start_poll_thread().
09950 { 09951 while (poll_thread_run) { 09952 struct timespec ts = { 0, }; 09953 struct timeval wait; 09954 09955 wait = ast_tvadd(ast_tvnow(), ast_samp2tv(poll_freq, 1)); 09956 ts.tv_sec = wait.tv_sec; 09957 ts.tv_nsec = wait.tv_usec * 1000; 09958 09959 ast_mutex_lock(&poll_lock); 09960 ast_cond_timedwait(&poll_cond, &poll_lock, &ts); 09961 ast_mutex_unlock(&poll_lock); 09962 09963 if (!poll_thread_run) 09964 break; 09965 09966 poll_subscribed_mailboxes(); 09967 } 09968 09969 return NULL; 09970 }
| static const char* mbox | ( | int | id | ) | [static] |
Definition at line 1308 of file app_voicemail.c.
Referenced by acf_mailbox_exists(), add_peer_mailboxes(), adsi_load_vmail(), build_gateway(), copy_message(), get_folder(), has_voicemail(), notify_new_message(), open_mailbox(), save_to_folder(), vm_box_exists(), and vm_execmain().
01309 { 01310 static const char *msgs[] = { 01311 #ifdef IMAP_STORAGE 01312 imapfolder, 01313 #else 01314 "INBOX", 01315 #endif 01316 "Old", 01317 "Work", 01318 "Family", 01319 "Friends", 01320 "Cust1", 01321 "Cust2", 01322 "Cust3", 01323 "Cust4", 01324 "Cust5", 01325 "Deleted", 01326 "Urgent" 01327 }; 01328 return (id >= 0 && id < (sizeof(msgs)/sizeof(msgs[0]))) ? msgs[id] : "Unknown"; 01329 }
| static int messagecount | ( | const char * | context, | |
| const char * | mailbox, | |||
| const char * | folder | |||
| ) | [static] |
Definition at line 4680 of file app_voicemail.c.
References __has_voicemail().
Referenced by load_module().
04681 { 04682 return __has_voicemail(context, mailbox, folder, 0); 04683 }
| static void mwi_sub_destroy | ( | struct mwi_sub * | mwi_sub | ) | [static] |
Definition at line 9972 of file app_voicemail.c.
References ast_free.
Referenced by handle_unsubscribe().
09973 { 09974 ast_free(mwi_sub); 09975 }
| static void mwi_sub_event_cb | ( | const struct ast_event * | event, | |
| void * | userdata | |||
| ) | [static] |
Definition at line 10049 of file app_voicemail.c.
References ast_calloc, ast_event_get_ie_str(), ast_event_get_ie_uint(), ast_event_get_type(), AST_EVENT_IE_CONTEXT, AST_EVENT_IE_EVENTTYPE, AST_EVENT_IE_MAILBOX, AST_EVENT_IE_UNIQUEID, AST_EVENT_MWI, AST_EVENT_SUB, ast_free, ast_log(), ast_strdup, ast_taskprocessor_push(), mwi_sub_task::context, handle_subscribe(), LOG_ERROR, mwi_sub_task::mailbox, mwi_subscription_tps, and mwi_sub_task::uniqueid.
Referenced by start_poll_thread().
10050 { 10051 struct mwi_sub_task *mwist; 10052 10053 if (ast_event_get_type(event) != AST_EVENT_SUB) 10054 return; 10055 10056 if (ast_event_get_ie_uint(event, AST_EVENT_IE_EVENTTYPE) != AST_EVENT_MWI) 10057 return; 10058 10059 if ((mwist = ast_calloc(1, (sizeof(*mwist)))) == NULL) { 10060 ast_log(LOG_ERROR, "could not allocate a mwi_sub_task\n"); 10061 return; 10062 } 10063 mwist->mailbox = ast_strdup(ast_event_get_ie_str(event, AST_EVENT_IE_MAILBOX)); 10064 mwist->context = ast_strdup(ast_event_get_ie_str(event, AST_EVENT_IE_CONTEXT)); 10065 mwist->uniqueid = ast_event_get_ie_uint(event, AST_EVENT_IE_UNIQUEID); 10066 10067 if (ast_taskprocessor_push(mwi_subscription_tps, handle_subscribe, mwist) < 0) { 10068 ast_free(mwist); 10069 } 10070 }
| static void mwi_unsub_event_cb | ( | const struct ast_event * | event, | |
| void * | userdata | |||
| ) | [static] |
Definition at line 10033 of file app_voicemail.c.
References ast_calloc, ast_event_get_ie_uint(), ast_event_get_type(), AST_EVENT_IE_EVENTTYPE, AST_EVENT_IE_UNIQUEID, AST_EVENT_MWI, AST_EVENT_UNSUB, ast_free, ast_taskprocessor_push(), handle_unsubscribe(), mwi_subscription_tps, and mwi_sub_task::uniqueid.
Referenced by start_poll_thread().
10034 { 10035 uint32_t u, *uniqueid = ast_calloc(1, sizeof(*uniqueid)); 10036 if (ast_event_get_type(event) != AST_EVENT_UNSUB) 10037 return; 10038 10039 if (ast_event_get_ie_uint(event, AST_EVENT_IE_EVENTTYPE) != AST_EVENT_MWI) 10040 return; 10041 10042 u = ast_event_get_ie_uint(event, AST_EVENT_IE_UNIQUEID); 10043 *uniqueid = u; 10044 if (ast_taskprocessor_push(mwi_subscription_tps, handle_unsubscribe, uniqueid) < 0) { 10045 ast_free(uniqueid); 10046 } 10047 }
| static int notify_new_message | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| int | msgnum, | |||
| long | duration, | |||
| char * | fmt, | |||
| char * | cidnum, | |||
| char * | cidname, | |||
| const char * | flag | |||
| ) | [static] |
Sends email notification that a user has a new voicemail waiting for them.
| chan | ||
| vmu | ||
| vms | ||
| msgnum | ||
| duration | ||
| fmt | ||
| cidnum | The Caller ID phone number value. | |
| cidname | The Caller ID name value. |
Definition at line 6197 of file app_voicemail.c.
References ast_app_has_voicemail(), ast_app_inboxcount2(), ast_channel_lock, ast_channel_unlock, ast_log(), AST_LOG_WARNING, ast_strdupa, ast_strlen_zero(), ast_test_flag, ast_vm_user::attachfmt, ast_vm_user::context, vm_state::curmsg, DELETE, DISPOSE, ast_vm_user::email, EVENT_FLAG_CALL, globalflags, ast_vm_user::mailbox, make_dir(), make_file(), manager_event, mbox(), vm_state::newmessages, ast_vm_user::pager, pbx_builtin_getvar_helper(), queue_mwi_event(), RETRIEVE, run_externnotify(), sendmail(), sendpage(), ast_vm_user::serveremail, strsep(), VM_ATTACH, vm_delete(), and VM_DELETE.
Referenced by copy_message(), and leave_voicemail().
06198 { 06199 char todir[PATH_MAX], fn[PATH_MAX], ext_context[PATH_MAX], *stringp; 06200 int newmsgs = 0, oldmsgs = 0, urgentmsgs = 0; 06201 const char *category; 06202 char *myserveremail = serveremail; 06203 06204 ast_channel_lock(chan); 06205 if ((category = pbx_builtin_getvar_helper(chan, "VM_CATEGORY"))) { 06206 category = ast_strdupa(category); 06207 } 06208 ast_channel_unlock(chan); 06209 06210 make_dir(todir, sizeof(todir), vmu->context, vmu->mailbox, "INBOX"); 06211 make_file(fn, sizeof(fn), todir, msgnum); 06212 snprintf(ext_context, sizeof(ext_context), "%s@%s", vmu->mailbox, vmu->context); 06213 06214 if (!ast_strlen_zero(vmu->attachfmt)) { 06215 if (strstr(fmt, vmu->attachfmt)) 06216 fmt = vmu->attachfmt; 06217 else 06218 ast_log(AST_LOG_WARNING, "Attachment format '%s' is not one of the recorded formats '%s'. Falling back to default format for '%s@%s'.\n", vmu->attachfmt, fmt, vmu->mailbox, vmu->context); 06219 } 06220 06221 /* Attach only the first format */ 06222 fmt = ast_strdupa(fmt); 06223 stringp = fmt; 06224 strsep(&stringp, "|"); 06225 06226 if (!ast_strlen_zero(vmu->serveremail)) 06227 myserveremail = vmu->serveremail; 06228 06229 if (!ast_strlen_zero(vmu->email)) { 06230 int attach_user_voicemail = ast_test_flag(vmu, VM_ATTACH); 06231 if (!attach_user_voicemail) 06232 attach_user_voicemail = ast_test_flag((&globalflags), VM_ATTACH); 06233 06234 if (attach_user_voicemail) 06235 RETRIEVE(todir, msgnum, vmu->mailbox, vmu->context); 06236 06237 /* XXX possible imap issue, should category be NULL XXX */ 06238 sendmail(myserveremail, vmu, msgnum, vmu->context, vmu->mailbox, mbox(0), cidnum, cidname, fn, NULL, fmt, duration, attach_user_voicemail, chan, category, flag); 06239 06240 if (attach_user_voicemail) 06241 DISPOSE(todir, msgnum); 06242 } 06243 06244 if (!ast_strlen_zero(vmu->pager)) { 06245 sendpage(myserveremail, vmu->pager, msgnum, vmu->context, vmu->mailbox, mbox(0), cidnum, cidname, duration, vmu, category, flag); 06246 } 06247 06248 if (ast_test_flag(vmu, VM_DELETE)) 06249 DELETE(todir, msgnum, fn, vmu); 06250 06251 /* Leave voicemail for someone */ 06252 if (ast_app_has_voicemail(ext_context, NULL)) 06253 ast_app_inboxcount2(ext_context, &urgentmsgs, &newmsgs, &oldmsgs); 06254 06255 queue_mwi_event(ext_context, urgentmsgs, newmsgs, oldmsgs); 06256 06257 manager_event(EVENT_FLAG_CALL, "MessageWaiting", "Mailbox: %s@%s\r\nWaiting: %d\r\nNew: %d\r\nOld: %d\r\n", vmu->mailbox, vmu->context, ast_app_has_voicemail(ext_context, NULL), newmsgs, oldmsgs); 06258 run_externnotify(vmu->context, vmu->mailbox, flag); 06259 06260 #ifdef IMAP_STORAGE 06261 vm_delete(fn); /* Delete the file, but not the IMAP message */ 06262 if (ast_test_flag(vmu, VM_DELETE)) { /* Delete the IMAP message if delete = yes */ 06263 vm_imap_delete(vms->curmsg, vmu); 06264 vms->newmessages--; /* Fix new message count */ 06265 } 06266 #endif 06267 06268 return 0; 06269 }
| static int ochar | ( | struct baseio * | bio, | |
| int | c, | |||
| FILE * | so | |||
| ) | [static] |
utility used by base_encode()
Definition at line 3646 of file app_voicemail.c.
References BASELINELEN, eol, and baseio::linelength.
Referenced by base_encode().
03647 { 03648 if (bio->linelength >= BASELINELEN) { 03649 if (fputs(eol,so) == EOF) 03650 return -1; 03651 03652 bio->linelength= 0; 03653 } 03654 03655 if (putc(((unsigned char)c),so) == EOF) 03656 return -1; 03657 03658 bio->linelength++; 03659 03660 return 1; 03661 }
| static int open_mailbox | ( | struct vm_state * | vms, | |
| struct ast_vm_user * | vmu, | |||
| int | box | |||
| ) | [static] |
Definition at line 6953 of file app_voicemail.c.
References ast_copy_string(), ast_log(), AST_LOG_ERROR, ast_unlock_path(), ast_vm_user::context, count_messages(), create_dirpath(), vm_state::curbox, vm_state::curdir, last_message_index(), vm_state::lastmsg, mbox(), vm_state::username, vm_lock_path(), and vm_state::vmbox.
Referenced by vm_execmain().
06954 { 06955 int count_msg, last_msg; 06956 06957 ast_copy_string(vms->curbox, mbox(box), sizeof(vms->curbox)); 06958 06959 /* Rename the member vmbox HERE so that we don't try to return before 06960 * we know what's going on. 06961 */ 06962 snprintf(vms->vmbox, sizeof(vms->vmbox), "vm-%s", vms->curbox); 06963 06964 /* Faster to make the directory than to check if it exists. */ 06965 create_dirpath(vms->curdir, sizeof(vms->curdir), vmu->context, vms->username, vms->curbox); 06966 06967 count_msg = count_messages(vmu, vms->curdir); 06968 if (count_msg < 0) 06969 return count_msg; 06970 else 06971 vms->lastmsg = count_msg - 1; 06972 06973 /* 06974 The following test is needed in case sequencing gets messed up. 06975 There appears to be more than one way to mess up sequence, so 06976 we will not try to find all of the root causes--just fix it when 06977 detected. 06978 */ 06979 06980 if (vm_lock_path(vms->curdir)) { 06981 ast_log(AST_LOG_ERROR, "Could not open mailbox %s: mailbox is locked\n", vms->curdir); 06982 return -1; 06983 } 06984 06985 last_msg = last_message_index(vmu, vms->curdir); 06986 ast_unlock_path(vms->curdir); 06987 06988 if (last_msg < 0) 06989 return last_msg; 06990 06991 return 0; 06992 }
| static int play_message | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 6751 of file app_voicemail.c.
References adsi_message(), ast_config_destroy(), ast_config_load, AST_DIGIT_ANY, ast_fileexists(), ast_log(), AST_LOG_WARNING, ast_say_number(), ast_strdupa, ast_strlen_zero(), ast_test_flag, ast_variable_retrieve(), CONFIG_FLAG_NOCACHE, ast_vm_user::context, vm_state::curdir, vm_state::curmsg, DISPOSE, vm_state::fn, vm_state::heard, vm_state::lastmsg, LOG_WARNING, ast_vm_user::mailbox, make_file(), play_message_callerid(), play_message_category(), play_message_datetime(), play_message_duration(), RETRIEVE, ast_vm_user::saydurationm, vm_state::starting, VM_ENVELOPE, VM_SAYCID, VM_SAYDURATION, wait_file(), and wait_file2().
Referenced by vm_browse_messages_en(), vm_browse_messages_es(), vm_browse_messages_gr(), vm_browse_messages_he(), vm_browse_messages_it(), vm_browse_messages_pt(), vm_browse_messages_zh(), and vm_execmain().
06752 { 06753 int res = 0; 06754 char filename[256], *cid; 06755 const char *origtime, *context, *category, *duration, *flag; 06756 struct ast_config *msg_cfg; 06757 struct ast_flags config_flags = { CONFIG_FLAG_NOCACHE }; 06758 06759 vms->starting = 0; 06760 make_file(vms->fn, sizeof(vms->fn), vms->curdir, vms->curmsg); 06761 adsi_message(chan, vms); 06762 if (!vms->curmsg) 06763 res = wait_file2(chan, vms, "vm-first"); /* "First" */ 06764 else if (vms->curmsg == vms->lastmsg) 06765 res = wait_file2(chan, vms, "vm-last"); /* "last" */ 06766 06767 snprintf(filename, sizeof(filename), "%s.txt", vms->fn); 06768 RETRIEVE(vms->curdir, vms->curmsg, vmu->mailbox, vmu->context); 06769 msg_cfg = ast_config_load(filename, config_flags); 06770 if (!msg_cfg) { 06771 ast_log(LOG_WARNING, "No message attribute file?!! (%s)\n", filename); 06772 return 0; 06773 } 06774 flag = ast_variable_retrieve(msg_cfg, "message", "flag"); 06775 06776 /* Play the word urgent if we are listening to urgent messages */ 06777 if (!ast_strlen_zero(flag) && !strcmp(flag, "Urgent")) { 06778 res = wait_file2(chan, vms, "vm-Urgent"); /* "urgent" */ 06779 } 06780 06781 if (!res) { 06782 /* POLISH syntax */ 06783 if (!strcasecmp(chan->language, "pl")) { 06784 if (vms->curmsg && (vms->curmsg != vms->lastmsg)) { 06785 int ten, one; 06786 char nextmsg[256]; 06787 ten = (vms->curmsg + 1) / 10; 06788 one = (vms->curmsg + 1) % 10; 06789 06790 if (vms->curmsg < 20) { 06791 snprintf(nextmsg, sizeof(nextmsg), "digits/n-%d", vms->curmsg + 1); 06792 res = wait_file2(chan, vms, nextmsg); 06793 } else { 06794 snprintf(nextmsg, sizeof(nextmsg), "digits/n-%d", ten * 10); 06795 res = wait_file2(chan, vms, nextmsg); 06796 if (one > 0) { 06797 if (!res) { 06798 snprintf(nextmsg, sizeof(nextmsg), "digits/n-%d", one); 06799 res = wait_file2(chan, vms, nextmsg); 06800 } 06801 } 06802 } 06803 } 06804 if (!res) 06805 res = wait_file2(chan, vms, "vm-message"); 06806 /* HEBREW syntax */ 06807 } else if (!strcasecmp(chan->language, "he")) { 06808 if (!vms->curmsg) { 06809 res = wait_file2(chan, vms, "vm-message"); 06810 res = wait_file2(chan, vms, "vm-first"); 06811 } else if (vms->curmsg == vms->lastmsg) { 06812 res = wait_file2(chan, vms, "vm-message"); 06813 res = wait_file2(chan, vms, "vm-last"); 06814 } else { 06815 res = wait_file2(chan, vms, "vm-message"); 06816 res = wait_file2(chan, vms, "vm-number"); 06817 res = ast_say_number(chan, vms->curmsg + 1, AST_DIGIT_ANY, chan->language, "f"); 06818 } 06819 } else { 06820 if (!strcasecmp(chan->language, "se")) /* SWEDISH syntax */ 06821 res = wait_file2(chan, vms, "vm-meddelandet"); /* "message" */ 06822 else /* DEFAULT syntax */ { 06823 res = wait_file2(chan, vms, "vm-message"); 06824 } 06825 if (vms->curmsg && (vms->curmsg != vms->lastmsg)) { 06826 if (!res) { 06827 res = ast_say_number(chan, vms->curmsg + 1, AST_DIGIT_ANY, chan->language, NULL); 06828 } 06829 } 06830 } 06831 } 06832 06833 if (!msg_cfg) { 06834 ast_log(AST_LOG_WARNING, "No message attribute file?!! (%s)\n", filename); 06835 return 0; 06836 } 06837 06838 if (!(origtime = ast_variable_retrieve(msg_cfg, "message", "origtime"))) { 06839 ast_log(AST_LOG_WARNING, "No origtime?!\n"); 06840 DISPOSE(vms->curdir, vms->curmsg); 06841 ast_config_destroy(msg_cfg); 06842 return 0; 06843 } 06844 06845 cid = ast_strdupa(ast_variable_retrieve(msg_cfg, "message", "callerid")); 06846 duration = ast_variable_retrieve(msg_cfg, "message", "duration"); 06847 category = ast_variable_retrieve(msg_cfg, "message", "category"); 06848 06849 context = ast_variable_retrieve(msg_cfg, "message", "context"); 06850 if (!strncasecmp("macro",context,5)) /* Macro names in contexts are useless for our needs */ 06851 context = ast_variable_retrieve(msg_cfg, "message","macrocontext"); 06852 if (!res) { 06853 res = play_message_category(chan, category); 06854 } 06855 if ((!res) && (ast_test_flag(vmu, VM_ENVELOPE))) 06856 res = play_message_datetime(chan, vmu, origtime, filename); 06857 if ((!res) && (ast_test_flag(vmu, VM_SAYCID))) 06858 res = play_message_callerid(chan, vms, cid, context, 0); 06859 if ((!res) && (ast_test_flag(vmu, VM_SAYDURATION))) 06860 res = play_message_duration(chan, vms, duration, vmu->saydurationm); 06861 /* Allow pressing '1' to skip envelope / callerid */ 06862 if (res == '1') 06863 res = 0; 06864 ast_config_destroy(msg_cfg); 06865 06866 if (!res) { 06867 make_file(vms->fn, sizeof(vms->fn), vms->curdir, vms->curmsg); 06868 vms->heard[vms->curmsg] = 1; 06869 #ifdef IMAP_STORAGE 06870 /*IMAP storage stores any prepended message from a forward 06871 * as a separate file from the rest of the message 06872 */ 06873 if (!ast_strlen_zero(vms->introfn) && ast_fileexists(vms->introfn, NULL, NULL) > 0) { 06874 wait_file(chan, vms, vms->introfn); 06875 } 06876 #endif 06877 if ((res = wait_file(chan, vms, vms->fn)) < 0) { 06878 ast_log(AST_LOG_WARNING, "Playback of message %s failed\n", vms->fn); 06879 res = 0; 06880 } 06881 } 06882 DISPOSE(vms->curdir, vms->curmsg); 06883 return res; 06884 }
| static int play_message_callerid | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| char * | cid, | |||
| const char * | context, | |||
| int | callback | |||
| ) | [static] |
Definition at line 6637 of file app_voicemail.c.
References ast_callerid_parse(), ast_debug, AST_DIGIT_ANY, ast_fileexists(), ast_say_digit_str(), ast_stream_and_wait(), ast_strlen_zero(), ast_verb, cidinternalcontexts, MAX_NUM_CID_CONTEXTS, and wait_file2().
Referenced by advanced_options(), and play_message().
06638 { 06639 int res = 0; 06640 int i; 06641 char *callerid, *name; 06642 char prefile[PATH_MAX] = ""; 06643 06644 06645 /* If voicemail cid is not enabled, or we didn't get cid or context from 06646 * the attribute file, leave now. 06647 * 06648 * TODO Still need to change this so that if this function is called by the 06649 * message envelope (and someone is explicitly requesting to hear the CID), 06650 * it does not check to see if CID is enabled in the config file. 06651 */ 06652 if ((cid == NULL)||(context == NULL)) 06653 return res; 06654 06655 /* Strip off caller ID number from name */ 06656 ast_debug(1, "VM-CID: composite caller ID received: %s, context: %s\n", cid, context); 06657 ast_callerid_parse(cid, &name, &callerid); 06658 if ((!ast_strlen_zero(callerid)) && strcmp(callerid, "Unknown")) { 06659 /* Check for internal contexts and only */ 06660 /* say extension when the call didn't come from an internal context in the list */ 06661 for (i = 0 ; i < MAX_NUM_CID_CONTEXTS ; i++){ 06662 ast_debug(1, "VM-CID: comparing internalcontext: %s\n", cidinternalcontexts[i]); 06663 if ((strcmp(cidinternalcontexts[i], context) == 0)) 06664 break; 06665 } 06666 if (i != MAX_NUM_CID_CONTEXTS){ /* internal context? */ 06667 if (!res) { 06668 snprintf(prefile, sizeof(prefile), "%s%s/%s/greet", VM_SPOOL_DIR, context, callerid); 06669 if (!ast_strlen_zero(prefile)) { 06670 /* See if we can find a recorded name for this person instead of their extension number */ 06671 if (ast_fileexists(prefile, NULL, NULL) > 0) { 06672 ast_verb(3, "Playing envelope info: CID number '%s' matches mailbox number, playing recorded name\n", callerid); 06673 if (!callback) 06674 res = wait_file2(chan, vms, "vm-from"); 06675 res = ast_stream_and_wait(chan, prefile, ""); 06676 } else { 06677 ast_verb(3, "Playing envelope info: message from '%s'\n", callerid); 06678 /* Say "from extension" as one saying to sound smoother */ 06679 if (!callback) 06680 res = wait_file2(chan, vms, "vm-from-extension"); 06681 res = ast_say_digit_str(chan, callerid, "", chan->language); 06682 } 06683 } 06684 } 06685 } else if (!res) { 06686 ast_debug(1, "VM-CID: Numeric caller id: (%s)\n", callerid); 06687 /* Since this is all nicely figured out, why not say "from phone number" in this case? */ 06688 if (!callback) 06689 res = wait_file2(chan, vms, "vm-from-phonenumber"); 06690 res = ast_say_digit_str(chan, callerid, AST_DIGIT_ANY, chan->language); 06691 } 06692 } else { 06693 /* Number unknown */ 06694 ast_debug(1, "VM-CID: From an unknown number\n"); 06695 /* Say "from an unknown caller" as one phrase - it is already recorded by "the voice" anyhow */ 06696 res = wait_file2(chan, vms, "vm-unknown-caller"); 06697 } 06698 return res; 06699 }
| static int play_message_category | ( | struct ast_channel * | chan, | |
| const char * | category | |||
| ) | [static] |
Definition at line 6549 of file app_voicemail.c.
References ast_log(), AST_LOG_WARNING, ast_play_and_wait(), and ast_strlen_zero().
Referenced by play_message().
06550 { 06551 int res = 0; 06552 06553 if (!ast_strlen_zero(category)) 06554 res = ast_play_and_wait(chan, category); 06555 06556 if (res) { 06557 ast_log(AST_LOG_WARNING, "No sound file for category '%s' was found.\n", category); 06558 res = 0; 06559 } 06560 06561 return res; 06562 }
| static int play_message_datetime | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| const char * | origtime, | |||
| const char * | filename | |||
| ) | [static] |
Definition at line 6564 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_get_time_t(), AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_localtime(), ast_log(), AST_LOG_WARNING, ast_say_date_with_format, ast_strlen_zero(), ast_tvnow(), vm_zone::msg_format, vm_zone::name, pbx_builtin_setvar_helper(), vm_zone::timezone, and ast_vm_user::zonetag.
Referenced by advanced_options(), and play_message().
06565 { 06566 int res = 0; 06567 struct vm_zone *the_zone = NULL; 06568 time_t t; 06569 06570 if (ast_get_time_t(origtime, &t, 0, NULL)) { 06571 ast_log(AST_LOG_WARNING, "Couldn't find origtime in %s\n", filename); 06572 return 0; 06573 } 06574 06575 /* Does this user have a timezone specified? */ 06576 if (!ast_strlen_zero(vmu->zonetag)) { 06577 /* Find the zone in the list */ 06578 struct vm_zone *z; 06579 AST_LIST_LOCK(&zones); 06580 AST_LIST_TRAVERSE(&zones, z, list) { 06581 if (!strcmp(z->name, vmu->zonetag)) { 06582 the_zone = z; 06583 break; 06584 } 06585 } 06586 AST_LIST_UNLOCK(&zones); 06587 } 06588 06589 /* No internal variable parsing for now, so we'll comment it out for the time being */ 06590 #if 0 06591 /* Set the DIFF_* variables */ 06592 ast_localtime(&t, &time_now, NULL); 06593 tv_now = ast_tvnow(); 06594 ast_localtime(&tv_now, &time_then, NULL); 06595 06596 /* Day difference */ 06597 if (time_now.tm_year == time_then.tm_year) 06598 snprintf(temp,sizeof(temp),"%d",time_now.tm_yday); 06599 else 06600 snprintf(temp,sizeof(temp),"%d",(time_now.tm_year - time_then.tm_year) * 365 + (time_now.tm_yday - time_then.tm_yday)); 06601 pbx_builtin_setvar_helper(chan, "DIFF_DAY", temp); 06602 06603 /* Can't think of how other diffs might be helpful, but I'm sure somebody will think of something. */ 06604 #endif 06605 if (the_zone) { 06606 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, the_zone->msg_format, the_zone->timezone); 06607 } 06608 else if (!strcasecmp(chan->language,"pl")) /* POLISH syntax */ 06609 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' Q HM", NULL); 06610 else if (!strcasecmp(chan->language,"se")) /* SWEDISH syntax */ 06611 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' dB 'digits/at' k 'and' M", NULL); 06612 else if (!strcasecmp(chan->language,"no")) /* NORWEGIAN syntax */ 06613 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' Q 'digits/at' HM", NULL); 06614 else if (!strcasecmp(chan->language,"de")) /* GERMAN syntax */ 06615 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' Q 'digits/at' HM", NULL); 06616 else if (!strcasecmp(chan->language,"nl")) /* DUTCH syntax */ 06617 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' q 'digits/nl-om' HM", NULL); 06618 else if (!strcasecmp(chan->language,"it")) /* ITALIAN syntax */ 06619 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' q 'digits/at' 'digits/hours' k 'digits/e' M 'digits/minutes'", NULL); 06620 else if (!strcasecmp(chan->language,"gr")) 06621 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' q H 'digits/kai' M ", NULL); 06622 else if (!strcasecmp(chan->language,"pt_BR")) 06623 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' Ad 'digits/pt-de' B 'digits/pt-de' Y 'digits/pt-as' HM ", NULL); 06624 else if (!strncasecmp(chan->language, "zh", 2)) /* CHINESE (Taiwan) syntax */ 06625 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "qR 'vm-received'", NULL); 06626 else { 06627 res = ast_say_date_with_format(chan, t, AST_DIGIT_ANY, chan->language, "'vm-received' q 'digits/at' IMp", NULL); 06628 } 06629 #if 0 06630 pbx_builtin_setvar_helper(chan, "DIFF_DAY", NULL); 06631 #endif 06632 return res; 06633 }
| static int play_message_duration | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| const char * | duration, | |||
| int | minduration | |||
| ) | [static] |
Definition at line 6701 of file app_voicemail.c.
References ast_debug, AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), num, say_and_wait(), and wait_file2().
Referenced by play_message().
06702 { 06703 int res = 0; 06704 int durationm; 06705 int durations; 06706 /* Verify that we have a duration for the message */ 06707 if (duration == NULL) 06708 return res; 06709 06710 /* Convert from seconds to minutes */ 06711 durations=atoi(duration); 06712 durationm=(durations / 60); 06713 06714 ast_debug(1, "VM-Duration: duration is: %d seconds converted to: %d minutes\n", durations, durationm); 06715 06716 if ((!res) && (durationm >= minduration)) { 06717 res = wait_file2(chan, vms, "vm-duration"); 06718 06719 /* POLISH syntax */ 06720 if (!strcasecmp(chan->language, "pl")) { 06721 div_t num = div(durationm, 10); 06722 06723 if (durationm == 1) { 06724 res = ast_play_and_wait(chan, "digits/1z"); 06725 res = res ? res : ast_play_and_wait(chan, "vm-minute-ta"); 06726 } else if (num.rem > 1 && num.rem < 5 && num.quot != 1) { 06727 if (num.rem == 2) { 06728 if (!num.quot) { 06729 res = ast_play_and_wait(chan, "digits/2-ie"); 06730 } else { 06731 res = say_and_wait(chan, durationm - 2 , chan->language); 06732 res = res ? res : ast_play_and_wait(chan, "digits/2-ie"); 06733 } 06734 } else { 06735 res = say_and_wait(chan, durationm, chan->language); 06736 } 06737 res = res ? res : ast_play_and_wait(chan, "vm-minute-ty"); 06738 } else { 06739 res = say_and_wait(chan, durationm, chan->language); 06740 res = res ? res : ast_play_and_wait(chan, "vm-minute-t"); 06741 } 06742 /* DEFAULT syntax */ 06743 } else { 06744 res = ast_say_number(chan, durationm, AST_DIGIT_ANY, chan->language, NULL); 06745 res = wait_file2(chan, vms, "vm-minutes"); 06746 } 06747 } 06748 return res; 06749 }
| static int play_record_review | ( | struct ast_channel * | chan, | |
| char * | playfile, | |||
| char * | recordfile, | |||
| int | maxtime, | |||
| char * | fmt, | |||
| int | outsidecaller, | |||
| struct ast_vm_user * | vmu, | |||
| int * | duration, | |||
| const char * | unlockdir, | |||
| signed char | record_gain, | |||
| struct vm_state * | vms, | |||
| char * | flag | |||
| ) | [static] |
Definition at line 11250 of file app_voicemail.c.
References acceptdtmf, ast_channel_setoption(), ast_copy_string(), ast_debug, AST_DIGIT_ANY, ast_filedelete(), ast_filerename(), ast_log(), AST_LOG_WARNING, AST_OPTION_RXGAIN, ast_play_and_record_full(), ast_play_and_wait(), ast_stream_and_wait(), ast_strlen_zero(), ast_test_flag, ast_verb, ast_verbose, ast_waitfordigit(), ast_vm_user::context, DELETE, DISPOSE, INTRO, ast_vm_user::mailbox, STORE, VERBOSE_PREFIX_3, vm_exec(), VM_OPERATOR, and VM_REVIEW.
Referenced by leave_voicemail(), vm_forwardoptions(), vm_newuser(), vm_options(), and vm_tempgreeting().
11253 { 11254 /* Record message & let caller review or re-record it, or set options if applicable */ 11255 int res = 0; 11256 int cmd = 0; 11257 int max_attempts = 3; 11258 int attempts = 0; 11259 int recorded = 0; 11260 int msg_exists = 0; 11261 signed char zero_gain = 0; 11262 char tempfile[PATH_MAX]; 11263 char *acceptdtmf = "#"; 11264 char *canceldtmf = ""; 11265 11266 /* Note that urgent and private are for flagging messages as such in the future */ 11267 11268 /* barf if no pointer passed to store duration in */ 11269 if (duration == NULL) { 11270 ast_log(AST_LOG_WARNING, "Error play_record_review called without duration pointer\n"); 11271 return -1; 11272 } 11273 11274 if (!outsidecaller) 11275 snprintf(tempfile, sizeof(tempfile), "%s.tmp", recordfile); 11276 else 11277 ast_copy_string(tempfile, recordfile, sizeof(tempfile)); 11278 11279 cmd = '3'; /* Want to start by recording */ 11280 11281 while ((cmd >= 0) && (cmd != 't')) { 11282 switch (cmd) { 11283 case '1': 11284 if (!msg_exists) { 11285 /* In this case, 1 is to record a message */ 11286 cmd = '3'; 11287 break; 11288 } else { 11289 /* Otherwise 1 is to save the existing message */ 11290 ast_verb(3, "Saving message as is\n"); 11291 if (!outsidecaller) 11292 ast_filerename(tempfile, recordfile, NULL); 11293 ast_stream_and_wait(chan, "vm-msgsaved", ""); 11294 if (!outsidecaller) { 11295 /* Saves to IMAP server - but SHOULD save to filesystem ONLY if recording greetings! */ 11296 #ifndef IMAP_STORAGE 11297 STORE(recordfile, vmu->mailbox, vmu->context, -1, chan, vmu, fmt, *duration, vms, flag); 11298 DISPOSE(recordfile, -1); 11299 #endif 11300 } 11301 cmd = 't'; 11302 return res; 11303 } 11304 case '2': 11305 /* Review */ 11306 ast_verb(3, "Reviewing the message\n"); 11307 cmd = ast_stream_and_wait(chan, tempfile, AST_DIGIT_ANY); 11308 break; 11309 case '3': 11310 msg_exists = 0; 11311 /* Record */ 11312 if (recorded == 1) 11313 ast_verb(3, "Re-recording the message\n"); 11314 else 11315 ast_verb(3, "Recording the message\n"); 11316 11317 if (recorded && outsidecaller) { 11318 cmd = ast_play_and_wait(chan, INTRO); 11319 cmd = ast_play_and_wait(chan, "beep"); 11320 } 11321 recorded = 1; 11322 /* After an attempt has been made to record message, we have to take care of INTRO and beep for incoming messages, but not for greetings */ 11323 if (record_gain) 11324 ast_channel_setoption(chan, AST_OPTION_RXGAIN, &record_gain, sizeof(record_gain), 0); 11325 if (ast_test_flag(vmu, VM_OPERATOR)) 11326 canceldtmf = "0"; 11327 cmd = ast_play_and_record_full(chan, playfile, tempfile, maxtime, fmt, duration, silencethreshold, maxsilence, unlockdir, acceptdtmf, canceldtmf); 11328 if (record_gain) 11329 ast_channel_setoption(chan, AST_OPTION_RXGAIN, &zero_gain, sizeof(zero_gain), 0); 11330 if (cmd == -1) { 11331 /* User has hung up, no options to give */ 11332 if (!outsidecaller) { 11333 /* user was recording a greeting and they hung up, so let's delete the recording. */ 11334 ast_filedelete(tempfile, NULL); 11335 } 11336 return cmd; 11337 } 11338 if (cmd == '0') { 11339 break; 11340 } else if (cmd == '*') { 11341 break; 11342 #if 0 11343 } else if (vmu->review && (*duration < 5)) { 11344 /* Message is too short */ 11345 ast_verb(3, "Message too short\n"); 11346 cmd = ast_play_and_wait(chan, "vm-tooshort"); 11347 cmd = ast_filedelete(tempfile, NULL); 11348 break; 11349 } else if (vmu->review && (cmd == 2 && *duration < (maxsilence + 3))) { 11350 /* Message is all silence */ 11351 ast_verb(3, "Nothing recorded\n"); 11352 cmd = ast_filedelete(tempfile, NULL); 11353 cmd = ast_play_and_wait(chan, "vm-nothingrecorded"); 11354 if (!cmd) 11355 cmd = ast_play_and_wait(chan, "vm-speakup"); 11356 break; 11357 #endif 11358 } else { 11359 /* If all is well, a message exists */ 11360 msg_exists = 1; 11361 cmd = 0; 11362 } 11363 break; 11364 case '4': 11365 if (outsidecaller) { /* only mark vm messages */ 11366 /* Mark Urgent */ 11367 if ((flag && ast_strlen_zero(flag)) || (!ast_strlen_zero(flag) && strcmp(flag, "Urgent"))) { 11368 ast_verbose(VERBOSE_PREFIX_3 "marking message as Urgent\n"); 11369 ast_debug(1000, "This message is too urgent!\n"); 11370 res = ast_play_and_wait(chan, "vm-marked-urgent"); 11371 strcpy(flag, "Urgent"); 11372 } else if (flag) { 11373 ast_verbose(VERBOSE_PREFIX_3 "UNmarking message as Urgent\n"); 11374 res = ast_play_and_wait(chan, "vm-urgent-removed"); 11375 strcpy(flag, ""); 11376 } else { 11377 ast_play_and_wait(chan, "vm-sorry"); 11378 } 11379 cmd = 0; 11380 } else { 11381 cmd = ast_play_and_wait(chan, "vm-sorry"); 11382 } 11383 break; 11384 case '5': 11385 case '6': 11386 case '7': 11387 case '8': 11388 case '9': 11389 case '*': 11390 case '#': 11391 cmd = ast_play_and_wait(chan, "vm-sorry"); 11392 break; 11393 #if 0 11394 /* XXX Commented out for the moment because of the dangers of deleting 11395 a message while recording (can put the message numbers out of sync) */ 11396 case '*': 11397 /* Cancel recording, delete message, offer to take another message*/ 11398 cmd = ast_play_and_wait(chan, "vm-deleted"); 11399 cmd = ast_filedelete(tempfile, NULL); 11400 if (outsidecaller) { 11401 res = vm_exec(chan, NULL); 11402 return res; 11403 } 11404 else 11405 return 1; 11406 #endif 11407 case '0': 11408 if (!ast_test_flag(vmu, VM_OPERATOR)) { 11409 cmd = ast_play_and_wait(chan, "vm-sorry"); 11410 break; 11411 } 11412 if (msg_exists || recorded) { 11413 cmd = ast_play_and_wait(chan, "vm-saveoper"); 11414 if (!cmd) 11415 cmd = ast_waitfordigit(chan, 3000); 11416 if (cmd == '1') { 11417 ast_play_and_wait(chan, "vm-msgsaved"); 11418 cmd = '0'; 11419 } else if (cmd == '4') { 11420 if (flag) { 11421 ast_play_and_wait(chan, "vm-marked-urgent"); 11422 strcpy(flag, "Urgent"); 11423 } 11424 ast_play_and_wait(chan, "vm-msgsaved"); 11425 cmd = '0'; 11426 } else { 11427 ast_play_and_wait(chan, "vm-deleted"); 11428 DELETE(recordfile, -1, recordfile, vmu); 11429 cmd = '0'; 11430 } 11431 } 11432 return cmd; 11433 default: 11434 /* If the caller is an ouside caller, and the review option is enabled, 11435 allow them to review the message, but let the owner of the box review 11436 their OGM's */ 11437 if (outsidecaller && !ast_test_flag(vmu, VM_REVIEW)) 11438 return cmd; 11439 if (msg_exists) { 11440 cmd = ast_play_and_wait(chan, "vm-review"); 11441 if (!cmd && outsidecaller) { 11442 if ((flag && ast_strlen_zero(flag)) || (!ast_strlen_zero(flag) && strcmp(flag, "Urgent"))) { 11443 cmd = ast_play_and_wait(chan, "vm-review-urgent"); 11444 } else if (flag) { 11445 cmd = ast_play_and_wait(chan, "vm-review-nonurgent"); 11446 } 11447 } 11448 } else { 11449 cmd = ast_play_and_wait(chan, "vm-torerecord"); 11450 if (!cmd) 11451 cmd = ast_waitfordigit(chan, 600); 11452 } 11453 11454 if (!cmd && outsidecaller && ast_test_flag(vmu, VM_OPERATOR)) { 11455 cmd = ast_play_and_wait(chan, "vm-reachoper"); 11456 if (!cmd) 11457 cmd = ast_waitfordigit(chan, 600); 11458 } 11459 #if 0 11460 if (!cmd) 11461 cmd = ast_play_and_wait(chan, "vm-tocancelmsg"); 11462 #endif 11463 if (!cmd) 11464 cmd = ast_waitfordigit(chan, 6000); 11465 if (!cmd) { 11466 attempts++; 11467 } 11468 if (attempts > max_attempts) { 11469 cmd = 't'; 11470 } 11471 } 11472 } 11473 if (outsidecaller) 11474 ast_play_and_wait(chan, "vm-goodbye"); 11475 if (cmd == 't') 11476 cmd = 0; 11477 return cmd; 11478 }
| static void poll_subscribed_mailboxes | ( | void | ) | [static] |
Definition at line 9926 of file app_voicemail.c.
References AST_RWLIST_RDLOCK, AST_RWLIST_TRAVERSE, AST_RWLIST_UNLOCK, ast_strlen_zero(), mwi_sub::entry, inboxcount2(), mwi_sub::mailbox, mwi_sub::old_new, mwi_sub::old_old, mwi_sub::old_urgent, and queue_mwi_event().
Referenced by mb_poll_thread().
09927 { 09928 struct mwi_sub *mwi_sub; 09929 09930 AST_RWLIST_RDLOCK(&mwi_subs); 09931 AST_RWLIST_TRAVERSE(&mwi_subs, mwi_sub, entry) { 09932 int new = 0, old = 0, urgent = 0; 09933 09934 if (ast_strlen_zero(mwi_sub->mailbox)) 09935 continue; 09936 09937 inboxcount2(mwi_sub->mailbox, &urgent, &new, &old); 09938 09939 if (urgent != mwi_sub->old_urgent || new != mwi_sub->old_new || old != mwi_sub->old_old) { 09940 mwi_sub->old_urgent = urgent; 09941 mwi_sub->old_new = new; 09942 mwi_sub->old_old = old; 09943 queue_mwi_event(mwi_sub->mailbox, urgent, new, old); 09944 } 09945 } 09946 AST_RWLIST_UNLOCK(&mwi_subs); 09947 }
| static void populate_defaults | ( | struct ast_vm_user * | vmu | ) | [static] |
Sets default voicemail system options to a voicemail user.
This applies select global settings to a newly created (dynamic) instance of a voicemail user.
Definition at line 738 of file app_voicemail.c.
References ast_copy_flags, ast_copy_string(), AST_FLAGS_ALL, ast_vm_user::callback, callcontext, dialcontext, ast_vm_user::dialout, ast_vm_user::exit, exitcontext, globalflags, ast_vm_user::maxdeletedmsg, ast_vm_user::maxmsg, ast_vm_user::maxsecs, ast_vm_user::saydurationm, saydurationminfo, ast_vm_user::volgain, and ast_vm_user::zonetag.
Referenced by append_mailbox(), find_user_realtime(), and load_config().
00739 { 00740 ast_copy_flags(vmu, (&globalflags), AST_FLAGS_ALL); 00741 if (saydurationminfo) 00742 vmu->saydurationm = saydurationminfo; 00743 ast_copy_string(vmu->callback, callcontext, sizeof(vmu->callback)); 00744 ast_copy_string(vmu->dialout, dialcontext, sizeof(vmu->dialout)); 00745 ast_copy_string(vmu->exit, exitcontext, sizeof(vmu->exit)); 00746 ast_copy_string(vmu->zonetag, zonetag, sizeof(vmu->zonetag)); 00747 if (vmmaxsecs) 00748 vmu->maxsecs = vmmaxsecs; 00749 if (maxmsg) 00750 vmu->maxmsg = maxmsg; 00751 if (maxdeletedmsg) 00752 vmu->maxdeletedmsg = maxdeletedmsg; 00753 vmu->volgain = volgain; 00754 }
| static void prep_email_sub_vars | ( | struct ast_channel * | ast, | |
| struct ast_vm_user * | vmu, | |||
| int | msgnum, | |||
| char * | context, | |||
| char * | mailbox, | |||
| const char * | fromfolder, | |||
| char * | cidnum, | |||
| char * | cidname, | |||
| char * | dur, | |||
| char * | date, | |||
| char * | passdata, | |||
| size_t | passdatasize, | |||
| const char * | category, | |||
| const char * | flag | |||
| ) | [static] |
Definition at line 3731 of file app_voicemail.c.
References ast_callerid_merge(), ast_callerid_split(), ast_config_destroy(), ast_config_load, ast_localtime(), ast_log(), ast_strdupa, ast_strftime(), ast_strlen_zero(), ast_variable_retrieve(), CONFIG_FLAG_NOCACHE, ast_vm_user::context, emaildateformat, ast_vm_user::fullname, LOG_DEBUG, ast_vm_user::mailbox, make_dir(), make_file(), option_debug, and pbx_builtin_setvar_helper().
Referenced by make_email_file(), and sendpage().
03732 { 03733 char callerid[256]; 03734 char fromdir[256], fromfile[256]; 03735 struct ast_config *msg_cfg; 03736 const char *origcallerid, *origtime; 03737 char origcidname[80], origcidnum[80], origdate[80]; 03738 int inttime; 03739 struct ast_flags config_flags = { CONFIG_FLAG_NOCACHE }; 03740 03741 /* Prepare variables for substitution in email body and subject */ 03742 pbx_builtin_setvar_helper(ast, "VM_NAME", vmu->fullname); 03743 pbx_builtin_setvar_helper(ast, "VM_DUR", dur); 03744 snprintf(passdata, passdatasize, "%d", msgnum); 03745 pbx_builtin_setvar_helper(ast, "VM_MSGNUM", passdata); 03746 pbx_builtin_setvar_helper(ast, "VM_CONTEXT", context); 03747 pbx_builtin_setvar_helper(ast, "VM_MAILBOX", mailbox); 03748 pbx_builtin_setvar_helper(ast, "VM_CALLERID", (!ast_strlen_zero(cidname) || !ast_strlen_zero(cidnum)) ? 03749 ast_callerid_merge(callerid, sizeof(callerid), cidname, cidnum, NULL) : "an unknown caller"); 03750 pbx_builtin_setvar_helper(ast, "VM_CIDNAME", (!ast_strlen_zero(cidname) ? cidname : "an unknown caller")); 03751 pbx_builtin_setvar_helper(ast, "VM_CIDNUM", (!ast_strlen_zero(cidnum) ? cidnum : "an unknown caller")); 03752 pbx_builtin_setvar_helper(ast, "VM_DATE", date); 03753 pbx_builtin_setvar_helper(ast, "VM_CATEGORY", category ? ast_strdupa(category) : "no category"); 03754 pbx_builtin_setvar_helper(ast, "VM_FLAG", flag); 03755 03756 /* Retrieve info from VM attribute file */ 03757 make_dir(fromdir, sizeof(fromdir), vmu->context, vmu->mailbox, fromfolder); 03758 make_file(fromfile, sizeof(fromfile), fromdir, msgnum - 1); 03759 if (strlen(fromfile) < sizeof(fromfile) - 5) { 03760 strcat(fromfile, ".txt"); 03761 } 03762 if (!(msg_cfg = ast_config_load(fromfile, config_flags))) { 03763 if (option_debug > 0) { 03764 ast_log(LOG_DEBUG, "Config load for message text file '%s' failed\n", fromfile); 03765 } 03766 return; 03767 } 03768 03769 if ((origcallerid = ast_variable_retrieve(msg_cfg, "message", "callerid"))) { 03770 pbx_builtin_setvar_helper(ast, "ORIG_VM_CALLERID", origcallerid); 03771 ast_callerid_split(origcallerid, origcidname, sizeof(origcidname), origcidnum, sizeof(origcidnum)); 03772 pbx_builtin_setvar_helper(ast, "ORIG_VM_CIDNAME", origcidname); 03773 pbx_builtin_setvar_helper(ast, "ORIG_VM_CIDNUM", origcidnum); 03774 } 03775 03776 if ((origtime = ast_variable_retrieve(msg_cfg, "message", "origtime")) && sscanf(origtime, "%30d", &inttime) == 1) { 03777 struct timeval tv = { inttime, }; 03778 struct ast_tm tm; 03779 ast_localtime(&tv, &tm, NULL); 03780 ast_strftime(origdate, sizeof(origdate), emaildateformat, &tm); 03781 pbx_builtin_setvar_helper(ast, "ORIG_VM_DATE", origdate); 03782 } 03783 ast_config_destroy(msg_cfg); 03784 }
| static void queue_mwi_event | ( | const char * | box, | |
| int | urgent, | |||
| int | new, | |||
| int | old | |||
| ) | [static] |
Definition at line 6161 of file app_voicemail.c.
References AST_EVENT_IE_CONTEXT, AST_EVENT_IE_END, AST_EVENT_IE_MAILBOX, AST_EVENT_IE_NEWMSGS, AST_EVENT_IE_OLDMSGS, AST_EVENT_IE_PLTYPE_STR, AST_EVENT_IE_PLTYPE_UINT, AST_EVENT_MWI, ast_event_new(), ast_event_queue_and_cache(), ast_strdupa, ast_strlen_zero(), and strsep().
Referenced by append_mailbox(), notify_new_message(), poll_subscribed_mailboxes(), and vm_execmain().
06162 { 06163 struct ast_event *event; 06164 char *mailbox, *context; 06165 06166 /* Strip off @default */ 06167 context = mailbox = ast_strdupa(box); 06168 strsep(&context, "@"); 06169 if (ast_strlen_zero(context)) 06170 context = "default"; 06171 06172 if (!(event = ast_event_new(AST_EVENT_MWI, 06173 AST_EVENT_IE_MAILBOX, AST_EVENT_IE_PLTYPE_STR, mailbox, 06174 AST_EVENT_IE_CONTEXT, AST_EVENT_IE_PLTYPE_STR, context, 06175 AST_EVENT_IE_NEWMSGS, AST_EVENT_IE_PLTYPE_UINT, (new+urgent), 06176 AST_EVENT_IE_OLDMSGS, AST_EVENT_IE_PLTYPE_UINT, old, 06177 AST_EVENT_IE_END))) { 06178 return; 06179 } 06180 06181 ast_event_queue_and_cache(event); 06182 }
| static char* quote | ( | const char * | from, | |
| char * | to, | |||
| size_t | len | |||
| ) | [static] |
Wraps a character sequence in double quotes, escaping occurences of quotes within the string.
| from | The string to work with. | |
| to | The string to write the modified quoted string. This buffer should be sufficiently larger than the from string, so as to allow it to be expanded by the surrounding quotes and escaping of internal quotes. |
Definition at line 3793 of file app_voicemail.c.
Referenced by make_email_file().
03794 { 03795 char *ptr = to; 03796 *ptr++ = '"'; 03797 for (; ptr < to + len - 1; from++) { 03798 if (*from == '"') 03799 *ptr++ = '\\'; 03800 else if (*from == '\0') 03801 break; 03802 *ptr++ = *from; 03803 } 03804 if (ptr < to + len - 1) 03805 *ptr++ = '"'; 03806 *ptr = '\0'; 03807 return to; 03808 }
| static int reload | ( | void | ) | [static] |
Definition at line 10926 of file app_voicemail.c.
References load_config().
10927 { 10928 return load_config(1); 10929 }
| static void rename_file | ( | char * | sfn, | |
| char * | dfn | |||
| ) | [static] |
Renames a message in a mailbox folder.
| sfn | The path to the mailbox information and data file to be renamed. | |
| dfn | The path for where the message data and information files will be renamed to. |
This method is used by the RENAME macro when mailboxes are stored on the filesystem. (not ODBC and not IMAP).
Definition at line 3414 of file app_voicemail.c.
References ast_check_realtime(), ast_filerename(), ast_update_realtime(), and SENTINEL.
03415 { 03416 char stxt[PATH_MAX]; 03417 char dtxt[PATH_MAX]; 03418 ast_filerename(sfn,dfn,NULL); 03419 snprintf(stxt, sizeof(stxt), "%s.txt", sfn); 03420 snprintf(dtxt, sizeof(dtxt), "%s.txt", dfn); 03421 if (ast_check_realtime("voicemail_data")) { 03422 ast_update_realtime("voicemail_data", "filename", sfn, "filename", dfn, SENTINEL); 03423 } 03424 rename(stxt, dtxt); 03425 }
| static int reset_user_pw | ( | const char * | context, | |
| const char * | mailbox, | |||
| const char * | newpass | |||
| ) | [static] |
Resets a user password to a specified password.
| context | ||
| mailbox | ||
| newpass | This does the actual change password work, called by the vm_change_password() function. |
Definition at line 1134 of file app_voicemail.c.
References ast_copy_string(), AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_vm_user::context, ast_vm_user::mailbox, and ast_vm_user::password.
Referenced by vm_change_password(), and vm_change_password_shell().
01135 { 01136 /* This function could be made to generate one from a database, too */ 01137 struct ast_vm_user *cur; 01138 int res = -1; 01139 AST_LIST_LOCK(&users); 01140 AST_LIST_TRAVERSE(&users, cur, list) { 01141 if ((!context || !strcasecmp(context, cur->context)) && 01142 (!strcasecmp(mailbox, cur->mailbox))) 01143 break; 01144 } 01145 if (cur) { 01146 ast_copy_string(cur->password, newpass, sizeof(cur->password)); 01147 res = 0; 01148 } 01149 AST_LIST_UNLOCK(&users); 01150 return res; 01151 }
| static void run_externnotify | ( | char * | context, | |
| char * | extension, | |||
| const char * | flag | |||
| ) | [static] |
Definition at line 4816 of file app_voicemail.c.
References ast_app_has_voicemail(), ast_copy_string(), ast_debug, ast_log(), AST_LOG_ERROR, AST_LOG_WARNING, ast_safe_system(), ast_smdi_mwi_message_destroy(), ast_smdi_mwi_message_wait_station(), ast_smdi_mwi_set(), ast_smdi_mwi_unset(), ast_strlen_zero(), ASTOBJ_UNREF, ast_smdi_mwi_message::cause, ast_smdi_mwi_message::fwd_st, inboxcount2(), and SMDI_MWI_WAIT_TIMEOUT.
Referenced by forward_message(), notify_new_message(), and vm_execmain().
04817 { 04818 char arguments[255]; 04819 char ext_context[256] = ""; 04820 int newvoicemails = 0, oldvoicemails = 0, urgentvoicemails = 0; 04821 struct ast_smdi_mwi_message *mwi_msg; 04822 04823 if (!ast_strlen_zero(context)) 04824 snprintf(ext_context, sizeof(ext_context), "%s@%s", extension, context); 04825 else 04826 ast_copy_string(ext_context, extension, sizeof(ext_context)); 04827 04828 if (smdi_iface) { 04829 if (ast_app_has_voicemail(ext_context, NULL)) 04830 ast_smdi_mwi_set(smdi_iface, extension); 04831 else 04832 ast_smdi_mwi_unset(smdi_iface, extension); 04833 04834 if ((mwi_msg = ast_smdi_mwi_message_wait_station(smdi_iface, SMDI_MWI_WAIT_TIMEOUT, extension))) { 04835 ast_log(AST_LOG_ERROR, "Error executing SMDI MWI change for %s\n", extension); 04836 if (!strncmp(mwi_msg->cause, "INV", 3)) 04837 ast_log(AST_LOG_ERROR, "Invalid MWI extension: %s\n", mwi_msg->fwd_st); 04838 else if (!strncmp(mwi_msg->cause, "BLK", 3)) 04839 ast_log(AST_LOG_WARNING, "MWI light was already on or off for %s\n", mwi_msg->fwd_st); 04840 ast_log(AST_LOG_WARNING, "The switch reported '%s'\n", mwi_msg->cause); 04841 ASTOBJ_UNREF(mwi_msg, ast_smdi_mwi_message_destroy); 04842 } else { 04843 ast_debug(1, "Successfully executed SMDI MWI change for %s\n", extension); 04844 } 04845 } 04846 04847 if (!ast_strlen_zero(externnotify)) { 04848 if (inboxcount2(ext_context, &urgentvoicemails, &newvoicemails, &oldvoicemails)) { 04849 ast_log(AST_LOG_ERROR, "Problem in calculating number of voicemail messages available for extension %s\n", extension); 04850 } else { 04851 snprintf(arguments, sizeof(arguments), "%s %s %s %d %d %d &", externnotify, context, extension, newvoicemails, oldvoicemails, urgentvoicemails); 04852 ast_debug(1, "Executing %s\n", arguments); 04853 ast_safe_system(arguments); 04854 } 04855 } 04856 }
| static int save_to_folder | ( | struct ast_vm_user * | vmu, | |
| struct vm_state * | vms, | |||
| int | msg, | |||
| int | box | |||
| ) | [static] |
Definition at line 5390 of file app_voicemail.c.
References ast_debug, ast_log(), AST_LOG_NOTICE, ast_mutex_lock(), ast_mutex_unlock(), ast_unlock_path(), ast_vm_user::context, COPY, create_dirpath(), vm_state::curbox, vm_state::curdir, ERROR_LOCK_PATH, EXISTS, last_message_index(), ast_vm_user::mailbox, make_file(), ast_vm_user::maxdeletedmsg, ast_vm_user::maxmsg, mbox(), NEW_FOLDER, OLD_FOLDER, RENAME, vm_state::username, and vm_lock_path().
Referenced by close_mailbox(), and vm_execmain().
05391 { 05392 #ifdef IMAP_STORAGE 05393 /* we must use mbox(x) folder names, and copy the message there */ 05394 /* simple. huh? */ 05395 char sequence[10]; 05396 char mailbox[256]; 05397 int res; 05398 05399 /* get the real IMAP message number for this message */ 05400 snprintf(sequence, sizeof(sequence), "%ld", vms->msgArray[msg]); 05401 05402 ast_debug(3, "Copying sequence %s to mailbox %s\n", sequence, mbox(box)); 05403 ast_mutex_lock(&vms->lock); 05404 /* if save to Old folder, put in INBOX as read */ 05405 if (box == OLD_FOLDER) { 05406 mail_setflag(vms->mailstream, sequence, "\\Seen"); 05407 mail_clearflag(vms->mailstream, sequence, "\\Unseen"); 05408 } else if (box == NEW_FOLDER) { 05409 mail_setflag(vms->mailstream, sequence, "\\Unseen"); 05410 mail_clearflag(vms->mailstream, sequence, "\\Seen"); 05411 } 05412 if (!strcasecmp(mbox(NEW_FOLDER), vms->curbox) && (box == NEW_FOLDER || box == OLD_FOLDER)) { 05413 ast_mutex_unlock(&vms->lock); 05414 return 0; 05415 } 05416 /* Create the folder if it don't exist */ 05417 imap_mailbox_name(mailbox, sizeof(mailbox), vms, box, 1); /* Get the full mailbox name */ 05418 ast_debug(5, "Checking if folder exists: %s\n",mailbox); 05419 if (mail_create(vms->mailstream, mailbox) == NIL) 05420 ast_debug(5, "Folder exists.\n"); 05421 else 05422 ast_log(AST_LOG_NOTICE, "Folder %s created!\n",mbox(box)); 05423 res = !mail_copy(vms->mailstream, sequence, (char *)mbox(box)); 05424 ast_mutex_unlock(&vms->lock); 05425 return res; 05426 #else 05427 char *dir = vms->curdir; 05428 char *username = vms->username; 05429 char *context = vmu->context; 05430 char sfn[PATH_MAX]; 05431 char dfn[PATH_MAX]; 05432 char ddir[PATH_MAX]; 05433 const char *dbox = mbox(box); 05434 int x, i; 05435 create_dirpath(ddir, sizeof(ddir), context, username, dbox); 05436 05437 if (vm_lock_path(ddir)) 05438 return ERROR_LOCK_PATH; 05439 05440 x = last_message_index(vmu, ddir) + 1; 05441 05442 if (box == 10 && x >= vmu->maxdeletedmsg) { /* "Deleted" folder*/ 05443 x--; 05444 for (i = 1; i <= x; i++) { 05445 /* Push files down a "slot". The oldest file (msg0000) will be deleted. */ 05446 make_file(sfn, sizeof(sfn), ddir, i); 05447 make_file(dfn, sizeof(dfn), ddir, i - 1); 05448 if (EXISTS(ddir, i, sfn, NULL)) { 05449 RENAME(ddir, i, vmu->mailbox, vmu->context, ddir, i - 1, sfn, dfn); 05450 } else 05451 break; 05452 } 05453 } else { 05454 if (x >= vmu->maxmsg) { 05455 ast_unlock_path(ddir); 05456 return -1; 05457 } 05458 } 05459 make_file(sfn, sizeof(sfn), dir, msg); 05460 make_file(dfn, sizeof(dfn), ddir, x); 05461 if (strcmp(sfn, dfn)) { 05462 COPY(dir, msg, ddir, x, username, context, sfn, dfn); 05463 } 05464 ast_unlock_path(ddir); 05465 #endif 05466 return 0; 05467 }
| static int say_and_wait | ( | struct ast_channel * | chan, | |
| int | num, | |||
| const char * | language | |||
| ) | [static] |
Definition at line 5383 of file app_voicemail.c.
References AST_DIGIT_ANY, and ast_say_number().
Referenced by play_message_duration(), vm_execmain(), vm_intro_cz(), vm_intro_de(), vm_intro_en(), vm_intro_es(), vm_intro_fr(), vm_intro_it(), vm_intro_nl(), vm_intro_no(), vm_intro_pl(), vm_intro_se(), and vm_intro_zh().
05384 { 05385 int d; 05386 d = ast_say_number(chan, num, AST_DIGIT_ANY, language, NULL); 05387 return d; 05388 }
| static int sayname | ( | struct ast_channel * | chan, | |
| const char * | mailbox, | |||
| const char * | context | |||
| ) | [static] |
Definition at line 10912 of file app_voicemail.c.
References ast_debug, AST_DIGIT_ANY, ast_fileexists(), ast_stream_and_wait(), DISPOSE, and RETRIEVE.
Referenced by load_module().
10913 { 10914 int res = -1; 10915 char dir[PATH_MAX]; 10916 snprintf(dir, sizeof(dir), "%s%s/%s/greet", VM_SPOOL_DIR, context, mailbox); 10917 ast_debug(2, "About to try retrieving name file %s\n", dir); 10918 RETRIEVE(dir, -1, mailbox, context); 10919 if (ast_fileexists(dir, NULL, NULL)) { 10920 res = ast_stream_and_wait(chan, dir, AST_DIGIT_ANY); 10921 } 10922 DISPOSE(dir, -1); 10923 return res; 10924 }
| static int sendmail | ( | char * | srcemail, | |
| struct ast_vm_user * | vmu, | |||
| int | msgnum, | |||
| char * | context, | |||
| char * | mailbox, | |||
| const char * | fromfolder, | |||
| char * | cidnum, | |||
| char * | cidname, | |||
| char * | attach, | |||
| char * | attach2, | |||
| char * | format, | |||
| int | duration, | |||
| int | attach_user_voicemail, | |||
| struct ast_channel * | chan, | |||
| const char * | category, | |||
| const char * | flag | |||
| ) | [static] |
Definition at line 4237 of file app_voicemail.c.
References ast_debug, ast_log(), AST_LOG_WARNING, ast_safe_system(), ast_strlen_zero(), ast_test_flag, ast_vm_user::email, globalflags, ast_vm_user::mailbox, make_email_file(), VM_ATTACH, and vm_mkftemp().
Referenced by forward_message(), and notify_new_message().
04238 { 04239 FILE *p=NULL; 04240 char tmp[80] = "/tmp/astmail-XXXXXX"; 04241 char tmp2[256]; 04242 04243 if (vmu && ast_strlen_zero(vmu->email)) { 04244 ast_log(AST_LOG_WARNING, "E-mail address missing for mailbox [%s]. E-mail will not be sent.\n", vmu->mailbox); 04245 return(0); 04246 } 04247 if (!strcmp(format, "wav49")) 04248 format = "WAV"; 04249 ast_debug(3, "Attaching file '%s', format '%s', uservm is '%d', global is %d\n", attach, format, attach_user_voicemail, ast_test_flag((&globalflags), VM_ATTACH)); 04250 /* Make a temporary file instead of piping directly to sendmail, in case the mail 04251 command hangs */ 04252 if ((p = vm_mkftemp(tmp)) == NULL) { 04253 ast_log(AST_LOG_WARNING, "Unable to launch '%s' (can't create temporary file)\n", mailcmd); 04254 return -1; 04255 } else { 04256 make_email_file(p, srcemail, vmu, msgnum, context, mailbox, fromfolder, cidnum, cidname, attach, attach2, format, duration, attach_user_voicemail, chan, category, 0, flag); 04257 fclose(p); 04258 snprintf(tmp2, sizeof(tmp2), "( %s < %s ; rm -f %s ) &", mailcmd, tmp, tmp); 04259 ast_safe_system(tmp2); 04260 ast_debug(1, "Sent mail to %s with command '%s'\n", vmu->email, mailcmd); 04261 } 04262 return 0; 04263 }
| static int sendpage | ( | char * | srcemail, | |
| char * | pager, | |||
| int | msgnum, | |||
| char * | context, | |||
| char * | mailbox, | |||
| const char * | fromfolder, | |||
| char * | cidnum, | |||
| char * | cidname, | |||
| int | duration, | |||
| struct ast_vm_user * | vmu, | |||
| const char * | category, | |||
| const char * | flag | |||
| ) | [static] |
Definition at line 4265 of file app_voicemail.c.
References ast_channel_alloc, ast_channel_free(), ast_copy_string(), ast_debug, ast_log(), AST_LOG_WARNING, ast_safe_system(), AST_STATE_DOWN, ast_strftime(), ast_strlen_zero(), fromstring, MAXHOSTNAMELEN, pagerbody, pagerfromstring, pagersubject, pbx_substitute_variables_helper(), prep_email_sub_vars(), vm_mkftemp(), and vmu_tm().
Referenced by notify_new_message().
04266 { 04267 char date[256]; 04268 char host[MAXHOSTNAMELEN] = ""; 04269 char who[256]; 04270 char dur[PATH_MAX]; 04271 char tmp[80] = "/tmp/astmail-XXXXXX"; 04272 char tmp2[PATH_MAX]; 04273 struct ast_tm tm; 04274 FILE *p; 04275 04276 if ((p = vm_mkftemp(tmp)) == NULL) { 04277 ast_log(AST_LOG_WARNING, "Unable to launch '%s' (can't create temporary file)\n", mailcmd); 04278 return -1; 04279 } 04280 gethostname(host, sizeof(host)-1); 04281 if (strchr(srcemail, '@')) 04282 ast_copy_string(who, srcemail, sizeof(who)); 04283 else 04284 snprintf(who, sizeof(who), "%s@%s", srcemail, host); 04285 snprintf(dur, sizeof(dur), "%d:%02d", duration / 60, duration % 60); 04286 ast_strftime(date, sizeof(date), "%a, %d %b %Y %H:%M:%S %z", vmu_tm(vmu, &tm)); 04287 fprintf(p, "Date: %s\n", date); 04288 04289 if (*pagerfromstring) { 04290 struct ast_channel *ast; 04291 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 04292 char *passdata; 04293 int vmlen = strlen(fromstring)*3 + 200; 04294 passdata = alloca(vmlen); 04295 memset(passdata, 0, vmlen); 04296 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, cidnum, cidname, dur, date, passdata, vmlen, category, flag); 04297 pbx_substitute_variables_helper(ast, pagerfromstring, passdata, vmlen); 04298 fprintf(p, "From: %s <%s>\n", passdata, who); 04299 ast_channel_free(ast); 04300 } else 04301 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 04302 } else 04303 fprintf(p, "From: Asterisk PBX <%s>\n", who); 04304 fprintf(p, "To: %s\n", pager); 04305 if (pagersubject) { 04306 struct ast_channel *ast; 04307 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 04308 char *passdata; 04309 int vmlen = strlen(pagersubject) * 3 + 200; 04310 passdata = alloca(vmlen); 04311 memset(passdata, 0, vmlen); 04312 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, cidnum, cidname, dur, date, passdata, vmlen, category, flag); 04313 pbx_substitute_variables_helper(ast, pagersubject, passdata, vmlen); 04314 fprintf(p, "Subject: %s\n\n", passdata); 04315 ast_channel_free(ast); 04316 } else 04317 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 04318 } else { 04319 if (ast_strlen_zero(flag)) { 04320 fprintf(p, "Subject: New VM\n\n"); 04321 } else { 04322 fprintf(p, "Subject: New %s VM\n\n", flag); 04323 } 04324 } 04325 04326 ast_strftime(date, sizeof(date), "%A, %B %d, %Y at %r", &tm); 04327 if (pagerbody) { 04328 struct ast_channel *ast; 04329 if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "", "", "", 0, "Substitution/voicemail"))) { 04330 char *passdata; 04331 int vmlen = strlen(pagerbody) * 3 + 200; 04332 passdata = alloca(vmlen); 04333 memset(passdata, 0, vmlen); 04334 prep_email_sub_vars(ast, vmu, msgnum + 1, context, mailbox, fromfolder, cidnum, cidname, dur, date, passdata, vmlen, category, flag); 04335 pbx_substitute_variables_helper(ast, pagerbody, passdata, vmlen); 04336 fprintf(p, "%s\n", passdata); 04337 ast_channel_free(ast); 04338 } else 04339 ast_log(AST_LOG_WARNING, "Cannot allocate the channel for variables substitution\n"); 04340 } else { 04341 fprintf(p, "New %s long %s msg in box %s\n" 04342 "from %s, on %s", dur, flag, mailbox, (cidname ? cidname : (cidnum ? cidnum : "unknown")), date); 04343 } 04344 fclose(p); 04345 snprintf(tmp2, sizeof(tmp2), "( %s < %s ; rm -f %s ) &", mailcmd, tmp, tmp); 04346 ast_safe_system(tmp2); 04347 ast_debug(1, "Sent page to %s with command '%s'\n", pager, mailcmd); 04348 return 0; 04349 }
| static char* show_users_realtime | ( | int | fd, | |
| const char * | context | |||
| ) | [static] |
Definition at line 9724 of file app_voicemail.c.
References ast_category_browse(), ast_cli(), ast_config_destroy(), ast_load_realtime_multientry(), ast_variable_browse(), CLI_FAILURE, CLI_SUCCESS, ast_variable::name, ast_variable::next, SENTINEL, and ast_variable::value.
Referenced by handle_voicemail_show_users().
09725 { 09726 struct ast_config *cfg; 09727 const char *cat = NULL; 09728 09729 if (!(cfg = ast_load_realtime_multientry("voicemail", 09730 "context", context, SENTINEL))) { 09731 return CLI_FAILURE; 09732 } 09733 09734 ast_cli(fd, 09735 "\n" 09736 "=============================================================\n" 09737 "=== Configured Voicemail Users ==============================\n" 09738 "=============================================================\n" 09739 "===\n"); 09740 09741 while ((cat = ast_category_browse(cfg, cat))) { 09742 struct ast_variable *var = NULL; 09743 ast_cli(fd, 09744 "=== Mailbox ...\n" 09745 "===\n"); 09746 for (var = ast_variable_browse(cfg, cat); var; var = var->next) 09747 ast_cli(fd, "=== ==> %s: %s\n", var->name, var->value); 09748 ast_cli(fd, 09749 "===\n" 09750 "=== ---------------------------------------------------------\n" 09751 "===\n"); 09752 } 09753 09754 ast_cli(fd, 09755 "=============================================================\n" 09756 "\n"); 09757 09758 ast_config_destroy(cfg); 09759 09760 return CLI_SUCCESS; 09761 }
| static void start_poll_thread | ( | void | ) | [static] |
Definition at line 10072 of file app_voicemail.c.
References AST_EVENT_IE_END, AST_EVENT_IE_EVENTTYPE, AST_EVENT_IE_PLTYPE_UINT, AST_EVENT_MWI, ast_event_report_subs(), AST_EVENT_SUB, ast_event_subscribe(), AST_EVENT_UNSUB, ast_pthread_create, mb_poll_thread(), mwi_sub_event_cb(), and mwi_unsub_event_cb().
Referenced by load_config().
10073 { 10074 mwi_sub_sub = ast_event_subscribe(AST_EVENT_SUB, mwi_sub_event_cb, NULL, 10075 AST_EVENT_IE_EVENTTYPE, AST_EVENT_IE_PLTYPE_UINT, AST_EVENT_MWI, 10076 AST_EVENT_IE_END); 10077 10078 mwi_unsub_sub = ast_event_subscribe(AST_EVENT_UNSUB, mwi_unsub_event_cb, NULL, 10079 AST_EVENT_IE_EVENTTYPE, AST_EVENT_IE_PLTYPE_UINT, AST_EVENT_MWI, 10080 AST_EVENT_IE_END); 10081 10082 if (mwi_sub_sub) 10083 ast_event_report_subs(mwi_sub_sub); 10084 10085 poll_thread_run = 1; 10086 10087 ast_pthread_create(&poll_thread, NULL, mb_poll_thread, NULL); 10088 }
| static void stop_poll_thread | ( | void | ) | [static] |
Definition at line 10090 of file app_voicemail.c.
References ast_cond_signal(), ast_event_unsubscribe(), ast_mutex_lock(), ast_mutex_unlock(), AST_PTHREADT_NULL, and poll_lock.
Referenced by load_config(), and unload_module().
10091 { 10092 poll_thread_run = 0; 10093 10094 if (mwi_sub_sub) { 10095 ast_event_unsubscribe(mwi_sub_sub); 10096 mwi_sub_sub = NULL; 10097 } 10098 10099 if (mwi_unsub_sub) { 10100 ast_event_unsubscribe(mwi_unsub_sub); 10101 mwi_unsub_sub = NULL; 10102 } 10103 10104 ast_mutex_lock(&poll_lock); 10105 ast_cond_signal(&poll_cond); 10106 ast_mutex_unlock(&poll_lock); 10107 10108 pthread_join(poll_thread, NULL); 10109 10110 poll_thread = AST_PTHREADT_NULL; 10111 }
| static char* strip_control | ( | const char * | input, | |
| char * | buf, | |||
| size_t | buflen | |||
| ) | [static] |
Definition at line 709 of file app_voicemail.c.
Referenced by make_email_file().
| static char* substitute_escapes | ( | const char * | value | ) | [static] |
Definition at line 10236 of file app_voicemail.c.
References ast_free, ast_log(), AST_LOG_NOTICE, ast_str_append(), ast_str_create(), ast_strdup, ast_str::str, and ast_str::used.
Referenced by load_config().
10237 { 10238 char *current, *result; 10239 10240 /* Add 16 for fudge factor */ 10241 struct ast_str *str = ast_str_create(strlen(value) + 16); 10242 10243 /* Substitute strings \r, \n, and \t into the appropriate characters */ 10244 for (current = (char *) value; *current; current++) { 10245 if (*current == '\\') { 10246 current++; 10247 if (!*current) { 10248 ast_log(AST_LOG_NOTICE, "Incomplete escape at end of value.\n"); 10249 break; 10250 } 10251 switch (*current) { 10252 case 'r': 10253 ast_str_append(&str, 0, "\r"); 10254 break; 10255 case 'n': 10256 #ifdef IMAP_STORAGE 10257 if (!str->used || str->str[str->used - 1] != '\r') { 10258 ast_str_append(&str, 0, "\r"); 10259 } 10260 #endif 10261 ast_str_append(&str, 0, "\n"); 10262 break; 10263 case 't': 10264 ast_str_append(&str, 0, "\t"); 10265 break; 10266 default: 10267 ast_log(AST_LOG_NOTICE, "Substitution routine does not support this character: \\%c\n", *current); 10268 break; 10269 } 10270 } else { 10271 ast_str_append(&str, 0, "%c", *current); 10272 } 10273 } 10274 10275 result = ast_strdup(str->str); 10276 ast_free(str); 10277 10278 return result; 10279 }
| static int unload_module | ( | void | ) | [static] |
Definition at line 10931 of file app_voicemail.c.
References ast_cli_unregister_multiple(), ast_custom_function_unregister(), ast_manager_unregister(), AST_PTHREADT_NULL, ast_taskprocessor_unreference(), ast_uninstall_vm_functions(), ast_unload_realtime(), ast_unregister_application(), cli_voicemail, free_vm_users(), free_vm_zones(), mailbox_exists_acf, mwi_subscription_tps, and stop_poll_thread().
10932 { 10933 int res; 10934 10935 res = ast_unregister_application(app); 10936 res |= ast_unregister_application(app2); 10937 res |= ast_unregister_application(app3); 10938 res |= ast_unregister_application(app4); 10939 res |= ast_custom_function_unregister(&mailbox_exists_acf); 10940 res |= ast_manager_unregister("VoicemailUsersList"); 10941 ast_cli_unregister_multiple(cli_voicemail, sizeof(cli_voicemail) / sizeof(struct ast_cli_entry)); 10942 ast_uninstall_vm_functions(); 10943 10944 if (poll_thread != AST_PTHREADT_NULL) 10945 stop_poll_thread(); 10946 10947 mwi_subscription_tps = ast_taskprocessor_unreference(mwi_subscription_tps); 10948 ast_unload_realtime("voicemail"); 10949 ast_unload_realtime("voicemail_data"); 10950 10951 free_vm_users(); 10952 free_vm_zones(); 10953 return res; 10954 }
| static int vm_authenticate | ( | struct ast_channel * | chan, | |
| char * | mailbox, | |||
| int | mailbox_size, | |||
| struct ast_vm_user * | res_vmu, | |||
| const char * | context, | |||
| const char * | prefix, | |||
| int | skipuser, | |||
| int | max_logins, | |||
| int | silent | |||
| ) | [static] |
Definition at line 8679 of file app_voicemail.c.
References adsi_begin(), adsi_login(), adsi_password(), ast_copy_string(), ast_debug, ast_log(), AST_LOG_WARNING, AST_MAX_EXTENSION, ast_play_and_wait(), ast_readstring(), ast_stopstream(), ast_streamfile(), ast_strlen_zero(), ast_verb, ast_waitstream(), ast_channel::cid, ast_callerid::cid_num, find_user(), ast_vm_user::password, and vm_password.
Referenced by vm_execmain(), and vmauthenticate().
08682 { 08683 int useadsi=0, valid=0, logretries=0; 08684 char password[AST_MAX_EXTENSION]="", *passptr; 08685 struct ast_vm_user vmus, *vmu = NULL; 08686 08687 /* If ADSI is supported, setup login screen */ 08688 adsi_begin(chan, &useadsi); 08689 if (!skipuser && useadsi) 08690 adsi_login(chan); 08691 if (!silent && !skipuser && ast_streamfile(chan, "vm-login", chan->language)) { 08692 ast_log(AST_LOG_WARNING, "Couldn't stream login file\n"); 08693 return -1; 08694 } 08695 08696 /* Authenticate them and get their mailbox/password */ 08697 08698 while (!valid && (logretries < max_logins)) { 08699 /* Prompt for, and read in the username */ 08700 if (!skipuser && ast_readstring(chan, mailbox, mailbox_size - 1, 2000, 10000, "#") < 0) { 08701 ast_log(AST_LOG_WARNING, "Couldn't read username\n"); 08702 return -1; 08703 } 08704 if (ast_strlen_zero(mailbox)) { 08705 if (chan->cid.cid_num) { 08706 ast_copy_string(mailbox, chan->cid.cid_num, mailbox_size); 08707 } else { 08708 ast_verb(3,"Username not entered\n"); 08709 return -1; 08710 } 08711 } 08712 if (useadsi) 08713 adsi_password(chan); 08714 08715 if (!ast_strlen_zero(prefix)) { 08716 char fullusername[80] = ""; 08717 ast_copy_string(fullusername, prefix, sizeof(fullusername)); 08718 strncat(fullusername, mailbox, sizeof(fullusername) - 1 - strlen(fullusername)); 08719 ast_copy_string(mailbox, fullusername, mailbox_size); 08720 } 08721 08722 ast_debug(1, "Before find user for mailbox %s\n",mailbox); 08723 vmu = find_user(&vmus, context, mailbox); 08724 if (vmu && (vmu->password[0] == '\0' || (vmu->password[0] == '-' && vmu->password[1] == '\0'))) { 08725 /* saved password is blank, so don't bother asking */ 08726 password[0] = '\0'; 08727 } else { 08728 if (ast_streamfile(chan, vm_password, chan->language)) { 08729 ast_log(AST_LOG_WARNING, "Unable to stream password file\n"); 08730 return -1; 08731 } 08732 if (ast_readstring(chan, password, sizeof(password) - 1, 2000, 10000, "#") < 0) { 08733 ast_log(AST_LOG_WARNING, "Unable to read password\n"); 08734 return -1; 08735 } 08736 } 08737 08738 if (vmu) { 08739 passptr = vmu->password; 08740 if (passptr[0] == '-') passptr++; 08741 } 08742 if (vmu && !strcmp(passptr, password)) 08743 valid++; 08744 else { 08745 ast_verb(3, "Incorrect password '%s' for user '%s' (context = %s)\n", password, mailbox, context ? context : "default"); 08746 if (!ast_strlen_zero(prefix)) 08747 mailbox[0] = '\0'; 08748 } 08749 logretries++; 08750 if (!valid) { 08751 if (skipuser || logretries >= max_logins) { 08752 if (ast_streamfile(chan, "vm-incorrect", chan->language)) { 08753 ast_log(AST_LOG_WARNING, "Unable to stream incorrect message\n"); 08754 return -1; 08755 } 08756 } else { 08757 if (useadsi) 08758 adsi_login(chan); 08759 if (ast_streamfile(chan, "vm-incorrect-mailbox", chan->language)) { 08760 ast_log(AST_LOG_WARNING, "Unable to stream incorrect mailbox message\n"); 08761 return -1; 08762 } 08763 } 08764 if (ast_waitstream(chan, "")) /* Channel is hung up */ 08765 return -1; 08766 } 08767 } 08768 if (!valid && (logretries >= max_logins)) { 08769 ast_stopstream(chan); 08770 ast_play_and_wait(chan, "vm-goodbye"); 08771 return -1; 08772 } 08773 if (vmu && !skipuser) { 08774 memcpy(res_vmu, vmu, sizeof(struct ast_vm_user)); 08775 } 08776 return 0; 08777 }
| static int vm_box_exists | ( | struct ast_channel * | chan, | |
| void * | data | |||
| ) | [static] |
Definition at line 9619 of file app_voicemail.c.
References AST_APP_ARG, AST_DECLARE_APP_ARGS, ast_log(), AST_LOG_ERROR, AST_LOG_WARNING, AST_STANDARD_APP_ARGS, ast_strdupa, ast_strlen_zero(), find_user(), mbox(), and pbx_builtin_setvar_helper().
Referenced by load_module().
09620 { 09621 struct ast_vm_user svm; 09622 char *context, *box; 09623 AST_DECLARE_APP_ARGS(args, 09624 AST_APP_ARG(mbox); 09625 AST_APP_ARG(options); 09626 ); 09627 static int dep_warning = 0; 09628 09629 if (ast_strlen_zero(data)) { 09630 ast_log(AST_LOG_ERROR, "MailboxExists requires an argument: (vmbox[@context][|options])\n"); 09631 return -1; 09632 } 09633 09634 if (!dep_warning) { 09635 dep_warning = 1; 09636 ast_log(AST_LOG_WARNING, "MailboxExists is deprecated. Please use ${MAILBOX_EXISTS(%s)} instead.\n", (char *)data); 09637 } 09638 09639 box = ast_strdupa(data); 09640 09641 AST_STANDARD_APP_ARGS(args, box); 09642 09643 if (args.options) { 09644 } 09645 09646 if ((context = strchr(args.mbox, '@'))) { 09647 *context = '\0'; 09648 context++; 09649 } 09650 09651 if (find_user(&svm, context, args.mbox)) { 09652 pbx_builtin_setvar_helper(chan, "VMBOXEXISTSSTATUS", "SUCCESS"); 09653 } else 09654 pbx_builtin_setvar_helper(chan, "VMBOXEXISTSSTATUS", "FAILED"); 09655 09656 return 0; 09657 }
| static int vm_browse_messages | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Top level method to invoke the language variant vm_browse_messages_XX function.
| chan | The channel for the current user. We read the language property from this. | |
| vms | passed into the language-specific vm_browse_messages function. | |
| vmu | passed into the language-specific vm_browse_messages function. |
The method to be invoked is determined by the value of language code property in the user's channel. The default (when unable to match) is to use english.
Definition at line 8660 of file app_voicemail.c.
References vm_browse_messages_en(), vm_browse_messages_es(), vm_browse_messages_gr(), vm_browse_messages_he(), vm_browse_messages_it(), vm_browse_messages_pt(), and vm_browse_messages_zh().
Referenced by vm_execmain().
08661 { 08662 if (!strcasecmp(chan->language, "es")) { /* SPANISH */ 08663 return vm_browse_messages_es(chan, vms, vmu); 08664 } else if (!strcasecmp(chan->language, "it")) { /* ITALIAN */ 08665 return vm_browse_messages_it(chan, vms, vmu); 08666 } else if (!strcasecmp(chan->language, "pt") || !strcasecmp(chan->language, "pt_BR")) { /* PORTUGUESE */ 08667 return vm_browse_messages_pt(chan, vms, vmu); 08668 } else if (!strcasecmp(chan->language, "gr")){ 08669 return vm_browse_messages_gr(chan, vms, vmu); /* GREEK */ 08670 } else if (!strncasecmp(chan->language, "zh", 2)) { 08671 return vm_browse_messages_zh(chan, vms, vmu); /* CHINESE (Taiwan) */ 08672 } else if (!strcasecmp(chan->language, "he")) { 08673 return vm_browse_messages_he(chan, vms, vmu); /* HEBREW */ 08674 } else { /* Default to English syntax */ 08675 return vm_browse_messages_en(chan, vms, vmu); 08676 } 08677 }
| static int vm_browse_messages_en | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Default English syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8523 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08524 { 08525 int cmd=0; 08526 08527 if (vms->lastmsg > -1) { 08528 cmd = play_message(chan, vmu, vms); 08529 } else { 08530 cmd = ast_play_and_wait(chan, "vm-youhave"); 08531 if (!cmd) 08532 cmd = ast_play_and_wait(chan, "vm-no"); 08533 if (!cmd) { 08534 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08535 cmd = ast_play_and_wait(chan, vms->fn); 08536 } 08537 if (!cmd) 08538 cmd = ast_play_and_wait(chan, "vm-messages"); 08539 } 08540 return cmd; 08541 }
| static int vm_browse_messages_es | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Spanish syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8577 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08578 { 08579 int cmd=0; 08580 08581 if (vms->lastmsg > -1) { 08582 cmd = play_message(chan, vmu, vms); 08583 } else { 08584 cmd = ast_play_and_wait(chan, "vm-youhaveno"); 08585 if (!cmd) 08586 cmd = ast_play_and_wait(chan, "vm-messages"); 08587 if (!cmd) { 08588 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08589 cmd = ast_play_and_wait(chan, vms->fn); 08590 } 08591 } 08592 return cmd; 08593 }
| static int vm_browse_messages_gr | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Greek syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8471 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, play_message(), and vm_state::vmbox.
Referenced by vm_browse_messages().
08472 { 08473 int cmd=0; 08474 08475 if (vms->lastmsg > -1) { 08476 cmd = play_message(chan, vmu, vms); 08477 } else { 08478 cmd = ast_play_and_wait(chan, "vm-youhaveno"); 08479 if (!strcasecmp(vms->vmbox, "vm-INBOX") ||!strcasecmp(vms->vmbox, "vm-Old")){ 08480 if (!cmd) { 08481 snprintf(vms->fn, sizeof(vms->fn), "vm-%ss", vms->curbox); 08482 cmd = ast_play_and_wait(chan, vms->fn); 08483 } 08484 if (!cmd) 08485 cmd = ast_play_and_wait(chan, "vm-messages"); 08486 } else { 08487 if (!cmd) 08488 cmd = ast_play_and_wait(chan, "vm-messages"); 08489 if (!cmd) { 08490 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08491 cmd = ast_play_and_wait(chan, vms->fn); 08492 } 08493 } 08494 } 08495 return cmd; 08496 }
| static int vm_browse_messages_he | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Definition at line 8499 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08500 { 08501 int cmd = 0; 08502 08503 if (vms->lastmsg > -1) { 08504 cmd = play_message(chan, vmu, vms); 08505 } else { 08506 if (!strcasecmp(vms->fn, "INBOX")) { 08507 cmd = ast_play_and_wait(chan, "vm-nonewmessages"); 08508 } else { 08509 cmd = ast_play_and_wait(chan, "vm-nomessages"); 08510 } 08511 } 08512 return cmd; 08513 }
| static int vm_browse_messages_it | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Italian syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8551 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08552 { 08553 int cmd=0; 08554 08555 if (vms->lastmsg > -1) { 08556 cmd = play_message(chan, vmu, vms); 08557 } else { 08558 cmd = ast_play_and_wait(chan, "vm-no"); 08559 if (!cmd) 08560 cmd = ast_play_and_wait(chan, "vm-message"); 08561 if (!cmd) { 08562 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08563 cmd = ast_play_and_wait(chan, vms->fn); 08564 } 08565 } 08566 return cmd; 08567 }
| static int vm_browse_messages_pt | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Portuguese syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8603 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08604 { 08605 int cmd=0; 08606 08607 if (vms->lastmsg > -1) { 08608 cmd = play_message(chan, vmu, vms); 08609 } else { 08610 cmd = ast_play_and_wait(chan, "vm-no"); 08611 if (!cmd) { 08612 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08613 cmd = ast_play_and_wait(chan, vms->fn); 08614 } 08615 if (!cmd) 08616 cmd = ast_play_and_wait(chan, "vm-messages"); 08617 } 08618 return cmd; 08619 }
| static int vm_browse_messages_zh | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| struct ast_vm_user * | vmu | |||
| ) | [static] |
Chinese (Taiwan)syntax for 'You have N messages' greeting.
| chan | ||
| vms | ||
| vmu |
Definition at line 8629 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::curbox, vm_state::fn, vm_state::lastmsg, and play_message().
Referenced by vm_browse_messages().
08630 { 08631 int cmd=0; 08632 08633 if (vms->lastmsg > -1) { 08634 cmd = play_message(chan, vmu, vms); 08635 } else { 08636 cmd = ast_play_and_wait(chan, "vm-you"); 08637 if (!cmd) 08638 cmd = ast_play_and_wait(chan, "vm-haveno"); 08639 if (!cmd) 08640 cmd = ast_play_and_wait(chan, "vm-messages"); 08641 if (!cmd) { 08642 snprintf(vms->fn, sizeof(vms->fn), "vm-%s", vms->curbox); 08643 cmd = ast_play_and_wait(chan, vms->fn); 08644 } 08645 } 08646 return cmd; 08647 }
| static void vm_change_password | ( | struct ast_vm_user * | vmu, | |
| const char * | newpassword | |||
| ) | [static] |
The handler for the change password option.
| vmu | The voicemail user to work with. | |
| newpassword | The new password (that has been gathered from the appropriate prompting). This is called when a new user logs in for the first time and the option to force them to change their password is set. It is also called when the user wants to change their password from menu option '5' on the mailbox options menu. |
Definition at line 1160 of file app_voicemail.c.
References ast_category_browse(), ast_category_get(), ast_config_load, ast_copy_string(), ast_debug, ast_log(), AST_LOG_WARNING, ast_variable_append(), ast_variable_new(), ast_variable_retrieve(), ast_variable_update(), change_password_realtime(), CONFIG_FLAG_WITHCOMMENTS, config_text_file_save(), ast_vm_user::context, ast_vm_user::mailbox, ast_vm_user::password, reset_user_pw(), var, and VOICEMAIL_CONFIG.
Referenced by vm_newuser(), and vm_options().
01161 { 01162 struct ast_config *cfg=NULL; 01163 struct ast_variable *var=NULL; 01164 struct ast_category *cat=NULL; 01165 char *category=NULL, *value=NULL, *new=NULL; 01166 const char *tmp=NULL; 01167 struct ast_flags config_flags = { CONFIG_FLAG_WITHCOMMENTS }; 01168 if (!change_password_realtime(vmu, newpassword)) 01169 return; 01170 01171 /* check voicemail.conf */ 01172 if ((cfg = ast_config_load(VOICEMAIL_CONFIG, config_flags))) { 01173 while ((category = ast_category_browse(cfg, category))) { 01174 if (!strcasecmp(category, vmu->context)) { 01175 if (!(tmp = ast_variable_retrieve(cfg, category, vmu->mailbox))) { 01176 ast_log(AST_LOG_WARNING, "We could not find the mailbox.\n"); 01177 break; 01178 } 01179 value = strstr(tmp,","); 01180 if (!value) { 01181 ast_log(AST_LOG_WARNING, "variable has bad format.\n"); 01182 break; 01183 } 01184 new = alloca((strlen(value)+strlen(newpassword)+1)); 01185 sprintf(new,"%s%s", newpassword, value); 01186 if (!(cat = ast_category_get(cfg, category))) { 01187 ast_log(AST_LOG_WARNING, "Failed to get category structure.\n"); 01188 break; 01189 } 01190 ast_variable_update(cat, vmu->mailbox, new, NULL, 0); 01191 } 01192 } 01193 /* save the results */ 01194 reset_user_pw(vmu->context, vmu->mailbox, newpassword); 01195 ast_copy_string(vmu->password, newpassword, sizeof(vmu->password)); 01196 config_text_file_save(VOICEMAIL_CONFIG, cfg, "AppVoicemail"); 01197 } 01198 category = NULL; 01199 var = NULL; 01200 /* check users.conf and update the password stored for the mailbox*/ 01201 /* if no vmsecret entry exists create one. */ 01202 if ((cfg = ast_config_load("users.conf", config_flags))) { 01203 ast_debug(4, "we are looking for %s\n", vmu->mailbox); 01204 while ((category = ast_category_browse(cfg, category))) { 01205 ast_debug(4, "users.conf: %s\n", category); 01206 if (!strcasecmp(category, vmu->mailbox)) { 01207 if (!(tmp = ast_variable_retrieve(cfg, category, "vmsecret"))) { 01208 ast_debug(3, "looks like we need to make vmsecret!\n"); 01209 var = ast_variable_new("vmsecret", newpassword, ""); 01210 } 01211 new = alloca(strlen(newpassword)+1); 01212 sprintf(new, "%s", newpassword); 01213 if (!(cat = ast_category_get(cfg, category))) { 01214 ast_debug(4, "failed to get category!\n"); 01215 break; 01216 } 01217 if (!var) 01218 ast_variable_update(cat, "vmsecret", new, NULL, 0); 01219 else 01220 ast_variable_append(cat, var); 01221 } 01222 } 01223 /* save the results and clean things up */ 01224 reset_user_pw(vmu->context, vmu->mailbox, newpassword); 01225 ast_copy_string(vmu->password, newpassword, sizeof(vmu->password)); 01226 config_text_file_save("users.conf", cfg, "AppVoicemail"); 01227 } 01228 }
| static void vm_change_password_shell | ( | struct ast_vm_user * | vmu, | |
| char * | newpassword | |||
| ) | [static] |
Definition at line 1230 of file app_voicemail.c.
References ast_copy_string(), ast_safe_system(), buf, ast_vm_user::context, ast_vm_user::mailbox, ast_vm_user::password, and reset_user_pw().
Referenced by vm_newuser(), and vm_options().
01231 { 01232 char buf[255]; 01233 snprintf(buf,255,"%s %s %s %s",ext_pass_cmd,vmu->context,vmu->mailbox,newpassword); 01234 if (!ast_safe_system(buf)) { 01235 ast_copy_string(vmu->password, newpassword, sizeof(vmu->password)); 01236 /* Reset the password in memory, too */ 01237 reset_user_pw(vmu->context, vmu->mailbox, newpassword); 01238 } 01239 }
| static char* vm_check_password_shell | ( | char * | command, | |
| char * | buf, | |||
| size_t | len | |||
| ) | [static] |
Definition at line 861 of file app_voicemail.c.
References AST_APP_ARG, ast_close_fds_above_n(), AST_DECLARE_APP_ARGS, ast_log(), AST_NONSTANDARD_APP_ARGS, ast_safe_fork(), ast_strdupa, errno, and LOG_WARNING.
Referenced by check_password().
00862 { 00863 int fds[2], pid = 0; 00864 00865 memset(buf, 0, len); 00866 00867 if (pipe(fds)) { 00868 snprintf(buf, len, "FAILURE: Pipe failed: %s", strerror(errno)); 00869 } else { 00870 /* good to go*/ 00871 pid = ast_safe_fork(0); 00872 00873 if (pid < 0) { 00874 /* ok maybe not */ 00875 close(fds[0]); 00876 close(fds[1]); 00877 snprintf(buf, len, "FAILURE: Fork failed"); 00878 } else if (pid) { 00879 /* parent */ 00880 close(fds[1]); 00881 if (read(fds[0], buf, len) < 0) { 00882 ast_log(LOG_WARNING, "read() failed: %s\n", strerror(errno)); 00883 } 00884 close(fds[0]); 00885 } else { 00886 /* child */ 00887 AST_DECLARE_APP_ARGS(arg, 00888 AST_APP_ARG(v)[20]; 00889 ); 00890 char *mycmd = ast_strdupa(command); 00891 00892 close(fds[0]); 00893 dup2(fds[1], STDOUT_FILENO); 00894 close(fds[1]); 00895 ast_close_fds_above_n(STDOUT_FILENO); 00896 00897 AST_NONSTANDARD_APP_ARGS(arg, mycmd, ' '); 00898 00899 execv(arg.v[0], arg.v); 00900 printf("FAILURE: %s", strerror(errno)); 00901 _exit(0); 00902 } 00903 } 00904 return buf; 00905 }
| static int vm_delete | ( | char * | file | ) | [static] |
Removes the voicemail sound and information file.
| file | The path to the sound file. This will be the the folder and message index, without the extension. |
This is used by the DELETE macro when voicemails are stored on the file system.
Definition at line 3588 of file app_voicemail.c.
References ast_check_realtime(), ast_destroy_realtime(), ast_filedelete(), and SENTINEL.
Referenced by copy_message(), and notify_new_message().
03589 { 03590 char *txt; 03591 int txtsize = 0; 03592 03593 txtsize = (strlen(file) + 5)*sizeof(char); 03594 txt = alloca(txtsize); 03595 /* Sprintf here would safe because we alloca'd exactly the right length, 03596 * but trying to eliminate all sprintf's anyhow 03597 */ 03598 if (ast_check_realtime("voicemail_data")) { 03599 ast_destroy_realtime("voicemail_data", "filename", file, SENTINEL); 03600 } 03601 snprintf(txt, txtsize, "%s.txt", file); 03602 unlink(txt); 03603 return ast_filedelete(file, NULL); 03604 }
| static int vm_exec | ( | struct ast_channel * | chan, | |
| void * | data | |||
| ) | [static] |
Definition at line 9487 of file app_voicemail.c.
References ast_channel::_state, ast_answer(), AST_APP_ARG, ast_app_getdata(), ast_app_parse_options(), ast_copy_flags, AST_DECLARE_APP_ARGS, ast_log(), AST_LOG_ERROR, AST_LOG_WARNING, AST_STANDARD_APP_ARGS, AST_STATE_UP, ast_strdupa, ast_strlen_zero(), ast_test_flag, ERROR_LOCK_PATH, leave_vm_options::exitcontext, leave_voicemail(), OPT_ARG_ARRAY_SIZE, OPT_ARG_DTMFEXIT, OPT_ARG_RECORDGAIN, OPT_BUSY_GREETING, OPT_DTMFEXIT, OPT_MESSAGE_PRIORITY, OPT_MESSAGE_Urgent, OPT_RECORDGAIN, OPT_SILENT, OPT_UNAVAIL_GREETING, pbx_builtin_setvar_helper(), leave_vm_options::record_gain, and vm_app_options.
Referenced by load_module(), and play_record_review().
09488 { 09489 int res = 0; 09490 char *tmp; 09491 struct leave_vm_options leave_options; 09492 struct ast_flags flags = { 0 }; 09493 char *opts[OPT_ARG_ARRAY_SIZE]; 09494 AST_DECLARE_APP_ARGS(args, 09495 AST_APP_ARG(argv0); 09496 AST_APP_ARG(argv1); 09497 ); 09498 09499 memset(&leave_options, 0, sizeof(leave_options)); 09500 09501 if (chan->_state != AST_STATE_UP) 09502 ast_answer(chan); 09503 09504 if (!ast_strlen_zero(data)) { 09505 tmp = ast_strdupa(data); 09506 AST_STANDARD_APP_ARGS(args, tmp); 09507 if (args.argc == 2) { 09508 if (ast_app_parse_options(vm_app_options, &flags, opts, args.argv1)) 09509 return -1; 09510 ast_copy_flags(&leave_options, &flags, OPT_SILENT | OPT_BUSY_GREETING | OPT_UNAVAIL_GREETING | OPT_MESSAGE_Urgent | OPT_MESSAGE_PRIORITY | OPT_DTMFEXIT); 09511 if (ast_test_flag(&flags, OPT_RECORDGAIN)) { 09512 int gain; 09513 09514 if (sscanf(opts[OPT_ARG_RECORDGAIN], "%30d", &gain) != 1) { 09515 ast_log(AST_LOG_WARNING, "Invalid value '%s' provided for record gain option\n", opts[OPT_ARG_RECORDGAIN]); 09516 return -1; 09517 } else { 09518 leave_options.record_gain = (signed char) gain; 09519 } 09520 } 09521 if (ast_test_flag(&flags, OPT_DTMFEXIT)) { 09522 if (!ast_strlen_zero(opts[OPT_ARG_DTMFEXIT])) 09523 leave_options.exitcontext = opts[OPT_ARG_DTMFEXIT]; 09524 } 09525 } 09526 } else { 09527 char temp[256]; 09528 res = ast_app_getdata(chan, "vm-whichbox", temp, sizeof(temp) - 1, 0); 09529 if (res < 0) 09530 return res; 09531 if (ast_strlen_zero(temp)) 09532 return 0; 09533 args.argv0 = ast_strdupa(temp); 09534 } 09535 09536 res = leave_voicemail(chan, args.argv0, &leave_options); 09537 09538 if (res == ERROR_LOCK_PATH) { 09539 ast_log(AST_LOG_ERROR, "Could not leave voicemail. The path is already locked.\n"); 09540 pbx_builtin_setvar_helper(chan, "VMSTATUS", "FAILED"); 09541 res = 0; 09542 } 09543 09544 return res; 09545 }
| static int vm_execmain | ( | struct ast_channel * | chan, | |
| void * | data | |||
| ) | [static] |
Definition at line 8779 of file app_voicemail.c.
References ast_channel::_state, adsi_begin(), adsi_delete(), adsi_folders(), adsi_goodbye(), adsi_message(), adsi_status(), adsi_status2(), advanced_options(), ast_adsi_unload_session, ast_answer(), AST_APP_ARG, ast_app_inboxcount2(), ast_app_parse_options(), ast_calloc, ast_copy_string(), ast_debug, AST_DECLARE_APP_ARGS, ast_free, ast_log(), AST_LOG_ERROR, AST_LOG_WARNING, ast_mutex_lock(), ast_mutex_unlock(), ast_play_and_wait(), ast_set_flag, AST_STANDARD_APP_ARGS, AST_STATE_UP, ast_stopstream(), ast_strdupa, ast_string_field_set, ast_strlen_zero(), ast_test_flag, ast_verb, ast_waitfordigit(), ast_vm_user::callback, close_mailbox(), ast_vm_user::context, vm_state::context, vm_state::curdir, vm_state::curmsg, vm_state::deleted, dialout(), ast_vm_user::dialout, ERROR_LOCK_PATH, EVENT_FLAG_CALL, find_user(), vm_state::fn, forward_message(), free_user(), get_folder2(), globalflags, has_voicemail(), vm_state::heard, language, ast_vm_user::language, vm_state::lastmsg, ast_vm_user::mailbox, make_file(), manager_event, ast_vm_user::maxmsg, mbox(), NEW_FOLDER, vm_state::newmessages, OLD_FOLDER, vm_state::oldmessages, open_mailbox(), OPT_ARG_ARRAY_SIZE, OPT_ARG_PLAYFOLDER, OPT_ARG_RECORDGAIN, OPT_AUTOPLAY, OPT_PREPEND_MAILBOX, OPT_RECORDGAIN, OPT_SILENT, parse(), ast_vm_user::password, play_message(), queue_mwi_event(), vm_state::repeats, run_externnotify(), save_to_folder(), say_and_wait(), vm_state::starting, vm_state::urgentmessages, vm_state::username, vm_app_options, vm_authenticate(), vm_browse_messages(), VM_FORCEGREET, VM_FORCENAME, vm_instructions(), vm_intro(), VM_MESSAGEWRAP, vm_newuser(), vm_options(), vm_play_folder_name(), VM_SKIPAFTERCMD, VM_SVMAIL, and vm_state::vmbox.
Referenced by load_module().
08780 { 08781 /* XXX This is, admittedly, some pretty horrendous code. For some 08782 reason it just seemed a lot easier to do with GOTO's. I feel 08783 like I'm back in my GWBASIC days. XXX */ 08784 int res=-1; 08785 int cmd=0; 08786 int valid = 0; 08787 char prefixstr[80] =""; 08788 char ext_context[256]=""; 08789 int box; 08790 int useadsi = 0; 08791 int skipuser = 0; 08792 struct vm_state vms; 08793 struct ast_vm_user *vmu = NULL, vmus; 08794 char *context=NULL; 08795 int silentexit = 0; 08796 struct ast_flags flags = { 0 }; 08797 signed char record_gain = 0; 08798 int play_auto = 0; 08799 int play_folder = 0; 08800 int in_urgent = 0; 08801 #ifdef IMAP_STORAGE 08802 int deleted = 0; 08803 #endif 08804 08805 /* Add the vm_state to the active list and keep it active */ 08806 memset(&vms, 0, sizeof(vms)); 08807 08808 vms.lastmsg = -1; 08809 08810 memset(&vmus, 0, sizeof(vmus)); 08811 08812 if (chan->_state != AST_STATE_UP) { 08813 ast_debug(1, "Before ast_answer\n"); 08814 ast_answer(chan); 08815 } 08816 08817 if (!ast_strlen_zero(data)) { 08818 char *opts[OPT_ARG_ARRAY_SIZE]; 08819 char *parse; 08820 AST_DECLARE_APP_ARGS(args, 08821 AST_APP_ARG(argv0); 08822 AST_APP_ARG(argv1); 08823 ); 08824 08825 parse = ast_strdupa(data); 08826 08827 AST_STANDARD_APP_ARGS(args, parse); 08828 08829 if (args.argc == 2) { 08830 if (ast_app_parse_options(vm_app_options, &flags, opts, args.argv1)) 08831 return -1; 08832 if (ast_test_flag(&flags, OPT_RECORDGAIN)) { 08833 int gain; 08834 if (!ast_strlen_zero(opts[OPT_ARG_RECORDGAIN])) { 08835 if (sscanf(opts[OPT_ARG_RECORDGAIN], "%30d", &gain) != 1) { 08836 ast_log(AST_LOG_WARNING, "Invalid value '%s' provided for record gain option\n", opts[OPT_ARG_RECORDGAIN]); 08837 return -1; 08838 } else { 08839 record_gain = (signed char) gain; 08840 } 08841 } else { 08842 ast_log(AST_LOG_WARNING, "Invalid Gain level set with option g\n"); 08843 } 08844 } 08845 if (ast_test_flag(&flags, OPT_AUTOPLAY) ) { 08846 play_auto = 1; 08847 if (opts[OPT_ARG_PLAYFOLDER]) { 08848 if (sscanf(opts[OPT_ARG_PLAYFOLDER], "%30d", &play_folder) != 1) { 08849 ast_log(AST_LOG_WARNING, "Invalid value '%s' provided for folder autoplay option\n", opts[OPT_ARG_PLAYFOLDER]); 08850 } 08851 } else { 08852 ast_log(AST_LOG_WARNING, "Invalid folder set with option a\n"); 08853 } 08854 if ( play_folder > 9 || play_folder < 0) { 08855 ast_log(AST_LOG_WARNING, "Invalid value '%d' provided for folder autoplay option\n", play_folder); 08856 play_folder = 0; 08857 } 08858 } 08859 } else { 08860 /* old style options parsing */ 08861 while (*(args.argv0)) { 08862 if (*(args.argv0) == 's') 08863 ast_set_flag(&flags, OPT_SILENT); 08864 else if (*(args.argv0) == 'p') 08865 ast_set_flag(&flags, OPT_PREPEND_MAILBOX); 08866 else 08867 break; 08868 (args.argv0)++; 08869 } 08870 08871 } 08872 08873 valid = ast_test_flag(&flags, OPT_SILENT); 08874 08875 if ((context = strchr(args.argv0, '@'))) 08876 *context++ = '\0'; 08877 08878 if (ast_test_flag(&flags, OPT_PREPEND_MAILBOX)) 08879 ast_copy_string(prefixstr, args.argv0, sizeof(prefixstr)); 08880 else 08881 ast_copy_string(vms.username, args.argv0, sizeof(vms.username)); 08882 08883 if (!ast_strlen_zero(vms.username) && (vmu = find_user(&vmus, context ,vms.username))) 08884 skipuser++; 08885 else 08886 valid = 0; 08887 } 08888 08889 if (!valid) 08890 res = vm_authenticate(chan, vms.username, sizeof(vms.username), &vmus, context, prefixstr, skipuser, maxlogins, 0); 08891 08892 ast_debug(1, "After vm_authenticate\n"); 08893 if (!res) { 08894 valid = 1; 08895 if (!skipuser) 08896 vmu = &vmus; 08897 } else { 08898 res = 0; 08899 } 08900 08901 /* If ADSI is supported, setup login screen */ 08902 adsi_begin(chan, &useadsi); 08903 08904 if (!valid) { 08905 goto out; 08906 } 08907 08908 #ifdef IMAP_STORAGE 08909 pthread_once(&ts_vmstate.once, ts_vmstate.key_init); 08910 pthread_setspecific(ts_vmstate.key, &vms); 08911 08912 vms.interactive = 1; 08913 vms.updated = 1; 08914 if (vmu) 08915 ast_copy_string(vms.context, vmu->context, sizeof(vms.context)); 08916 vmstate_insert(&vms); 08917 init_vm_state(&vms); 08918 #endif 08919 if (!(vms.deleted = ast_calloc(vmu->maxmsg, sizeof(int)))) { 08920 ast_log(AST_LOG_ERROR, "Could not allocate memory for deleted message storage!\n"); 08921 cmd = ast_play_and_wait(chan, "an-error-has-occured"); 08922 return -1; 08923 } 08924 if (!(vms.heard = ast_calloc(vmu->maxmsg, sizeof(int)))) { 08925 ast_log(AST_LOG_ERROR, "Could not allocate memory for heard message storage!\n"); 08926 cmd = ast_play_and_wait(chan, "an-error-has-occured"); 08927 return -1; 08928 } 08929 08930 /* Set language from config to override channel language */ 08931 if (!ast_strlen_zero(vmu->language)) 08932 ast_string_field_set(chan, language, vmu->language); 08933 08934 /* Retrieve urgent, old and new message counts */ 08935 ast_debug(1, "Before open_mailbox\n"); 08936 res = open_mailbox(&vms, vmu, OLD_FOLDER); /* Count all messages, even Urgent */ 08937 if (res == ERROR_LOCK_PATH) 08938 goto out; 08939 vms.oldmessages = vms.lastmsg + 1; 08940 ast_debug(1, "Number of old messages: %d\n",vms.oldmessages); 08941 /* check INBOX */ 08942 res = open_mailbox(&vms, vmu, NEW_FOLDER); 08943 if (res == ERROR_LOCK_PATH) 08944 goto out; 08945 vms.newmessages = vms.lastmsg + 1; 08946 ast_debug(1, "Number of new messages: %d\n",vms.newmessages); 08947 /* Start in Urgent */ 08948 in_urgent = 1; 08949 res = open_mailbox(&vms, vmu, 11); /*11 is the Urgent folder */ 08950 if (res == ERROR_LOCK_PATH) 08951 goto out; 08952 vms.urgentmessages = vms.lastmsg + 1; 08953 ast_debug(1, "Number of urgent messages: %d\n",vms.urgentmessages); 08954 08955 /* Select proper mailbox FIRST!! */ 08956 if (play_auto) { 08957 if (vms.urgentmessages) { 08958 in_urgent = 1; 08959 res = open_mailbox(&vms, vmu, 11); 08960 } else { 08961 in_urgent = 0; 08962 res = open_mailbox(&vms, vmu, play_folder); 08963 } 08964 if (res == ERROR_LOCK_PATH) 08965 goto out; 08966 08967 /* If there are no new messages, inform the user and hangup */ 08968 if (vms.lastmsg == -1) { 08969 in_urgent = 0; 08970 cmd = vm_browse_messages(chan, &vms, vmu); 08971 res = 0; 08972 goto out; 08973 } 08974 } else { 08975 if (!vms.newmessages && !vms.urgentmessages && vms.oldmessages) { 08976 /* If we only have old messages start here */ 08977 res = open_mailbox(&vms, vmu, OLD_FOLDER); /* Count all messages, even Urgent */ 08978 in_urgent = 0; 08979 play_folder = 1; 08980 if (res == ERROR_LOCK_PATH) 08981 goto out; 08982 } else if (!vms.urgentmessages && vms.newmessages) { 08983 /* If we have new messages but none are urgent */ 08984 in_urgent = 0; 08985 res = open_mailbox(&vms, vmu, NEW_FOLDER); 08986 if (res == ERROR_LOCK_PATH) 08987 goto out; 08988 } 08989 } 08990 08991 if (useadsi) 08992 adsi_status(chan, &vms); 08993 res = 0; 08994 08995 /* Check to see if this is a new user */ 08996 if (!strcasecmp(vmu->mailbox, vmu->password) && 08997 (ast_test_flag(vmu, VM_FORCENAME | VM_FORCEGREET))) { 08998 if (ast_play_and_wait(chan, "vm-newuser") == -1) 08999 ast_log(AST_LOG_WARNING, "Couldn't stream new user file\n"); 09000 cmd = vm_newuser(chan, vmu, &vms, vmfmts, record_gain); 09001 if ((cmd == 't') || (cmd == '#')) { 09002 /* Timeout */ 09003 res = 0; 09004 goto out; 09005 } else if (cmd < 0) { 09006 /* Hangup */ 09007 res = -1; 09008 goto out; 09009 } 09010 } 09011 #ifdef IMAP_STORAGE 09012 ast_debug(3, "Checking quotas: comparing %u to %u\n",vms.quota_usage,vms.quota_limit); 09013 if (vms.quota_limit && vms.quota_usage >= vms.quota_limit) { 09014 ast_debug(1, "*** QUOTA EXCEEDED!!\n"); 09015 cmd = ast_play_and_wait(chan, "vm-mailboxfull"); 09016 } 09017 ast_debug(3, "Checking quotas: User has %d messages and limit is %d.\n",(vms.newmessages + vms.oldmessages),vmu->maxmsg); 09018 if ((vms.newmessages + vms.oldmessages) >= vmu->maxmsg) { 09019 ast_log(AST_LOG_WARNING, "No more messages possible. User has %d messages and limit is %d.\n", (vms.newmessages + vms.oldmessages), vmu->maxmsg); 09020 cmd = ast_play_and_wait(chan, "vm-mailboxfull"); 09021 } 09022 #endif 09023 if (play_auto) { 09024 cmd = '1'; 09025 } else { 09026 cmd = vm_intro(chan, vmu, &vms); 09027 } 09028 09029 vms.repeats = 0; 09030 vms.starting = 1; 09031 while ((cmd > -1) && (cmd != 't') && (cmd != '#')) { 09032 /* Run main menu */ 09033 switch (cmd) { 09034 case '1': /* First message */ 09035 vms.curmsg = 0; 09036 /* Fall through */ 09037 case '5': /* Play current message */ 09038 cmd = vm_browse_messages(chan, &vms, vmu); 09039 break; 09040 case '2': /* Change folders */ 09041 if (useadsi) 09042 adsi_folders(chan, 0, "Change to folder..."); 09043 cmd = get_folder2(chan, "vm-changeto", 0); 09044 if (cmd == '#') { 09045 cmd = 0; 09046 } else if (cmd > 0) { 09047 cmd = cmd - '0'; 09048 res = close_mailbox(&vms, vmu); 09049 if (res == ERROR_LOCK_PATH) 09050 goto out; 09051 /* If folder is not urgent, set in_urgent to zero! */ 09052 if (cmd != 11) in_urgent = 0; 09053 res = open_mailbox(&vms, vmu, cmd); 09054 if (res == ERROR_LOCK_PATH) 09055 goto out; 09056 play_folder = cmd; 09057 cmd = 0; 09058 } 09059 if (useadsi) 09060 adsi_status2(chan, &vms); 09061 09062 if (!cmd) 09063 cmd = vm_play_folder_name(chan, vms.vmbox); 09064 09065 vms.starting = 1; 09066 break; 09067 case '3': /* Advanced options */ 09068 cmd = 0; 09069 vms.repeats = 0; 09070 while ((cmd > -1) && (cmd != 't') && (cmd != '#')) { 09071 switch (cmd) { 09072 case '1': /* Reply */ 09073 if (vms.lastmsg > -1 && !vms.starting) { 09074 cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 1, record_gain); 09075 if (cmd == ERROR_LOCK_PATH) { 09076 res = cmd; 09077 goto out; 09078 } 09079 } else 09080 cmd = ast_play_and_wait(chan, "vm-sorry"); 09081 cmd = 't'; 09082 break; 09083 case '2': /* Callback */ 09084 if (!vms.starting) 09085 ast_verb(3, "Callback Requested\n"); 09086 if (!ast_strlen_zero(vmu->callback) && vms.lastmsg > -1 && !vms.starting) { 09087 cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 2, record_gain); 09088 if (cmd == 9) { 09089 silentexit = 1; 09090 goto out; 09091 } else if (cmd == ERROR_LOCK_PATH) { 09092 res = cmd; 09093 goto out; 09094 } 09095 } else 09096 cmd = ast_play_and_wait(chan, "vm-sorry"); 09097 cmd = 't'; 09098 break; 09099 case '3': /* Envelope */ 09100 if (vms.lastmsg > -1 && !vms.starting) { 09101 cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 3, record_gain); 09102 if (cmd == ERROR_LOCK_PATH) { 09103 res = cmd; 09104 goto out; 09105 } 09106 } else 09107 cmd = ast_play_and_wait(chan, "vm-sorry"); 09108 cmd = 't'; 09109 break; 09110 case '4': /* Dialout */ 09111 if (!ast_strlen_zero(vmu->dialout)) { 09112 cmd = dialout(chan, vmu, NULL, vmu->dialout); 09113 if (cmd == 9) { 09114 silentexit = 1; 09115 goto out; 09116 } 09117 } else 09118 cmd = ast_play_and_wait(chan, "vm-sorry"); 09119 cmd = 't'; 09120 break; 09121 09122 case '5': /* Leave VoiceMail */ 09123 if (ast_test_flag(vmu, VM_SVMAIL)) { 09124 cmd = forward_message(chan, context, &vms, vmu, vmfmts, 1, record_gain, 0); 09125 if (cmd == ERROR_LOCK_PATH) { 09126 res = cmd; 09127 ast_log(AST_LOG_WARNING, "forward_message failed to lock path.\n"); 09128 goto out; 09129 } 09130 } else 09131 cmd = ast_play_and_wait(chan,"vm-sorry"); 09132 cmd='t'; 09133 break; 09134 09135 case '*': /* Return to main menu */ 09136 cmd = 't'; 09137 break; 09138 09139 default: 09140 cmd = 0; 09141 if (!vms.starting) { 09142 cmd = ast_play_and_wait(chan, "vm-toreply"); 09143 } 09144 if (!ast_strlen_zero(vmu->callback) && !vms.starting && !cmd) { 09145 cmd = ast_play_and_wait(chan, "vm-tocallback"); 09146 } 09147 if (!cmd && !vms.starting) { 09148 cmd = ast_play_and_wait(chan, "vm-tohearenv"); 09149 } 09150 if (!ast_strlen_zero(vmu->dialout) && !cmd) { 09151 cmd = ast_play_and_wait(chan, "vm-tomakecall"); 09152 } 09153 if (ast_test_flag(vmu, VM_SVMAIL) && !cmd) 09154 cmd=ast_play_and_wait(chan, "vm-leavemsg"); 09155 if (!cmd) 09156 cmd = ast_play_and_wait(chan, "vm-starmain"); 09157 if (!cmd) 09158 cmd = ast_waitfordigit(chan,6000); 09159 if (!cmd) 09160 vms.repeats++; 09161 if (vms.repeats > 3) 09162 cmd = 't'; 09163 } 09164 } 09165 if (cmd == 't') { 09166 cmd = 0; 09167 vms.repeats = 0; 09168 } 09169 break; 09170 case '4': /* Go to the previous message */ 09171 if (vms.curmsg > 0) { 09172 vms.curmsg--; 09173 cmd = play_message(chan, vmu, &vms); 09174 } else { 09175 /* Check if we were listening to new 09176 messages. If so, go to Urgent messages 09177 instead of saying "no more messages" 09178 */ 09179 if (in_urgent == 0 && vms.urgentmessages > 0) { 09180 /* Check for Urgent messages */ 09181 in_urgent = 1; 09182 res = close_mailbox(&vms, vmu); 09183 if (res == ERROR_LOCK_PATH) 09184 goto out; 09185 res = open_mailbox(&vms, vmu, 11); /* Open Urgent folder */ 09186 if (res == ERROR_LOCK_PATH) 09187 goto out; 09188 ast_debug(1, "No more new messages, opened INBOX and got %d Urgent messages\n",vms.lastmsg + 1); 09189 vms.curmsg = vms.lastmsg; 09190 if (vms.lastmsg < 0) 09191 cmd = ast_play_and_wait(chan, "vm-nomore"); 09192 } else if (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms.lastmsg > 0) { 09193 vms.curmsg = vms.lastmsg; 09194 cmd = play_message(chan, vmu, &vms); 09195 } else { 09196 cmd = ast_play_and_wait(chan, "vm-nomore"); 09197 } 09198 } 09199 break; 09200 case '6': /* Go to the next message */ 09201 if (vms.curmsg < vms.lastmsg) { 09202 vms.curmsg++; 09203 cmd = play_message(chan, vmu, &vms); 09204 } else { 09205 if (in_urgent && vms.newmessages > 0) { 09206 /* Check if we were listening to urgent 09207 * messages. If so, go to regular new messages 09208 * instead of saying "no more messages" 09209 */ 09210 in_urgent = 0; 09211 res = close_mailbox(&vms, vmu); 09212 if (res == ERROR_LOCK_PATH) 09213 goto out; 09214 res = open_mailbox(&vms, vmu, NEW_FOLDER); 09215 if (res == ERROR_LOCK_PATH) 09216 goto out; 09217 ast_debug(1, "No more urgent messages, opened INBOX and got %d new messages\n",vms.lastmsg + 1); 09218 vms.curmsg = -1; 09219 if (vms.lastmsg < 0) { 09220 cmd = ast_play_and_wait(chan, "vm-nomore"); 09221 } 09222 } else if (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms.lastmsg > 0) { 09223 vms.curmsg = 0; 09224 cmd = play_message(chan, vmu, &vms); 09225 } else { 09226 cmd = ast_play_and_wait(chan, "vm-nomore"); 09227 } 09228 } 09229 break; 09230 case '7': /* Delete the current message */ 09231 if (vms.curmsg >= 0 && vms.curmsg <= vms.lastmsg) { 09232 vms.deleted[vms.curmsg] = !vms.deleted[vms.curmsg]; 09233 if (useadsi) 09234 adsi_delete(chan, &vms); 09235 if (vms.deleted[vms.curmsg]) { 09236 if (play_folder == 0) { 09237 if (in_urgent) { 09238 vms.urgentmessages--; 09239 } else { 09240 vms.newmessages--; 09241 } 09242 } 09243 else if (play_folder == 1) 09244 vms.oldmessages--; 09245 cmd = ast_play_and_wait(chan, "vm-deleted"); 09246 } else { 09247 if (play_folder == 0) { 09248 if (in_urgent) { 09249 vms.urgentmessages++; 09250 } else { 09251 vms.newmessages++; 09252 } 09253 } 09254 else if (play_folder == 1) 09255 vms.oldmessages++; 09256 cmd = ast_play_and_wait(chan, "vm-undeleted"); 09257 } 09258 if (ast_test_flag((&globalflags), VM_SKIPAFTERCMD)) { 09259 if (vms.curmsg < vms.lastmsg) { 09260 vms.curmsg++; 09261 cmd = play_message(chan, vmu, &vms); 09262 } else if (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms.lastmsg > 0) { 09263 vms.curmsg = 0; 09264 cmd = play_message(chan, vmu, &vms); 09265 } else { 09266 /* Check if we were listening to urgent 09267 messages. If so, go to regular new messages 09268 instead of saying "no more messages" 09269 */ 09270 if (in_urgent == 1) { 09271 /* Check for new messages */ 09272 in_urgent = 0; 09273 res = close_mailbox(&vms, vmu); 09274 if (res == ERROR_LOCK_PATH) 09275 goto out; 09276 res = open_mailbox(&vms, vmu, NEW_FOLDER); 09277 if (res == ERROR_LOCK_PATH) 09278 goto out; 09279 ast_debug(1, "No more urgent messages, opened INBOX and got %d new messages\n",vms.lastmsg + 1); 09280 vms.curmsg = -1; 09281 if (vms.lastmsg < 0) 09282 cmd = ast_play_and_wait(chan, "vm-nomore"); 09283 } else { 09284 cmd = ast_play_and_wait(chan, "vm-nomore"); 09285 } 09286 } 09287 } 09288 } else /* Delete not valid if we haven't selected a message */ 09289 cmd = 0; 09290 #ifdef IMAP_STORAGE 09291 deleted = 1; 09292 #endif 09293 break; 09294 09295 case '8': /* Forward the current messgae */ 09296 if (vms.lastmsg > -1) { 09297 cmd = forward_message(chan, context, &vms, vmu, vmfmts, 0, record_gain, in_urgent); 09298 if (cmd == ERROR_LOCK_PATH) { 09299 res = cmd; 09300 goto out; 09301 } 09302 } else { 09303 /* Check if we were listening to urgent 09304 messages. If so, go to regular new messages 09305 instead of saying "no more messages" 09306 */ 09307 if (in_urgent == 1 && vms.newmessages > 0) { 09308 /* Check for new messages */ 09309 in_urgent = 0; 09310 res = close_mailbox(&vms, vmu); 09311 if (res == ERROR_LOCK_PATH) 09312 goto out; 09313 res = open_mailbox(&vms, vmu, NEW_FOLDER); 09314 if (res == ERROR_LOCK_PATH) 09315 goto out; 09316 ast_debug(1, "No more urgent messages, opened INBOX and got %d new messages\n",vms.lastmsg + 1); 09317 vms.curmsg = -1; 09318 if (vms.lastmsg < 0) 09319 cmd = ast_play_and_wait(chan, "vm-nomore"); 09320 } else { 09321 cmd = ast_play_and_wait(chan, "vm-nomore"); 09322 } 09323 } 09324 break; 09325 case '9': /* Save message to folder */ 09326 if (vms.curmsg < 0 || vms.curmsg > vms.lastmsg) { 09327 /* No message selected */ 09328 cmd = 0; 09329 break; 09330 } 09331 if (useadsi) 09332 adsi_folders(chan, 1, "Save to folder..."); 09333 cmd = get_folder2(chan, "vm-savefolder", 1); 09334 box = 0; /* Shut up compiler */ 09335 if (cmd == '#') { 09336 cmd = 0; 09337 break; 09338 } else if (cmd > 0) { 09339 box = cmd = cmd - '0'; 09340 cmd = save_to_folder(vmu, &vms, vms.curmsg, cmd); 09341 if (cmd == ERROR_LOCK_PATH) { 09342 res = cmd; 09343 goto out; 09344 #ifndef IMAP_STORAGE 09345 } else if (!cmd) { 09346 vms.deleted[vms.curmsg] = 1; 09347 #endif 09348 } else { 09349 vms.deleted[vms.curmsg] = 0; 09350 vms.heard[vms.curmsg] = 0; 09351 } 09352 } 09353 make_file(vms.fn, sizeof(vms.fn), vms.curdir, vms.curmsg); 09354 if (useadsi) 09355 adsi_message(chan, &vms); 09356 snprintf(vms.fn, sizeof(vms.fn), "vm-%s", mbox(box)); 09357 if (!cmd) { 09358 cmd = ast_play_and_wait(chan, "vm-message"); 09359 if (!cmd) 09360 cmd = say_and_wait(chan, vms.curmsg + 1, chan->language); 09361 if (!cmd) 09362 cmd = ast_play_and_wait(chan, "vm-savedto"); 09363 if (!cmd) 09364 cmd = vm_play_folder_name(chan, vms.fn); 09365 } else { 09366 cmd = ast_play_and_wait(chan, "vm-mailboxfull"); 09367 } 09368 if (ast_test_flag((&globalflags), VM_SKIPAFTERCMD)) { 09369 if (vms.curmsg < vms.lastmsg) { 09370 vms.curmsg++; 09371 cmd = play_message(chan, vmu, &vms); 09372 } else if (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms.lastmsg > 0) { 09373 vms.curmsg = 0; 09374 cmd = play_message(chan, vmu, &vms); 09375 } else { 09376 /* Check if we were listening to urgent 09377 messages. If so, go to regular new messages 09378 instead of saying "no more messages" 09379 */ 09380 if (in_urgent == 1 && vms.newmessages > 0) { 09381 /* Check for new messages */ 09382 in_urgent = 0; 09383 res = close_mailbox(&vms, vmu); 09384 if (res == ERROR_LOCK_PATH) 09385 goto out; 09386 res = open_mailbox(&vms, vmu, NEW_FOLDER); 09387 if (res == ERROR_LOCK_PATH) 09388 goto out; 09389 ast_debug(1, "No more urgent messages, opened INBOX and got %d new messages\n",vms.lastmsg + 1); 09390 vms.curmsg = -1; 09391 if (vms.lastmsg < 0) 09392 cmd = ast_play_and_wait(chan, "vm-nomore"); 09393 } else { 09394 cmd = ast_play_and_wait(chan, "vm-nomore"); 09395 } 09396 } 09397 } 09398 break; 09399 case '*': /* Help */ 09400 if (!vms.starting) { 09401 cmd = ast_play_and_wait(chan, "vm-onefor"); 09402 if (!cmd) 09403 cmd = vm_play_folder_name(chan, vms.vmbox); 09404 if (!cmd) 09405 cmd = ast_play_and_wait(chan, "vm-opts"); 09406 if (!cmd) 09407 cmd = vm_instructions(chan, vmu, &vms, 1, in_urgent); 09408 } else 09409 cmd = 0; 09410 break; 09411 case '0': /* Mailbox options */ 09412 cmd = vm_options(chan, vmu, &vms, vmfmts, record_gain); 09413 if (useadsi) 09414 adsi_status(chan, &vms); 09415 break; 09416 default: /* Nothing */ 09417 cmd = vm_instructions(chan, vmu, &vms, 0, in_urgent); 09418 break; 09419 } 09420 } 09421 if ((cmd == 't') || (cmd == '#')) { 09422 /* Timeout */ 09423 res = 0; 09424 } else { 09425 /* Hangup */ 09426 res = -1; 09427 } 09428 09429 out: 09430 if (res > -1) { 09431 ast_stopstream(chan); 09432 adsi_goodbye(chan); 09433 if (valid) { 09434 if (silentexit) 09435 res = ast_play_and_wait(chan, "vm-dialout"); 09436 else 09437 res = ast_play_and_wait(chan, "vm-goodbye"); 09438 if (res > 0) 09439 res = 0; 09440 } 09441 if (useadsi) 09442 ast_adsi_unload_session(chan); 09443 } 09444 if (vmu) 09445 close_mailbox(&vms, vmu); 09446 if (valid) { 09447 int new = 0, old = 0, urgent = 0; 09448 snprintf(ext_context, sizeof(ext_context), "%s@%s", vms.username, vmu->context); 09449 manager_event(EVENT_FLAG_CALL, "MessageWaiting", "Mailbox: %s\r\nWaiting: %d\r\n", ext_context, has_voicemail(ext_context, NULL)); 09450 /* Urgent flag not passwd to externnotify here */ 09451 run_externnotify(vmu->context, vmu->mailbox, NULL); 09452 ast_app_inboxcount2(ext_context, &urgent, &new, &old); 09453 queue_mwi_event(ext_context, urgent, new, old); 09454 } 09455 #ifdef IMAP_STORAGE 09456 /* expunge message - use UID Expunge if supported on IMAP server*/ 09457 ast_debug(3, "*** Checking if we can expunge, deleted set to %d, expungeonhangup set to %d\n",deleted,expungeonhangup); 09458 if (vmu && deleted == 1 && expungeonhangup == 1 && vms.mailstream != NULL) { 09459 ast_mutex_lock(&vms.lock); 09460 #ifdef HAVE_IMAP_TK2006 09461 if (LEVELUIDPLUS (vms.mailstream)) { 09462 mail_expunge_full(vms.mailstream,NIL,EX_UID); 09463 } else 09464 #endif 09465 mail_expunge(vms.mailstream); 09466 ast_mutex_unlock(&vms.lock); 09467 } 09468 /* before we delete the state, we should copy pertinent info 09469 * back to the persistent model */ 09470 if (vmu) { 09471 vmstate_delete(&vms); 09472 } 09473 #endif 09474 if (vmu) 09475 free_user(vmu); 09476 if (vms.deleted) 09477 ast_free(vms.deleted); 09478 if (vms.heard) 09479 ast_free(vms.heard); 09480 09481 #ifdef IMAP_STORAGE 09482 pthread_setspecific(ts_vmstate.key, NULL); 09483 #endif 09484 return res; 09485 }
| static int vm_forwardoptions | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| char * | curdir, | |||
| int | curmsg, | |||
| char * | vm_fmts, | |||
| char * | context, | |||
| signed char | record_gain, | |||
| long * | duration, | |||
| struct vm_state * | vms, | |||
| char * | flag | |||
| ) | [static] |
presents the option to prepend to an existing message when forwarding it.
| chan | ||
| vmu | ||
| curdir | ||
| curmsg | ||
| vmfmts | ||
| context | ||
| record_gain | ||
| duration | ||
| vms | Presents a prompt for 1 to prepend the current message, 2 to forward the message without prepending, or * to return to the main menu. |
This is invoked from forward_message() when performing a forward operation (option 8 from main menu).
Definition at line 6032 of file app_voicemail.c.
References ast_category_get(), ast_channel_setoption(), ast_config_destroy(), ast_config_load, ast_filecopy(), ast_filedelete(), AST_OPTION_RXGAIN, ast_play_and_prepend(), ast_play_and_wait(), ast_variable_retrieve(), ast_variable_update(), ast_waitfordigit(), CONFIG_FLAG_NOCACHE, config_text_file_save(), INTRO, make_file(), ast_vm_user::maxsecs, and play_record_review().
Referenced by forward_message().
06034 { 06035 #ifdef IMAP_STORAGE 06036 int res; 06037 #endif 06038 int cmd = 0; 06039 int retries = 0, prepend_duration = 0, already_recorded = 0; 06040 char msgfile[PATH_MAX], backup[PATH_MAX]; 06041 char textfile[PATH_MAX]; 06042 struct ast_config *msg_cfg; 06043 struct ast_flags config_flags = { CONFIG_FLAG_NOCACHE }; 06044 #ifndef IMAP_STORAGE 06045 signed char zero_gain = 0; 06046 #endif 06047 const char *duration_str; 06048 06049 /* Must always populate duration correctly */ 06050 make_file(msgfile, sizeof(msgfile), curdir, curmsg); 06051 strcpy(textfile, msgfile); 06052 strcpy(backup, msgfile); 06053 strncat(textfile, ".txt", sizeof(textfile) - strlen(textfile) - 1); 06054 strncat(backup, "-bak", sizeof(backup) - strlen(backup) - 1); 06055 06056 if ((msg_cfg = ast_config_load(textfile, config_flags)) && (duration_str = ast_variable_retrieve(msg_cfg, "message", "duration"))) { 06057 *duration = atoi(duration_str); 06058 } else { 06059 *duration = 0; 06060 } 06061 06062 while ((cmd >= 0) && (cmd != 't') && (cmd != '*')) { 06063 if (cmd) 06064 retries = 0; 06065 switch (cmd) { 06066 case '1': 06067 06068 #ifdef IMAP_STORAGE 06069 /* Record new intro file */ 06070 make_file(vms->introfn, sizeof(vms->introfn), curdir, curmsg); 06071 strncat(vms->introfn, "intro", sizeof(vms->introfn)); 06072 res = ast_play_and_wait(chan, INTRO); 06073 res = ast_play_and_wait(chan, "beep"); 06074 res = play_record_review(chan, NULL, vms->introfn, vmu->maxsecs, vm_fmts, 1, vmu, (int *)duration, NULL, record_gain, vms, flag); 06075 cmd = 't'; 06076 #else 06077 06078 /* prepend a message to the current message, update the metadata and return */ 06079 06080 make_file(msgfile, sizeof(msgfile), curdir, curmsg); 06081 strcpy(textfile, msgfile); 06082 strncat(textfile, ".txt", sizeof(textfile) - 1); 06083 *duration = 0; 06084 06085 /* if we can't read the message metadata, stop now */ 06086 if (!msg_cfg) { 06087 cmd = 0; 06088 break; 06089 } 06090 06091 /* Back up the original file, so we can retry the prepend */ 06092 if (already_recorded) 06093 ast_filecopy(backup, msgfile, NULL); 06094 else 06095 ast_filecopy(msgfile, backup, NULL); 06096 already_recorded = 1; 06097 06098 if (record_gain) 06099 ast_channel_setoption(chan, AST_OPTION_RXGAIN, &record_gain, sizeof(record_gain), 0); 06100 06101 cmd = ast_play_and_prepend(chan, NULL, msgfile, 0, vm_fmts, &prepend_duration, 1, silencethreshold, maxsilence); 06102 if (record_gain) 06103 ast_channel_setoption(chan, AST_OPTION_RXGAIN, &zero_gain, sizeof(zero_gain), 0); 06104 06105 06106 if ((duration_str = ast_variable_retrieve(msg_cfg, "message", "duration"))) 06107 *duration = atoi(duration_str); 06108 06109 if (prepend_duration) { 06110 struct ast_category *msg_cat; 06111 /* need enough space for a maximum-length message duration */ 06112 char duration_buf[12]; 06113 06114 *duration += prepend_duration; 06115 msg_cat = ast_category_get(msg_cfg, "message"); 06116 snprintf(duration_buf, 11, "%ld", *duration); 06117 if (!ast_variable_update(msg_cat, "duration", duration_buf, NULL, 0)) { 06118 config_text_file_save(textfile, msg_cfg, "app_voicemail"); 06119 } 06120 } 06121 06122 #endif 06123 break; 06124 case '2': 06125 /* NULL out introfile so we know there is no intro! */ 06126 #ifdef IMAP_STORAGE 06127 *vms->introfn = '\0'; 06128 #endif 06129 cmd = 't'; 06130 break; 06131 case '*': 06132 cmd = '*'; 06133 break; 06134 default: 06135 cmd = ast_play_and_wait(chan,"vm-forwardoptions"); 06136 /* "Press 1 to prepend a message or 2 to forward the message without prepending" */ 06137 if (!cmd) 06138 cmd = ast_play_and_wait(chan,"vm-starmain"); 06139 /* "press star to return to the main menu" */ 06140 if (!cmd) 06141 cmd = ast_waitfordigit(chan,6000); 06142 if (!cmd) 06143 retries++; 06144 if (retries > 3) 06145 cmd = 't'; 06146 } 06147 } 06148 06149 if (msg_cfg) 06150 ast_config_destroy(msg_cfg); 06151 if (already_recorded) 06152 ast_filedelete(backup, NULL); 06153 if (prepend_duration) 06154 *duration = prepend_duration; 06155 06156 if (cmd == 't' || cmd == 'S') 06157 cmd = 0; 06158 return cmd; 06159 }
| static int vm_instructions | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| int | skipadvanced, | |||
| int | in_urgent | |||
| ) | [static] |
Definition at line 8172 of file app_voicemail.c.
References vm_state::starting, vm_instructions_en(), and vm_instructions_zh().
Referenced by vm_execmain().
08173 { 08174 if (vms->starting && !strncasecmp(chan->language, "zh", 2)) { /* CHINESE (Taiwan) syntax */ 08175 return vm_instructions_zh(chan, vmu, vms, skipadvanced, in_urgent); 08176 } else { /* Default to ENGLISH */ 08177 return vm_instructions_en(chan, vmu, vms, skipadvanced, in_urgent); 08178 } 08179 }
| static int vm_instructions_en | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| int | skipadvanced, | |||
| int | in_urgent | |||
| ) | [static] |
Definition at line 8071 of file app_voicemail.c.
References ast_play_and_wait(), ast_test_flag, ast_waitfordigit(), vm_state::curmsg, vm_state::deleted, vm_state::lastmsg, vm_state::newmessages, vm_state::repeats, vm_state::starting, vm_state::urgentmessages, VM_MESSAGEWRAP, vm_play_folder_name(), and vm_state::vmbox.
Referenced by vm_instructions(), and vm_instructions_zh().
08072 { 08073 int res = 0; 08074 /* Play instructions and wait for new command */ 08075 while (!res) { 08076 if (vms->starting) { 08077 if (vms->lastmsg > -1) { 08078 if (skipadvanced) 08079 res = ast_play_and_wait(chan, "vm-onefor-full"); 08080 else 08081 res = ast_play_and_wait(chan, "vm-onefor"); 08082 if (!res) 08083 res = vm_play_folder_name(chan, vms->vmbox); 08084 } 08085 if (!res) { 08086 if (skipadvanced) 08087 res = ast_play_and_wait(chan, "vm-opts-full"); 08088 else 08089 res = ast_play_and_wait(chan, "vm-opts"); 08090 } 08091 } else { 08092 /* Added for additional help */ 08093 if (skipadvanced) { 08094 res = ast_play_and_wait(chan, "vm-onefor-full"); 08095 if (!res) 08096 res = vm_play_folder_name(chan, vms->vmbox); 08097 res = ast_play_and_wait(chan, "vm-opts-full"); 08098 } 08099 /* Logic: 08100 * If the current message is not the first OR 08101 * if we're listening to the first new message and there are 08102 * also urgent messages, then prompt for navigation to the 08103 * previous message 08104 */ 08105 if (vms->curmsg || (!in_urgent && vms->urgentmessages > 0) || (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms->lastmsg > 0)) { 08106 res = ast_play_and_wait(chan, "vm-prev"); 08107 } 08108 if (!res && !skipadvanced) 08109 res = ast_play_and_wait(chan, "vm-advopts"); 08110 if (!res) 08111 res = ast_play_and_wait(chan, "vm-repeat"); 08112 /* Logic: 08113 * If we're not listening to the last message OR 08114 * we're listening to the last urgent message and there are 08115 * also new non-urgent messages, then prompt for navigation 08116 * to the next message 08117 */ 08118 if (!res && ((vms->curmsg != vms->lastmsg) || (in_urgent && vms->newmessages > 0) || 08119 (ast_test_flag(vmu, VM_MESSAGEWRAP) && vms->lastmsg > 0) )) { 08120 res = ast_play_and_wait(chan, "vm-next"); 08121 } 08122 if (!res) { 08123 if (!vms->deleted[vms->curmsg]) 08124 res = ast_play_and_wait(chan, "vm-delete"); 08125 else 08126 res = ast_play_and_wait(chan, "vm-undelete"); 08127 if (!res) 08128 res = ast_play_and_wait(chan, "vm-toforward"); 08129 if (!res) 08130 res = ast_play_and_wait(chan, "vm-savemessage"); 08131 } 08132 } 08133 if (!res) { 08134 res = ast_play_and_wait(chan, "vm-helpexit"); 08135 } 08136 if (!res) 08137 res = ast_waitfordigit(chan, 6000); 08138 if (!res) { 08139 vms->repeats++; 08140 if (vms->repeats > 2) { 08141 res = 't'; 08142 } 08143 } 08144 } 08145 return res; 08146 }
| static int vm_instructions_zh | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| int | skipadvanced, | |||
| int | in_urgent | |||
| ) | [static] |
Definition at line 8148 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::lastmsg, vm_state::starting, vm_instructions_en(), vm_play_folder_name(), and vm_state::vmbox.
Referenced by vm_instructions().
08149 { 08150 int res = 0; 08151 /* Play instructions and wait for new command */ 08152 while (!res) { 08153 if (vms->lastmsg > -1) { 08154 res = ast_play_and_wait(chan, "vm-listen"); 08155 if (!res) 08156 res = vm_play_folder_name(chan, vms->vmbox); 08157 if (!res) 08158 res = ast_play_and_wait(chan, "press"); 08159 if (!res) 08160 res = ast_play_and_wait(chan, "digits/1"); 08161 } 08162 if (!res) 08163 res = ast_play_and_wait(chan, "vm-opts"); 08164 if (!res) { 08165 vms->starting = 0; 08166 return vm_instructions_en(chan, vmu, vms, skipadvanced, in_urgent); 08167 } 08168 } 08169 return res; 08170 }
| static int vm_intro | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 8019 of file app_voicemail.c.
References ast_fileexists(), ast_play_and_wait(), ast_test_flag, ast_vm_user::context, DISPOSE, ast_vm_user::mailbox, RETRIEVE, vm_state::username, vm_intro_cz(), vm_intro_de(), vm_intro_en(), vm_intro_es(), vm_intro_fr(), vm_intro_gr(), vm_intro_he(), vm_intro_it(), vm_intro_multilang(), vm_intro_nl(), vm_intro_no(), vm_intro_pl(), vm_intro_pt(), vm_intro_pt_BR(), vm_intro_se(), vm_intro_zh(), and VM_TEMPGREETWARN.
Referenced by vm_execmain().
08020 { 08021 char prefile[256]; 08022 08023 /* Notify the user that the temp greeting is set and give them the option to remove it */ 08024 snprintf(prefile, sizeof(prefile), "%s%s/%s/temp", VM_SPOOL_DIR, vmu->context, vms->username); 08025 if (ast_test_flag(vmu, VM_TEMPGREETWARN)) { 08026 RETRIEVE(prefile, -1, vmu->mailbox, vmu->context); 08027 if (ast_fileexists(prefile, NULL, NULL) > 0) { 08028 ast_play_and_wait(chan, "vm-tempgreetactive"); 08029 } 08030 DISPOSE(prefile, -1); 08031 } 08032 08033 /* Play voicemail intro - syntax is different for different languages */ 08034 if (!strcasecmp(chan->language, "de")) { /* GERMAN syntax */ 08035 return vm_intro_de(chan, vms); 08036 } else if (!strcasecmp(chan->language, "es")) { /* SPANISH syntax */ 08037 return vm_intro_es(chan, vms); 08038 } else if (!strcasecmp(chan->language, "it")) { /* ITALIAN syntax */ 08039 return vm_intro_it(chan, vms); 08040 } else if (!strcasecmp(chan->language, "fr")) { /* FRENCH syntax */ 08041 return vm_intro_fr(chan, vms); 08042 } else if (!strcasecmp(chan->language, "nl")) { /* DUTCH syntax */ 08043 return vm_intro_nl(chan, vms); 08044 } else if (!strcasecmp(chan->language, "pt")) { /* PORTUGUESE syntax */ 08045 return vm_intro_pt(chan, vms); 08046 } else if (!strcasecmp(chan->language, "pt_BR")) { /* BRAZILIAN PORTUGUESE syntax */ 08047 return vm_intro_pt_BR(chan, vms); 08048 } else if (!strcasecmp(chan->language, "cz")) { /* CZECH syntax */ 08049 return vm_intro_cz(chan, vms); 08050 } else if (!strcasecmp(chan->language, "gr")) { /* GREEK syntax */ 08051 return vm_intro_gr(chan, vms); 08052 } else if (!strcasecmp(chan->language, "pl")) { /* POLISH syntax */ 08053 return vm_intro_pl(chan, vms); 08054 } else if (!strcasecmp(chan->language, "se")) { /* SWEDISH syntax */ 08055 return vm_intro_se(chan, vms); 08056 } else if (!strcasecmp(chan->language, "no")) { /* NORWEGIAN syntax */ 08057 return vm_intro_no(chan, vms); 08058 } else if (!strcasecmp(chan->language, "ru")) { /* RUSSIAN syntax */ 08059 return vm_intro_multilang(chan, vms, "n"); 08060 } else if (!strncasecmp(chan->language, "zh", 2)) { /* CHINESE (Taiwan) syntax */ 08061 return vm_intro_zh(chan, vms); 08062 } else if (!strcasecmp(chan->language, "ua")) { /* UKRAINIAN syntax */ 08063 return vm_intro_multilang(chan, vms, "n"); 08064 } else if (!strcasecmp(chan->language, "he")) { /* HEBREW syntax */ 08065 return vm_intro_he(chan, vms); 08066 } else { /* Default to ENGLISH */ 08067 return vm_intro_en(chan, vms); 08068 } 08069 }
| static int vm_intro_cz | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7920 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07921 { 07922 int res; 07923 res = ast_play_and_wait(chan, "vm-youhave"); 07924 if (!res) { 07925 if (vms->newmessages) { 07926 if (vms->newmessages == 1) { 07927 res = ast_play_and_wait(chan, "digits/jednu"); 07928 } else { 07929 res = say_and_wait(chan, vms->newmessages, chan->language); 07930 } 07931 if (!res) { 07932 if ((vms->newmessages == 1)) 07933 res = ast_play_and_wait(chan, "vm-novou"); 07934 if ((vms->newmessages) > 1 && (vms->newmessages < 5)) 07935 res = ast_play_and_wait(chan, "vm-nove"); 07936 if (vms->newmessages > 4) 07937 res = ast_play_and_wait(chan, "vm-novych"); 07938 } 07939 if (vms->oldmessages && !res) 07940 res = ast_play_and_wait(chan, "vm-and"); 07941 else if (!res) { 07942 if ((vms->newmessages == 1)) 07943 res = ast_play_and_wait(chan, "vm-zpravu"); 07944 if ((vms->newmessages) > 1 && (vms->newmessages < 5)) 07945 res = ast_play_and_wait(chan, "vm-zpravy"); 07946 if (vms->newmessages > 4) 07947 res = ast_play_and_wait(chan, "vm-zprav"); 07948 } 07949 } 07950 if (!res && vms->oldmessages) { 07951 res = say_and_wait(chan, vms->oldmessages, chan->language); 07952 if (!res) { 07953 if ((vms->oldmessages == 1)) 07954 res = ast_play_and_wait(chan, "vm-starou"); 07955 if ((vms->oldmessages) > 1 && (vms->oldmessages < 5)) 07956 res = ast_play_and_wait(chan, "vm-stare"); 07957 if (vms->oldmessages > 4) 07958 res = ast_play_and_wait(chan, "vm-starych"); 07959 } 07960 if (!res) { 07961 if ((vms->oldmessages == 1)) 07962 res = ast_play_and_wait(chan, "vm-zpravu"); 07963 if ((vms->oldmessages) > 1 && (vms->oldmessages < 5)) 07964 res = ast_play_and_wait(chan, "vm-zpravy"); 07965 if (vms->oldmessages > 4) 07966 res = ast_play_and_wait(chan, "vm-zprav"); 07967 } 07968 } 07969 if (!res) { 07970 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07971 res = ast_play_and_wait(chan, "vm-no"); 07972 if (!res) 07973 res = ast_play_and_wait(chan, "vm-zpravy"); 07974 } 07975 } 07976 } 07977 return res; 07978 }
| static int vm_intro_de | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7616 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07617 { 07618 /* Introduce messages they have */ 07619 int res; 07620 res = ast_play_and_wait(chan, "vm-youhave"); 07621 if (!res) { 07622 if (vms->newmessages) { 07623 if ((vms->newmessages == 1)) 07624 res = ast_play_and_wait(chan, "digits/1F"); 07625 else 07626 res = say_and_wait(chan, vms->newmessages, chan->language); 07627 if (!res) 07628 res = ast_play_and_wait(chan, "vm-INBOX"); 07629 if (vms->oldmessages && !res) 07630 res = ast_play_and_wait(chan, "vm-and"); 07631 else if (!res) { 07632 if ((vms->newmessages == 1)) 07633 res = ast_play_and_wait(chan, "vm-message"); 07634 else 07635 res = ast_play_and_wait(chan, "vm-messages"); 07636 } 07637 07638 } 07639 if (!res && vms->oldmessages) { 07640 if (vms->oldmessages == 1) 07641 res = ast_play_and_wait(chan, "digits/1F"); 07642 else 07643 res = say_and_wait(chan, vms->oldmessages, chan->language); 07644 if (!res) 07645 res = ast_play_and_wait(chan, "vm-Old"); 07646 if (!res) { 07647 if (vms->oldmessages == 1) 07648 res = ast_play_and_wait(chan, "vm-message"); 07649 else 07650 res = ast_play_and_wait(chan, "vm-messages"); 07651 } 07652 } 07653 if (!res) { 07654 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07655 res = ast_play_and_wait(chan, "vm-no"); 07656 if (!res) 07657 res = ast_play_and_wait(chan, "vm-messages"); 07658 } 07659 } 07660 } 07661 return res; 07662 }
| static int vm_intro_en | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7365 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07366 { 07367 int res; 07368 07369 /* Introduce messages they have */ 07370 res = ast_play_and_wait(chan, "vm-youhave"); 07371 if (!res) { 07372 if (vms->urgentmessages) { 07373 res = say_and_wait(chan, vms->urgentmessages, chan->language); 07374 if (!res) 07375 res = ast_play_and_wait(chan, "vm-Urgent"); 07376 if ((vms->oldmessages || vms->newmessages) && !res) { 07377 res = ast_play_and_wait(chan, "vm-and"); 07378 } else if (!res) { 07379 if ((vms->urgentmessages == 1)) 07380 res = ast_play_and_wait(chan, "vm-message"); 07381 else 07382 res = ast_play_and_wait(chan, "vm-messages"); 07383 } 07384 } 07385 if (vms->newmessages) { 07386 res = say_and_wait(chan, vms->newmessages, chan->language); 07387 if (!res) 07388 res = ast_play_and_wait(chan, "vm-INBOX"); 07389 if (vms->oldmessages && !res) 07390 res = ast_play_and_wait(chan, "vm-and"); 07391 else if (!res) { 07392 if ((vms->newmessages == 1)) 07393 res = ast_play_and_wait(chan, "vm-message"); 07394 else 07395 res = ast_play_and_wait(chan, "vm-messages"); 07396 } 07397 07398 } 07399 if (!res && vms->oldmessages) { 07400 res = say_and_wait(chan, vms->oldmessages, chan->language); 07401 if (!res) 07402 res = ast_play_and_wait(chan, "vm-Old"); 07403 if (!res) { 07404 if (vms->oldmessages == 1) 07405 res = ast_play_and_wait(chan, "vm-message"); 07406 else 07407 res = ast_play_and_wait(chan, "vm-messages"); 07408 } 07409 } 07410 if (!res) { 07411 if (!vms->urgentmessages && !vms->oldmessages && !vms->newmessages) { 07412 res = ast_play_and_wait(chan, "vm-no"); 07413 if (!res) 07414 res = ast_play_and_wait(chan, "vm-messages"); 07415 } 07416 } 07417 } 07418 return res; 07419 }
| static int vm_intro_es | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7665 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07666 { 07667 /* Introduce messages they have */ 07668 int res; 07669 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07670 res = ast_play_and_wait(chan, "vm-youhaveno"); 07671 if (!res) 07672 res = ast_play_and_wait(chan, "vm-messages"); 07673 } else { 07674 res = ast_play_and_wait(chan, "vm-youhave"); 07675 } 07676 if (!res) { 07677 if (vms->newmessages) { 07678 if (!res) { 07679 if ((vms->newmessages == 1)) { 07680 res = ast_play_and_wait(chan, "digits/1M"); 07681 if (!res) 07682 res = ast_play_and_wait(chan, "vm-message"); 07683 if (!res) 07684 res = ast_play_and_wait(chan, "vm-INBOXs"); 07685 } else { 07686 res = say_and_wait(chan, vms->newmessages, chan->language); 07687 if (!res) 07688 res = ast_play_and_wait(chan, "vm-messages"); 07689 if (!res) 07690 res = ast_play_and_wait(chan, "vm-INBOX"); 07691 } 07692 } 07693 if (vms->oldmessages && !res) 07694 res = ast_play_and_wait(chan, "vm-and"); 07695 } 07696 if (vms->oldmessages) { 07697 if (!res) { 07698 if (vms->oldmessages == 1) { 07699 res = ast_play_and_wait(chan, "digits/1M"); 07700 if (!res) 07701 res = ast_play_and_wait(chan, "vm-message"); 07702 if (!res) 07703 res = ast_play_and_wait(chan, "vm-Olds"); 07704 } else { 07705 res = say_and_wait(chan, vms->oldmessages, chan->language); 07706 if (!res) 07707 res = ast_play_and_wait(chan, "vm-messages"); 07708 if (!res) 07709 res = ast_play_and_wait(chan, "vm-Old"); 07710 } 07711 } 07712 } 07713 } 07714 return res; 07715 }
| static int vm_intro_fr | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7763 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07764 { 07765 /* Introduce messages they have */ 07766 int res; 07767 res = ast_play_and_wait(chan, "vm-youhave"); 07768 if (!res) { 07769 if (vms->newmessages) { 07770 res = say_and_wait(chan, vms->newmessages, chan->language); 07771 if (!res) 07772 res = ast_play_and_wait(chan, "vm-INBOX"); 07773 if (vms->oldmessages && !res) 07774 res = ast_play_and_wait(chan, "vm-and"); 07775 else if (!res) { 07776 if ((vms->newmessages == 1)) 07777 res = ast_play_and_wait(chan, "vm-message"); 07778 else 07779 res = ast_play_and_wait(chan, "vm-messages"); 07780 } 07781 07782 } 07783 if (!res && vms->oldmessages) { 07784 res = say_and_wait(chan, vms->oldmessages, chan->language); 07785 if (!res) 07786 res = ast_play_and_wait(chan, "vm-Old"); 07787 if (!res) { 07788 if (vms->oldmessages == 1) 07789 res = ast_play_and_wait(chan, "vm-message"); 07790 else 07791 res = ast_play_and_wait(chan, "vm-messages"); 07792 } 07793 } 07794 if (!res) { 07795 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07796 res = ast_play_and_wait(chan, "vm-no"); 07797 if (!res) 07798 res = ast_play_and_wait(chan, "vm-messages"); 07799 } 07800 } 07801 } 07802 return res; 07803 }
| static int vm_intro_gr | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7164 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), vm_state::newmessages, and vm_state::oldmessages.
Referenced by vm_intro().
07165 { 07166 int res = 0; 07167 07168 if (vms->newmessages) { 07169 res = ast_play_and_wait(chan, "vm-youhave"); 07170 if (!res) 07171 res = ast_say_number(chan, vms->newmessages, AST_DIGIT_ANY, chan->language, NULL); 07172 if (!res) { 07173 if ((vms->newmessages == 1)) { 07174 res = ast_play_and_wait(chan, "vm-INBOX"); 07175 if (!res) 07176 res = ast_play_and_wait(chan, "vm-message"); 07177 } else { 07178 res = ast_play_and_wait(chan, "vm-INBOXs"); 07179 if (!res) 07180 res = ast_play_and_wait(chan, "vm-messages"); 07181 } 07182 } 07183 } else if (vms->oldmessages){ 07184 res = ast_play_and_wait(chan, "vm-youhave"); 07185 if (!res) 07186 res = ast_say_number(chan, vms->oldmessages, AST_DIGIT_ANY, chan->language, NULL); 07187 if ((vms->oldmessages == 1)){ 07188 res = ast_play_and_wait(chan, "vm-Old"); 07189 if (!res) 07190 res = ast_play_and_wait(chan, "vm-message"); 07191 } else { 07192 res = ast_play_and_wait(chan, "vm-Olds"); 07193 if (!res) 07194 res = ast_play_and_wait(chan, "vm-messages"); 07195 } 07196 } else if (!vms->oldmessages && !vms->newmessages) 07197 res = ast_play_and_wait(chan, "vm-denExeteMynhmata"); 07198 return res; 07199 }
| static int vm_intro_he | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7298 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), vm_state::newmessages, and vm_state::oldmessages.
Referenced by vm_intro().
07299 { 07300 int res = 0; 07301 07302 /* Introduce messages they have */ 07303 if (!res) { 07304 if ((vms->newmessages) || (vms->oldmessages)) { 07305 res = ast_play_and_wait(chan, "vm-youhave"); 07306 } 07307 /* 07308 * The word "shtei" refers to the number 2 in hebrew when performing a count 07309 * of elements. In Hebrew, there are 6 forms of enumerating the number 2 for 07310 * an element, this is one of them. 07311 */ 07312 if (vms->newmessages) { 07313 if (!res) { 07314 if (vms->newmessages == 1) { 07315 res = ast_play_and_wait(chan, "vm-INBOX1"); 07316 } else { 07317 if (vms->newmessages == 2) { 07318 res = ast_play_and_wait(chan, "vm-shtei"); 07319 } else { 07320 res = ast_say_number(chan, vms->newmessages, AST_DIGIT_ANY, chan->language, "f"); 07321 } 07322 res = ast_play_and_wait(chan, "vm-INBOX"); 07323 } 07324 } 07325 if (vms->oldmessages && !res) { 07326 res = ast_play_and_wait(chan, "vm-and"); 07327 if (vms->oldmessages == 1) { 07328 res = ast_play_and_wait(chan, "vm-Old1"); 07329 } else { 07330 if (vms->oldmessages == 2) { 07331 res = ast_play_and_wait(chan, "vm-shtei"); 07332 } else { 07333 res = ast_say_number(chan, vms->oldmessages, AST_DIGIT_ANY, chan->language, "f"); 07334 } 07335 res = ast_play_and_wait(chan, "vm-Old"); 07336 } 07337 } 07338 } 07339 if (!res && vms->oldmessages && !vms->newmessages) { 07340 if (!res) { 07341 if (vms->oldmessages == 1) { 07342 res = ast_play_and_wait(chan, "vm-Old1"); 07343 } else { 07344 if (vms->oldmessages == 2) { 07345 res = ast_play_and_wait(chan, "vm-shtei"); 07346 } else { 07347 res = ast_say_number(chan, vms->oldmessages, AST_DIGIT_ANY, chan->language, "f"); 07348 } 07349 res = ast_play_and_wait(chan, "vm-Old"); 07350 } 07351 } 07352 } 07353 if (!res) { 07354 if (!vms->oldmessages && !vms->newmessages) { 07355 if (!res) { 07356 res = ast_play_and_wait(chan, "vm-nomessages"); 07357 } 07358 } 07359 } 07360 } 07361 return res; 07362 }
| static int vm_intro_it | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7422 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07423 { 07424 /* Introduce messages they have */ 07425 int res; 07426 if (!vms->oldmessages && !vms->newmessages &&!vms->urgentmessages) 07427 res = ast_play_and_wait(chan, "vm-no") || 07428 ast_play_and_wait(chan, "vm-message"); 07429 else 07430 res = ast_play_and_wait(chan, "vm-youhave"); 07431 if (!res && vms->newmessages) { 07432 res = (vms->newmessages == 1) ? 07433 ast_play_and_wait(chan, "digits/un") || 07434 ast_play_and_wait(chan, "vm-nuovo") || 07435 ast_play_and_wait(chan, "vm-message") : 07436 /* 2 or more new messages */ 07437 say_and_wait(chan, vms->newmessages, chan->language) || 07438 ast_play_and_wait(chan, "vm-nuovi") || 07439 ast_play_and_wait(chan, "vm-messages"); 07440 if (!res && vms->oldmessages) 07441 res = ast_play_and_wait(chan, "vm-and"); 07442 } 07443 if (!res && vms->oldmessages) { 07444 res = (vms->oldmessages == 1) ? 07445 ast_play_and_wait(chan, "digits/un") || 07446 ast_play_and_wait(chan, "vm-vecchio") || 07447 ast_play_and_wait(chan, "vm-message") : 07448 /* 2 or more old messages */ 07449 say_and_wait(chan, vms->oldmessages, chan->language) || 07450 ast_play_and_wait(chan, "vm-vecchi") || 07451 ast_play_and_wait(chan, "vm-messages"); 07452 } 07453 return res; 07454 }
| static int vm_intro_multilang | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| const char | message_gender[] | |||
| ) | [static] |
Definition at line 7258 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_counted_adjective(), ast_say_counted_noun(), ast_say_number(), vm_state::newmessages, and vm_state::oldmessages.
Referenced by vm_intro().
07259 { 07260 int res; 07261 int lastnum = 0; 07262 07263 res = ast_play_and_wait(chan, "vm-youhave"); 07264 07265 if (!res && vms->newmessages) { 07266 lastnum = vms->newmessages; 07267 07268 if (!(res = ast_say_number(chan, lastnum, AST_DIGIT_ANY, chan->language, message_gender))) { 07269 res = ast_say_counted_adjective(chan, lastnum, "vm-new", message_gender); 07270 } 07271 07272 if (!res && vms->oldmessages) { 07273 res = ast_play_and_wait(chan, "vm-and"); 07274 } 07275 } 07276 07277 if (!res && vms->oldmessages) { 07278 lastnum = vms->oldmessages; 07279 07280 if (!(res = ast_say_number(chan, lastnum, AST_DIGIT_ANY, chan->language, message_gender))) { 07281 res = ast_say_counted_adjective(chan, lastnum, "vm-old", message_gender); 07282 } 07283 } 07284 07285 if (!res) { 07286 if (lastnum == 0) { 07287 res = ast_play_and_wait(chan, "vm-no"); 07288 } 07289 if (!res) { 07290 res = ast_say_counted_noun(chan, lastnum, "vm-message"); 07291 } 07292 } 07293 07294 return res; 07295 }
| static int vm_intro_nl | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7806 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07807 { 07808 /* Introduce messages they have */ 07809 int res; 07810 res = ast_play_and_wait(chan, "vm-youhave"); 07811 if (!res) { 07812 if (vms->newmessages) { 07813 res = say_and_wait(chan, vms->newmessages, chan->language); 07814 if (!res) { 07815 if (vms->newmessages == 1) 07816 res = ast_play_and_wait(chan, "vm-INBOXs"); 07817 else 07818 res = ast_play_and_wait(chan, "vm-INBOX"); 07819 } 07820 if (vms->oldmessages && !res) 07821 res = ast_play_and_wait(chan, "vm-and"); 07822 else if (!res) { 07823 if ((vms->newmessages == 1)) 07824 res = ast_play_and_wait(chan, "vm-message"); 07825 else 07826 res = ast_play_and_wait(chan, "vm-messages"); 07827 } 07828 07829 } 07830 if (!res && vms->oldmessages) { 07831 res = say_and_wait(chan, vms->oldmessages, chan->language); 07832 if (!res) { 07833 if (vms->oldmessages == 1) 07834 res = ast_play_and_wait(chan, "vm-Olds"); 07835 else 07836 res = ast_play_and_wait(chan, "vm-Old"); 07837 } 07838 if (!res) { 07839 if (vms->oldmessages == 1) 07840 res = ast_play_and_wait(chan, "vm-message"); 07841 else 07842 res = ast_play_and_wait(chan, "vm-messages"); 07843 } 07844 } 07845 if (!res) { 07846 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07847 res = ast_play_and_wait(chan, "vm-no"); 07848 if (!res) 07849 res = ast_play_and_wait(chan, "vm-messages"); 07850 } 07851 } 07852 } 07853 return res; 07854 }
| static int vm_intro_no | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7572 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07573 { 07574 /* Introduce messages they have */ 07575 int res; 07576 07577 res = ast_play_and_wait(chan, "vm-youhave"); 07578 if (res) 07579 return res; 07580 07581 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07582 res = ast_play_and_wait(chan, "vm-no"); 07583 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07584 return res; 07585 } 07586 07587 if (vms->newmessages) { 07588 if ((vms->newmessages == 1)) { 07589 res = ast_play_and_wait(chan, "digits/1"); 07590 res = res ? res : ast_play_and_wait(chan, "vm-ny"); 07591 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07592 } else { 07593 res = say_and_wait(chan, vms->newmessages, chan->language); 07594 res = res ? res : ast_play_and_wait(chan, "vm-nye"); 07595 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07596 } 07597 if (!res && vms->oldmessages) 07598 res = ast_play_and_wait(chan, "vm-and"); 07599 } 07600 if (!res && vms->oldmessages) { 07601 if (vms->oldmessages == 1) { 07602 res = ast_play_and_wait(chan, "digits/1"); 07603 res = res ? res : ast_play_and_wait(chan, "vm-gamel"); 07604 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07605 } else { 07606 res = say_and_wait(chan, vms->oldmessages, chan->language); 07607 res = res ? res : ast_play_and_wait(chan, "vm-gamle"); 07608 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07609 } 07610 } 07611 07612 return res; 07613 }
| static int vm_intro_pl | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7457 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, num, vm_state::oldmessages, and say_and_wait().
Referenced by vm_intro().
07458 { 07459 /* Introduce messages they have */ 07460 int res; 07461 div_t num; 07462 07463 if (!vms->oldmessages && !vms->newmessages) { 07464 res = ast_play_and_wait(chan, "vm-no"); 07465 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07466 return res; 07467 } else { 07468 res = ast_play_and_wait(chan, "vm-youhave"); 07469 } 07470 07471 if (vms->newmessages) { 07472 num = div(vms->newmessages, 10); 07473 if (vms->newmessages == 1) { 07474 res = ast_play_and_wait(chan, "digits/1-a"); 07475 res = res ? res : ast_play_and_wait(chan, "vm-new-a"); 07476 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07477 } else if (num.rem > 1 && num.rem < 5 && num.quot != 1) { 07478 if (num.rem == 2) { 07479 if (!num.quot) { 07480 res = ast_play_and_wait(chan, "digits/2-ie"); 07481 } else { 07482 res = say_and_wait(chan, vms->newmessages - 2 , chan->language); 07483 res = res ? res : ast_play_and_wait(chan, "digits/2-ie"); 07484 } 07485 } else { 07486 res = say_and_wait(chan, vms->newmessages, chan->language); 07487 } 07488 res = res ? res : ast_play_and_wait(chan, "vm-new-e"); 07489 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07490 } else { 07491 res = say_and_wait(chan, vms->newmessages, chan->language); 07492 res = res ? res : ast_play_and_wait(chan, "vm-new-ych"); 07493 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07494 } 07495 if (!res && vms->oldmessages) 07496 res = ast_play_and_wait(chan, "vm-and"); 07497 } 07498 if (!res && vms->oldmessages) { 07499 num = div(vms->oldmessages, 10); 07500 if (vms->oldmessages == 1) { 07501 res = ast_play_and_wait(chan, "digits/1-a"); 07502 res = res ? res : ast_play_and_wait(chan, "vm-old-a"); 07503 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07504 } else if (num.rem > 1 && num.rem < 5 && num.quot != 1) { 07505 if (num.rem == 2) { 07506 if (!num.quot) { 07507 res = ast_play_and_wait(chan, "digits/2-ie"); 07508 } else { 07509 res = say_and_wait(chan, vms->oldmessages - 2 , chan->language); 07510 res = res ? res : ast_play_and_wait(chan, "digits/2-ie"); 07511 } 07512 } else { 07513 res = say_and_wait(chan, vms->oldmessages, chan->language); 07514 } 07515 res = res ? res : ast_play_and_wait(chan, "vm-old-e"); 07516 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07517 } else { 07518 res = say_and_wait(chan, vms->oldmessages, chan->language); 07519 res = res ? res : ast_play_and_wait(chan, "vm-old-ych"); 07520 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07521 } 07522 } 07523 07524 return res; 07525 }
| static int vm_intro_pt | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7857 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), vm_state::newmessages, vm_state::oldmessages, and vm_state::urgentmessages.
Referenced by vm_intro().
07858 { 07859 /* Introduce messages they have */ 07860 int res; 07861 res = ast_play_and_wait(chan, "vm-youhave"); 07862 if (!res) { 07863 if (vms->newmessages) { 07864 res = ast_say_number(chan, vms->newmessages, AST_DIGIT_ANY, chan->language, "f"); 07865 if (!res) { 07866 if ((vms->newmessages == 1)) { 07867 res = ast_play_and_wait(chan, "vm-message"); 07868 if (!res) 07869 res = ast_play_and_wait(chan, "vm-INBOXs"); 07870 } else { 07871 res = ast_play_and_wait(chan, "vm-messages"); 07872 if (!res) 07873 res = ast_play_and_wait(chan, "vm-INBOX"); 07874 } 07875 } 07876 if (vms->oldmessages && !res) 07877 res = ast_play_and_wait(chan, "vm-and"); 07878 } 07879 if (!res && vms->oldmessages) { 07880 res = ast_say_number(chan, vms->oldmessages, AST_DIGIT_ANY, chan->language, "f"); 07881 if (!res) { 07882 if (vms->oldmessages == 1) { 07883 res = ast_play_and_wait(chan, "vm-message"); 07884 if (!res) 07885 res = ast_play_and_wait(chan, "vm-Olds"); 07886 } else { 07887 res = ast_play_and_wait(chan, "vm-messages"); 07888 if (!res) 07889 res = ast_play_and_wait(chan, "vm-Old"); 07890 } 07891 } 07892 } 07893 if (!res) { 07894 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07895 res = ast_play_and_wait(chan, "vm-no"); 07896 if (!res) 07897 res = ast_play_and_wait(chan, "vm-messages"); 07898 } 07899 } 07900 } 07901 return res; 07902 }
| static int vm_intro_pt_BR | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7718 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_play_and_wait(), ast_say_number(), vm_state::newmessages, vm_state::oldmessages, and vm_state::urgentmessages.
Referenced by vm_intro().
07718 { 07719 /* Introduce messages they have */ 07720 int res; 07721 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07722 res = ast_play_and_wait(chan, "vm-nomessages"); 07723 return res; 07724 } else { 07725 res = ast_play_and_wait(chan, "vm-youhave"); 07726 } 07727 if (vms->newmessages) { 07728 if (!res) 07729 res = ast_say_number(chan, vms->newmessages, AST_DIGIT_ANY, chan->language, "f"); 07730 if ((vms->newmessages == 1)) { 07731 if (!res) 07732 res = ast_play_and_wait(chan, "vm-message"); 07733 if (!res) 07734 res = ast_play_and_wait(chan, "vm-INBOXs"); 07735 } else { 07736 if (!res) 07737 res = ast_play_and_wait(chan, "vm-messages"); 07738 if (!res) 07739 res = ast_play_and_wait(chan, "vm-INBOX"); 07740 } 07741 if (vms->oldmessages && !res) 07742 res = ast_play_and_wait(chan, "vm-and"); 07743 } 07744 if (vms->oldmessages) { 07745 if (!res) 07746 res = ast_say_number(chan, vms->oldmessages, AST_DIGIT_ANY, chan->language, "f"); 07747 if (vms->oldmessages == 1) { 07748 if (!res) 07749 res = ast_play_and_wait(chan, "vm-message"); 07750 if (!res) 07751 res = ast_play_and_wait(chan, "vm-Olds"); 07752 } else { 07753 if (!res) 07754 res = ast_play_and_wait(chan, "vm-messages"); 07755 if (!res) 07756 res = ast_play_and_wait(chan, "vm-Old"); 07757 } 07758 } 07759 return res; 07760 }
| static int vm_intro_se | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7528 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, say_and_wait(), and vm_state::urgentmessages.
Referenced by vm_intro().
07529 { 07530 /* Introduce messages they have */ 07531 int res; 07532 07533 res = ast_play_and_wait(chan, "vm-youhave"); 07534 if (res) 07535 return res; 07536 07537 if (!vms->oldmessages && !vms->newmessages && !vms->urgentmessages) { 07538 res = ast_play_and_wait(chan, "vm-no"); 07539 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07540 return res; 07541 } 07542 07543 if (vms->newmessages) { 07544 if ((vms->newmessages == 1)) { 07545 res = ast_play_and_wait(chan, "digits/ett"); 07546 res = res ? res : ast_play_and_wait(chan, "vm-nytt"); 07547 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07548 } else { 07549 res = say_and_wait(chan, vms->newmessages, chan->language); 07550 res = res ? res : ast_play_and_wait(chan, "vm-nya"); 07551 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07552 } 07553 if (!res && vms->oldmessages) 07554 res = ast_play_and_wait(chan, "vm-and"); 07555 } 07556 if (!res && vms->oldmessages) { 07557 if (vms->oldmessages == 1) { 07558 res = ast_play_and_wait(chan, "digits/ett"); 07559 res = res ? res : ast_play_and_wait(chan, "vm-gammalt"); 07560 res = res ? res : ast_play_and_wait(chan, "vm-message"); 07561 } else { 07562 res = say_and_wait(chan, vms->oldmessages, chan->language); 07563 res = res ? res : ast_play_and_wait(chan, "vm-gamla"); 07564 res = res ? res : ast_play_and_wait(chan, "vm-messages"); 07565 } 07566 } 07567 07568 return res; 07569 }
| static int vm_intro_zh | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms | |||
| ) | [static] |
Definition at line 7981 of file app_voicemail.c.
References ast_play_and_wait(), vm_state::newmessages, vm_state::oldmessages, and say_and_wait().
Referenced by vm_intro().
07982 { 07983 int res; 07984 /* Introduce messages they have */ 07985 res = ast_play_and_wait(chan, "vm-you"); 07986 07987 if (!res && vms->newmessages) { 07988 res = ast_play_and_wait(chan, "vm-have"); 07989 if (!res) 07990 res = say_and_wait(chan, vms->newmessages, chan->language); 07991 if (!res) 07992 res = ast_play_and_wait(chan, "vm-tong"); 07993 if (!res) 07994 res = ast_play_and_wait(chan, "vm-INBOX"); 07995 if (vms->oldmessages && !res) 07996 res = ast_play_and_wait(chan, "vm-and"); 07997 else if (!res) 07998 res = ast_play_and_wait(chan, "vm-messages"); 07999 } 08000 if (!res && vms->oldmessages) { 08001 res = ast_play_and_wait(chan, "vm-have"); 08002 if (!res) 08003 res = say_and_wait(chan, vms->oldmessages, chan->language); 08004 if (!res) 08005 res = ast_play_and_wait(chan, "vm-tong"); 08006 if (!res) 08007 res = ast_play_and_wait(chan, "vm-Old"); 08008 if (!res) 08009 res = ast_play_and_wait(chan, "vm-messages"); 08010 } 08011 if (!res && !vms->oldmessages && !vms->newmessages) { 08012 res = ast_play_and_wait(chan, "vm-haveno"); 08013 if (!res) 08014 res = ast_play_and_wait(chan, "vm-messages"); 08015 } 08016 return res; 08017 }
| static int vm_lock_path | ( | const char * | path | ) | [static] |
Lock file path only return failure if ast_lock_path returns 'timeout', not if the path does not exist or any other reason.
Definition at line 2725 of file app_voicemail.c.
References ast_lock_path(), and AST_LOCK_TIMEOUT.
Referenced by close_mailbox(), copy_message(), count_messages(), leave_voicemail(), open_mailbox(), and save_to_folder().
02726 { 02727 switch (ast_lock_path(path)) { 02728 case AST_LOCK_TIMEOUT: 02729 return -1; 02730 default: 02731 return 0; 02732 } 02733 }
| static FILE* vm_mkftemp | ( | char * | template | ) | [static] |
Definition at line 1272 of file app_voicemail.c.
References VOICEMAIL_FILE_MODE.
Referenced by sendmail(), and sendpage().
01273 { 01274 FILE *p = NULL; 01275 int pfd = mkstemp(template); 01276 chmod(template, VOICEMAIL_FILE_MODE & ~my_umask); 01277 if (pfd > -1) { 01278 p = fdopen(pfd, "w+"); 01279 if (!p) { 01280 close(pfd); 01281 pfd = -1; 01282 } 01283 } 01284 return p; 01285 }
| static int vm_newuser | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| char * | fmtc, | |||
| signed char | record_gain | |||
| ) | [static] |
Definition at line 8182 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, adsi_logo(), ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, ast_debug, ast_fileexists(), ast_log(), AST_LOG_NOTICE, ast_play_and_wait(), ast_readstring(), ast_strlen_zero(), ast_test_flag, check_password(), ast_vm_user::context, play_record_review(), PWDCHANGE_EXTERNAL, PWDCHANGE_INTERNAL, vm_state::username, vm_change_password(), vm_change_password_shell(), VM_FORCEGREET, VM_FORCENAME, vm_invalid_password, vm_mismatch, vm_newpassword, vm_passchanged, and vm_reenterpassword.
Referenced by vm_execmain().
08183 { 08184 int cmd = 0; 08185 int duration = 0; 08186 int tries = 0; 08187 char newpassword[80] = ""; 08188 char newpassword2[80] = ""; 08189 char prefile[PATH_MAX] = ""; 08190 unsigned char buf[256]; 08191 int bytes=0; 08192 08193 if (ast_adsi_available(chan)) { 08194 bytes += adsi_logo(buf + bytes); 08195 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "New User Setup", ""); 08196 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "Not Done", ""); 08197 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 08198 bytes += ast_adsi_voice_mode(buf + bytes, 0); 08199 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 08200 } 08201 08202 /* First, have the user change their password 08203 so they won't get here again */ 08204 for (;;) { 08205 newpassword[1] = '\0'; 08206 newpassword[0] = cmd = ast_play_and_wait(chan, vm_newpassword); 08207 if (cmd == '#') 08208 newpassword[0] = '\0'; 08209 if (cmd < 0 || cmd == 't' || cmd == '#') 08210 return cmd; 08211 cmd = ast_readstring(chan,newpassword + strlen(newpassword),sizeof(newpassword)-1,2000,10000,"#"); 08212 if (cmd < 0 || cmd == 't' || cmd == '#') 08213 return cmd; 08214 cmd = check_password(vmu, newpassword); /* perform password validation */ 08215 if (cmd != 0) { 08216 ast_log(AST_LOG_NOTICE, "Invalid password for user %s (%s)\n", vms->username, newpassword); 08217 cmd = ast_play_and_wait(chan, vm_invalid_password); 08218 } else { 08219 newpassword2[1] = '\0'; 08220 newpassword2[0] = cmd = ast_play_and_wait(chan, vm_reenterpassword); 08221 if (cmd == '#') 08222 newpassword2[0] = '\0'; 08223 if (cmd < 0 || cmd == 't' || cmd == '#') 08224 return cmd; 08225 cmd = ast_readstring(chan, newpassword2 + strlen(newpassword2), sizeof(newpassword2) - 1, 2000, 10000, "#"); 08226 if (cmd < 0 || cmd == 't' || cmd == '#') 08227 return cmd; 08228 if (!strcmp(newpassword, newpassword2)) 08229 break; 08230 ast_log(AST_LOG_NOTICE, "Password mismatch for user %s (%s != %s)\n", vms->username, newpassword, newpassword2); 08231 cmd = ast_play_and_wait(chan, vm_mismatch); 08232 } 08233 if (++tries == 3) 08234 return -1; 08235 } 08236 if (pwdchange & PWDCHANGE_INTERNAL) 08237 vm_change_password(vmu, newpassword); 08238 if ((pwdchange & PWDCHANGE_EXTERNAL) && !ast_strlen_zero(ext_pass_cmd)) 08239 vm_change_password_shell(vmu, newpassword); 08240 08241 ast_debug(1,"User %s set password to %s of length %d\n",vms->username,newpassword,(int)strlen(newpassword)); 08242 cmd = ast_play_and_wait(chan, vm_passchanged); 08243 08244 /* If forcename is set, have the user record their name */ 08245 if (ast_test_flag(vmu, VM_FORCENAME)) { 08246 snprintf(prefile,sizeof(prefile), "%s%s/%s/greet", VM_SPOOL_DIR, vmu->context, vms->username); 08247 if (ast_fileexists(prefile, NULL, NULL) < 1) { 08248 cmd = play_record_review(chan, "vm-rec-name", prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08249 if (cmd < 0 || cmd == 't' || cmd == '#') 08250 return cmd; 08251 } 08252 } 08253 08254 /* If forcegreetings is set, have the user record their greetings */ 08255 if (ast_test_flag(vmu, VM_FORCEGREET)) { 08256 snprintf(prefile,sizeof(prefile), "%s%s/%s/unavail", VM_SPOOL_DIR, vmu->context, vms->username); 08257 if (ast_fileexists(prefile, NULL, NULL) < 1) { 08258 cmd = play_record_review(chan, "vm-rec-unv", prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08259 if (cmd < 0 || cmd == 't' || cmd == '#') 08260 return cmd; 08261 } 08262 08263 snprintf(prefile,sizeof(prefile), "%s%s/%s/busy", VM_SPOOL_DIR, vmu->context, vms->username); 08264 if (ast_fileexists(prefile, NULL, NULL) < 1) { 08265 cmd = play_record_review(chan, "vm-rec-busy", prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08266 if (cmd < 0 || cmd == 't' || cmd == '#') 08267 return cmd; 08268 } 08269 } 08270 08271 return cmd; 08272 }
| static int vm_options | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| char * | fmtc, | |||
| signed char | record_gain | |||
| ) | [static] |
Definition at line 8274 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, adsi_logo(), ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, ast_debug, ast_fileexists(), ast_log(), AST_LOG_NOTICE, ast_play_and_wait(), ast_readstring(), ast_strlen_zero(), ast_waitfordigit(), check_password(), ast_vm_user::context, DISPOSE, ast_vm_user::mailbox, ast_vm_user::password, play_record_review(), PWDCHANGE_EXTERNAL, PWDCHANGE_INTERNAL, RETRIEVE, vm_state::username, vm_change_password(), vm_change_password_shell(), vm_invalid_password, vm_mismatch, vm_newpassword, vm_passchanged, vm_reenterpassword, and vm_tempgreeting().
Referenced by vm_execmain().
08275 { 08276 int cmd = 0; 08277 int retries = 0; 08278 int duration = 0; 08279 char newpassword[80] = ""; 08280 char newpassword2[80] = ""; 08281 char prefile[PATH_MAX] = ""; 08282 unsigned char buf[256]; 08283 int bytes=0; 08284 08285 if (ast_adsi_available(chan)) { 08286 bytes += adsi_logo(buf + bytes); 08287 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Options Menu", ""); 08288 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "Not Done", ""); 08289 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 08290 bytes += ast_adsi_voice_mode(buf + bytes, 0); 08291 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 08292 } 08293 while ((cmd >= 0) && (cmd != 't')) { 08294 if (cmd) 08295 retries = 0; 08296 switch (cmd) { 08297 case '1': /* Record your unavailable message */ 08298 snprintf(prefile,sizeof(prefile), "%s%s/%s/unavail", VM_SPOOL_DIR, vmu->context, vms->username); 08299 cmd = play_record_review(chan,"vm-rec-unv",prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08300 break; 08301 case '2': /* Record your busy message */ 08302 snprintf(prefile,sizeof(prefile), "%s%s/%s/busy", VM_SPOOL_DIR, vmu->context, vms->username); 08303 cmd = play_record_review(chan,"vm-rec-busy",prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08304 break; 08305 case '3': /* Record greeting */ 08306 snprintf(prefile,sizeof(prefile), "%s%s/%s/greet", VM_SPOOL_DIR, vmu->context, vms->username); 08307 cmd = play_record_review(chan,"vm-rec-name",prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08308 break; 08309 case '4': /* manage the temporary greeting */ 08310 cmd = vm_tempgreeting(chan, vmu, vms, fmtc, record_gain); 08311 break; 08312 case '5': /* change password */ 08313 if (vmu->password[0] == '-') { 08314 cmd = ast_play_and_wait(chan, "vm-no"); 08315 break; 08316 } 08317 newpassword[1] = '\0'; 08318 newpassword[0] = cmd = ast_play_and_wait(chan, vm_newpassword); 08319 if (cmd == '#') 08320 newpassword[0] = '\0'; 08321 else { 08322 if (cmd < 0) 08323 break; 08324 if ((cmd = ast_readstring(chan,newpassword + strlen(newpassword),sizeof(newpassword)-1,2000,10000,"#")) < 0) { 08325 break; 08326 } 08327 } 08328 cmd = check_password(vmu, newpassword); /* perform password validation */ 08329 if (cmd != 0) { 08330 ast_log(AST_LOG_NOTICE, "Invalid password for user %s (%s)\n", vms->username, newpassword); 08331 cmd = ast_play_and_wait(chan, vm_invalid_password); 08332 break; 08333 } 08334 newpassword2[1] = '\0'; 08335 newpassword2[0] = cmd = ast_play_and_wait(chan, vm_reenterpassword); 08336 if (cmd == '#') 08337 newpassword2[0] = '\0'; 08338 else { 08339 if (cmd < 0) 08340 break; 08341 08342 if ((cmd = ast_readstring(chan,newpassword2 + strlen(newpassword2),sizeof(newpassword2)-1,2000,10000,"#")) < 0) { 08343 break; 08344 } 08345 } 08346 if (strcmp(newpassword, newpassword2)) { 08347 ast_log(AST_LOG_NOTICE, "Password mismatch for user %s (%s != %s)\n", vms->username, newpassword, newpassword2); 08348 cmd = ast_play_and_wait(chan, vm_mismatch); 08349 break; 08350 } 08351 if (pwdchange & PWDCHANGE_INTERNAL) 08352 vm_change_password(vmu, newpassword); 08353 if ((pwdchange & PWDCHANGE_EXTERNAL) && !ast_strlen_zero(ext_pass_cmd)) 08354 vm_change_password_shell(vmu, newpassword); 08355 08356 ast_debug(1,"User %s set password to %s of length %d\n",vms->username,newpassword,(int)strlen(newpassword)); 08357 cmd = ast_play_and_wait(chan, vm_passchanged); 08358 break; 08359 case '*': 08360 cmd = 't'; 08361 break; 08362 default: 08363 cmd = 0; 08364 snprintf(prefile, sizeof(prefile), "%s%s/%s/temp", VM_SPOOL_DIR, vmu->context, vms->username); 08365 RETRIEVE(prefile, -1, vmu->mailbox, vmu->context); 08366 if (ast_fileexists(prefile, NULL, NULL)) { 08367 cmd = ast_play_and_wait(chan, "vm-tmpexists"); 08368 } 08369 DISPOSE(prefile, -1); 08370 if (!cmd) { 08371 cmd = ast_play_and_wait(chan, "vm-options"); 08372 } 08373 if (!cmd) { 08374 cmd = ast_waitfordigit(chan,6000); 08375 } 08376 if (!cmd) { 08377 retries++; 08378 } 08379 if (retries > 3) { 08380 cmd = 't'; 08381 } 08382 } 08383 } 08384 if (cmd == 't') 08385 cmd = 0; 08386 return cmd; 08387 }
| static int vm_play_folder_name | ( | struct ast_channel * | chan, | |
| char * | mbox | |||
| ) | [static] |
Definition at line 7133 of file app_voicemail.c.
References ast_play_and_wait(), vm_play_folder_name_gr(), vm_play_folder_name_pl(), and vm_play_folder_name_ua().
Referenced by get_folder(), vm_execmain(), vm_instructions_en(), and vm_instructions_zh().
07134 { 07135 int cmd; 07136 07137 if (!strcasecmp(chan->language, "it") || !strcasecmp(chan->language, "es") || !strcasecmp(chan->language, "pt") || !strcasecmp(chan->language, "pt_BR")) { /* Italian, Spanish, French or Portuguese syntax */ 07138 cmd = ast_play_and_wait(chan, "vm-messages"); /* "messages */ 07139 return cmd ? cmd : ast_play_and_wait(chan, box); 07140 } else if (!strcasecmp(chan->language, "gr")){ 07141 return vm_play_folder_name_gr(chan, box); 07142 } else if (!strcasecmp(chan->language, "pl")){ 07143 return vm_play_folder_name_pl(chan, box); 07144 } else if (!strcasecmp(chan->language, "ua")){ /* Ukrainian syntax */ 07145 return vm_play_folder_name_ua(chan, box); 07146 } else { /* Default English */ 07147 cmd = ast_play_and_wait(chan, box); 07148 return cmd ? cmd : ast_play_and_wait(chan, "vm-messages"); /* "messages */ 07149 } 07150 }
| static int vm_play_folder_name_gr | ( | struct ast_channel * | chan, | |
| char * | box | |||
| ) | [static] |
Definition at line 7086 of file app_voicemail.c.
References ast_play_and_wait().
Referenced by vm_play_folder_name().
07087 { 07088 int cmd; 07089 char *buf; 07090 07091 buf = alloca(strlen(box)+2); 07092 strcpy(buf, box); 07093 strcat(buf,"s"); 07094 07095 if (!strcasecmp(box, "vm-INBOX") || !strcasecmp(box, "vm-Old")){ 07096 cmd = ast_play_and_wait(chan, buf); /* "NEA / PALIA" */ 07097 return cmd ? cmd : ast_play_and_wait(chan, "vm-messages"); /* "messages" -> "MYNHMATA" */ 07098 } else { 07099 cmd = ast_play_and_wait(chan, "vm-messages"); /* "messages" -> "MYNHMATA" */ 07100 return cmd ? cmd : ast_play_and_wait(chan, box); /* friends/family/work... -> "FILWN"/"OIKOGENIAS"/"DOULEIAS"*/ 07101 } 07102 }
| static int vm_play_folder_name_pl | ( | struct ast_channel * | chan, | |
| char * | box | |||
| ) | [static] |
Definition at line 7104 of file app_voicemail.c.
References ast_play_and_wait().
Referenced by vm_play_folder_name().
07105 { 07106 int cmd; 07107 07108 if (!strcasecmp(box, "vm-INBOX") || !strcasecmp(box, "vm-Old")) { 07109 if (!strcasecmp(box, "vm-INBOX")) 07110 cmd = ast_play_and_wait(chan, "vm-new-e"); 07111 else 07112 cmd = ast_play_and_wait(chan, "vm-old-e"); 07113 return cmd ? cmd : ast_play_and_wait(chan, "vm-messages"); 07114 } else { 07115 cmd = ast_play_and_wait(chan, "vm-messages"); 07116 return cmd ? cmd : ast_play_and_wait(chan, box); 07117 } 07118 }
| static int vm_play_folder_name_ua | ( | struct ast_channel * | chan, | |
| char * | box | |||
| ) | [static] |
Definition at line 7120 of file app_voicemail.c.
References ast_play_and_wait().
Referenced by vm_play_folder_name().
07121 { 07122 int cmd; 07123 07124 if (!strcasecmp(box, "vm-Family") || !strcasecmp(box, "vm-Friends") || !strcasecmp(box, "vm-Work")){ 07125 cmd = ast_play_and_wait(chan, "vm-messages"); 07126 return cmd ? cmd : ast_play_and_wait(chan, box); 07127 } else { 07128 cmd = ast_play_and_wait(chan, box); 07129 return cmd ? cmd : ast_play_and_wait(chan, "vm-messages"); 07130 } 07131 }
| static int vm_tempgreeting | ( | struct ast_channel * | chan, | |
| struct ast_vm_user * | vmu, | |||
| struct vm_state * | vms, | |||
| char * | fmtc, | |||
| signed char | record_gain | |||
| ) | [static] |
The handler for 'record a temporary greeting'.
| chan | ||
| vmu | ||
| vms | ||
| fmtc | ||
| record_gain | This is option 4 from the mailbox options menu. This function manages the following promptings: 1: play / record / review the temporary greeting. : invokes play_record_review(). 2: remove (delete) the temporary greeting. *: return to the main menu. |
Definition at line 8405 of file app_voicemail.c.
References ADSI_COMM_PAGE, ADSI_JUST_CENT, adsi_logo(), ADSI_MSG_DISPLAY, ast_adsi_available, ast_adsi_display, ast_adsi_set_line, ast_adsi_transmit_message, ast_adsi_voice_mode, ast_fileexists(), ast_play_and_wait(), ast_waitfordigit(), ast_vm_user::context, DELETE, DISPOSE, ast_vm_user::mailbox, play_record_review(), RETRIEVE, and vm_state::username.
Referenced by vm_options().
08406 { 08407 int cmd = 0; 08408 int retries = 0; 08409 int duration = 0; 08410 char prefile[PATH_MAX] = ""; 08411 unsigned char buf[256]; 08412 int bytes = 0; 08413 08414 if (ast_adsi_available(chan)) { 08415 bytes += adsi_logo(buf + bytes); 08416 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 3, ADSI_JUST_CENT, 0, "Temp Greeting Menu", ""); 08417 bytes += ast_adsi_display(buf + bytes, ADSI_COMM_PAGE, 4, ADSI_JUST_CENT, 0, "Not Done", ""); 08418 bytes += ast_adsi_set_line(buf + bytes, ADSI_COMM_PAGE, 1); 08419 bytes += ast_adsi_voice_mode(buf + bytes, 0); 08420 ast_adsi_transmit_message(chan, buf, bytes, ADSI_MSG_DISPLAY); 08421 } 08422 08423 snprintf(prefile, sizeof(prefile), "%s%s/%s/temp", VM_SPOOL_DIR, vmu->context, vms->username); 08424 while ((cmd >= 0) && (cmd != 't')) { 08425 if (cmd) 08426 retries = 0; 08427 RETRIEVE(prefile, -1, vmu->mailbox, vmu->context); 08428 if (ast_fileexists(prefile, NULL, NULL) <= 0) { 08429 play_record_review(chan, "vm-rec-temp", prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08430 cmd = 't'; 08431 } else { 08432 switch (cmd) { 08433 case '1': 08434 cmd = play_record_review(chan, "vm-rec-temp", prefile, maxgreet, fmtc, 0, vmu, &duration, NULL, record_gain, vms, NULL); 08435 break; 08436 case '2': 08437 DELETE(prefile, -1, prefile, vmu); 08438 ast_play_and_wait(chan, "vm-tempremoved"); 08439 cmd = 't'; 08440 break; 08441 case '*': 08442 cmd = 't'; 08443 break; 08444 default: 08445 cmd = ast_play_and_wait(chan, 08446 ast_fileexists(prefile, NULL, NULL) > 0 ? /* XXX always true ? */ 08447 "vm-tempgreeting2" : "vm-tempgreeting"); 08448 if (!cmd) 08449 cmd = ast_waitfordigit(chan,6000); 08450 if (!cmd) 08451 retries++; 08452 if (retries > 3) 08453 cmd = 't'; 08454 } 08455 } 08456 DISPOSE(prefile, -1); 08457 } 08458 if (cmd == 't') 08459 cmd = 0; 08460 return cmd; 08461 }
| static int vmauthenticate | ( | struct ast_channel * | chan, | |
| void * | data | |||
| ) | [static] |
Definition at line 9688 of file app_voicemail.c.
References ast_copy_string(), AST_MAX_EXTENSION, ast_play_and_wait(), ast_strdupa, ast_strlen_zero(), ast_vm_user::context, pbx_builtin_setvar_helper(), s, strsep(), and vm_authenticate().
Referenced by load_module().
09689 { 09690 char *s = data, *user=NULL, *context=NULL, mailbox[AST_MAX_EXTENSION] = ""; 09691 struct ast_vm_user vmus; 09692 char *options = NULL; 09693 int silent = 0, skipuser = 0; 09694 int res = -1; 09695 09696 if (s) { 09697 s = ast_strdupa(s); 09698 user = strsep(&s, ","); 09699 options = strsep(&s, ","); 09700 if (user) { 09701 s = user; 09702 user = strsep(&s, "@"); 09703 context = strsep(&s, ""); 09704 if (!ast_strlen_zero(user)) 09705 skipuser++; 09706 ast_copy_string(mailbox, user, sizeof(mailbox)); 09707 } 09708 } 09709 09710 if (options) { 09711 silent = (strchr(options, 's')) != NULL; 09712 } 09713 09714 if (!vm_authenticate(chan, mailbox, sizeof(mailbox), &vmus, context, NULL, skipuser, 3, silent)) { 09715 pbx_builtin_setvar_helper(chan, "AUTH_MAILBOX", mailbox); 09716 pbx_builtin_setvar_helper(chan, "AUTH_CONTEXT", vmus.context); 09717 ast_play_and_wait(chan, "auth-thankyou"); 09718 res = 0; 09719 } 09720 09721 return res; 09722 }
| static struct ast_tm* vmu_tm | ( | const struct ast_vm_user * | vmu, | |
| struct ast_tm * | tm | |||
| ) | [static, read] |
fill in *tm for current time according to the proper timezone, if any. Return tm so it can be used as a function argument.
Definition at line 3814 of file app_voicemail.c.
References AST_LIST_LOCK, AST_LIST_TRAVERSE, AST_LIST_UNLOCK, ast_localtime(), ast_strlen_zero(), ast_tvnow(), vm_zone::name, vm_zone::timezone, and ast_vm_user::zonetag.
Referenced by make_email_file(), and sendpage().
03815 { 03816 const struct vm_zone *z = NULL; 03817 struct timeval t = ast_tvnow(); 03818 03819 /* Does this user have a timezone specified? */ 03820 if (!ast_strlen_zero(vmu->zonetag)) { 03821 /* Find the zone in the list */ 03822 AST_LIST_LOCK(&zones); 03823 AST_LIST_TRAVERSE(&zones, z, list) { 03824 if (!strcmp(z->name, vmu->zonetag)) 03825 break; 03826 } 03827 AST_LIST_UNLOCK(&zones); 03828 } 03829 ast_localtime(&t, tm, z ? z->timezone : NULL); 03830 return tm; 03831 }
| static int wait_file | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| char * | file | |||
| ) | [static] |
Definition at line 6544 of file app_voicemail.c.
References ast_control_streamfile(), listen_control_forward_key, listen_control_pause_key, listen_control_restart_key, listen_control_reverse_key, and listen_control_stop_key.
Referenced by advanced_options(), and play_message().
06545 { 06546 return ast_control_streamfile(chan, file, listen_control_forward_key, listen_control_reverse_key, listen_control_stop_key, listen_control_pause_key, listen_control_restart_key, skipms, NULL); 06547 }
| static int wait_file2 | ( | struct ast_channel * | chan, | |
| struct vm_state * | vms, | |||
| char * | file | |||
| ) | [static] |
Definition at line 6536 of file app_voicemail.c.
References AST_DIGIT_ANY, ast_log(), AST_LOG_WARNING, and ast_stream_and_wait().
Referenced by play_message(), play_message_callerid(), and play_message_duration().
06537 { 06538 int res; 06539 if ((res = ast_stream_and_wait(chan, file, AST_DIGIT_ANY)) < 0) 06540 ast_log(AST_LOG_WARNING, "Unable to play message %s\n", file); 06541 return res; 06542 }
struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT , .description = "DAHDI Telephony w/PRI & SS7" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "a9c98e5d177805051735cb5b0b16b0a0" , .load = load_module, .unload = unload_module, .reload = reload, } [static] |
Definition at line 11488 of file app_voicemail.c.
char* addesc = "Comedian Mail" [static] |
Definition at line 504 of file app_voicemail.c.
unsigned char adsifdn[4] = "\x00\x00\x00\x0F" [static] |
Definition at line 685 of file app_voicemail.c.
Referenced by adsi_begin(), adsi_load_vmail(), and load_config().
unsigned char adsisec[4] = "\x9B\xDB\xF7\xAC" [static] |
Definition at line 686 of file app_voicemail.c.
Referenced by adsi_load_vmail(), and load_config().
int adsiver = 1 [static] |
Definition at line 687 of file app_voicemail.c.
Referenced by adsi_begin(), adsi_load_vmail(), and load_config().
char* app = "VoiceMail" [static] |
Definition at line 578 of file app_voicemail.c.
char* app2 = "VoiceMailMain" [static] |
Definition at line 581 of file app_voicemail.c.
char* app3 = "MailboxExists" [static] |
Definition at line 583 of file app_voicemail.c.
char* app4 = "VMAuthenticate" [static] |
Definition at line 584 of file app_voicemail.c.
struct ast_module_info* ast_module_info = &__mod_info [static] |
Definition at line 11488 of file app_voicemail.c.
char callcontext[AST_MAX_CONTEXT] = "" [static] |
Definition at line 671 of file app_voicemail.c.
Referenced by load_config(), and populate_defaults().
char charset[32] = "ISO-8859-1" [static] |
Definition at line 683 of file app_voicemail.c.
Referenced by encode_mime_str(), load_config(), make_email_file(), and tds_load_module().
char cidinternalcontexts[MAX_NUM_CID_CONTEXTS][64] [static] |
Definition at line 674 of file app_voicemail.c.
Referenced by load_config(), and play_message_callerid().
struct ast_cli_entry cli_voicemail[] [static] |
{
AST_CLI_DEFINE(handle_voicemail_show_users, "List defined voicemail boxes"),
AST_CLI_DEFINE(handle_voicemail_show_zones, "List zone message formats"),
AST_CLI_DEFINE(handle_voicemail_reload, "Reload voicemail configuration"),
}
Definition at line 9920 of file app_voicemail.c.
Referenced by load_module(), and unload_module().
char* descrip_vm [static] |
Definition at line 508 of file app_voicemail.c.
char* descrip_vm_box_exists [static] |
Definition at line 555 of file app_voicemail.c.
char* descrip_vmain [static] |
Definition at line 537 of file app_voicemail.c.
char* descrip_vmauthenticate [static] |
Definition at line 567 of file app_voicemail.c.
char dialcontext[AST_MAX_CONTEXT] = "" [static] |
Definition at line 670 of file app_voicemail.c.
Referenced by dial_exec_full(), directory_exec(), load_config(), populate_defaults(), ring_entry(), and wait_for_answer().
char* emailbody = NULL [static] |
Definition at line 677 of file app_voicemail.c.
Referenced by load_config(), make_email_file(), and message_template_parse_emailbody().
char emaildateformat[32] = "%A, %B %d, %Y at %r" [static] |
Definition at line 688 of file app_voicemail.c.
Referenced by load_config(), make_email_file(), and prep_email_sub_vars().
char* emailsubject = NULL [static] |
Definition at line 678 of file app_voicemail.c.
Referenced by load_config(), and make_email_file().
char exitcontext[AST_MAX_CONTEXT] = "" [static] |
Definition at line 672 of file app_voicemail.c.
Referenced by common_exec(), conf_run(), load_config(), and populate_defaults().
char ext_pass_check_cmd[128] [static] |
Definition at line 484 of file app_voicemail.c.
char ext_pass_cmd[128] [static] |
Definition at line 483 of file app_voicemail.c.
char externnotify[160] [static] |
Definition at line 595 of file app_voicemail.c.
char fromstring[100] [static] |
Definition at line 681 of file app_voicemail.c.
Referenced by load_config(), make_email_file(), and sendpage().
struct ast_flags globalflags = {0} [static] |
Definition at line 666 of file app_voicemail.c.
Referenced by find_or_create(), find_user(), find_user_realtime(), forward_message(), load_config(), make_email_file(), notify_new_message(), populate_defaults(), sendmail(), and vm_execmain().
char listen_control_forward_key[12] [static] |
Definition at line 652 of file app_voicemail.c.
Referenced by load_config(), and wait_file().
char listen_control_pause_key[12] [static] |
Definition at line 654 of file app_voicemail.c.
Referenced by load_config(), and wait_file().
char listen_control_restart_key[12] [static] |
Definition at line 655 of file app_voicemail.c.
Referenced by load_config(), and wait_file().
char listen_control_reverse_key[12] [static] |
Definition at line 653 of file app_voicemail.c.
Referenced by load_config(), and wait_file().
char listen_control_stop_key[12] [static] |
Definition at line 656 of file app_voicemail.c.
Referenced by load_config(), and wait_file().
struct ast_custom_function mailbox_exists_acf [static] |
Definition at line 9678 of file app_voicemail.c.
Referenced by load_module(), and unload_module().
char mailcmd[160] [static] |
Definition at line 594 of file app_voicemail.c.
int maxdeletedmsg [static] |
Definition at line 591 of file app_voicemail.c.
int maxgreet [static] |
Definition at line 601 of file app_voicemail.c.
int maxlogins [static] |
Definition at line 603 of file app_voicemail.c.
int maxmsg [static] |
Definition at line 590 of file app_voicemail.c.
int maxsilence [static] |
Definition at line 589 of file app_voicemail.c.
Referenced by ast_record_review().
int minpassword [static] |
Definition at line 604 of file app_voicemail.c.
struct ast_event_sub* mwi_sub_sub [static] |
Subscription to ... MWI event subscriptions
Definition at line 621 of file app_voicemail.c.
struct ast_taskprocessor* mwi_subscription_tps [static] |
Definition at line 647 of file app_voicemail.c.
Referenced by load_module(), mwi_sub_event_cb(), mwi_unsub_event_cb(), and unload_module().
struct ast_event_sub* mwi_unsub_sub [static] |
Subscription to ... MWI event un-subscriptions
Definition at line 623 of file app_voicemail.c.
int my_umask [static] |
Definition at line 486 of file app_voicemail.c.
char* pagerbody = NULL [static] |
Definition at line 679 of file app_voicemail.c.
Referenced by load_config(), and sendpage().
char pagerfromstring[100] [static] |
Definition at line 682 of file app_voicemail.c.
Referenced by load_config(), and sendpage().
char* pagersubject = NULL [static] |
Definition at line 680 of file app_voicemail.c.
Referenced by load_config(), and sendpage().
ast_cond_t poll_cond = PTHREAD_COND_INITIALIZER [static] |
Definition at line 616 of file app_voicemail.c.
unsigned int poll_freq [static] |
Polling frequency
Definition at line 611 of file app_voicemail.c.
ast_mutex_t poll_lock = ((ast_mutex_t) PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP ) [static] |
Definition at line 615 of file app_voicemail.c.
Referenced by mb_poll_thread(), and stop_poll_thread().
unsigned int poll_mailboxes [static] |
Poll mailboxes for changes since there is something external to app_voicemail that may change them.
Definition at line 608 of file app_voicemail.c.
pthread_t poll_thread = AST_PTHREADT_NULL [static] |
Definition at line 617 of file app_voicemail.c.
unsigned char poll_thread_run [static] |
Definition at line 618 of file app_voicemail.c.
int pwdchange = PWDCHANGE_INTERNAL [static] |
Definition at line 490 of file app_voicemail.c.
int saydurationminfo [static] |
Definition at line 668 of file app_voicemail.c.
Referenced by load_config(), and populate_defaults().
char serveremail[80] [static] |
Definition at line 593 of file app_voicemail.c.
int silencethreshold = 128 [static] |
Definition at line 592 of file app_voicemail.c.
int skipms [static] |
Definition at line 602 of file app_voicemail.c.
Referenced by controlplayback_exec(), and handle_controlstreamfile().
struct ast_smdi_interface* smdi_iface = NULL [static] |
Definition at line 596 of file app_voicemail.c.
char* synopsis_vm = "Leave a Voicemail message" [static] |
Definition at line 506 of file app_voicemail.c.
char* synopsis_vm_box_exists [static] |
"Check to see if Voicemail mailbox exists"
Definition at line 552 of file app_voicemail.c.
char* synopsis_vmain = "Check Voicemail messages" [static] |
Definition at line 535 of file app_voicemail.c.
char* synopsis_vmauthenticate = "Authenticate with Voicemail passwords" [static] |
Definition at line 565 of file app_voicemail.c.
char userscontext[AST_MAX_EXTENSION] = "default" [static] |
Definition at line 502 of file app_voicemail.c.
struct ast_app_option vm_app_options[128] = { [ 's' ] = { .flag = OPT_SILENT }, [ 'b' ] = { .flag = OPT_BUSY_GREETING }, [ 'u' ] = { .flag = OPT_UNAVAIL_GREETING }, [ 'g' ] = { .flag = OPT_RECORDGAIN , .arg_index = OPT_ARG_RECORDGAIN + 1 }, [ 'd' ] = { .flag = OPT_DTMFEXIT , .arg_index = OPT_ARG_DTMFEXIT + 1 }, [ 'p' ] = { .flag = OPT_PREPEND_MAILBOX }, [ 'a' ] = { .flag = OPT_AUTOPLAY , .arg_index = OPT_ARG_PLAYFOLDER + 1 }, [ 'U' ] = { .flag = OPT_MESSAGE_Urgent }, [ 'P' ] = { .flag = OPT_MESSAGE_PRIORITY }} [static] |
Definition at line 281 of file app_voicemail.c.
Referenced by vm_exec(), and vm_execmain().
| enum { ... } vm_box |
char vm_invalid_password[80] = "vm-invalid-password" [static] |
Definition at line 664 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
char vm_mismatch[80] = "vm-mismatch" [static] |
Definition at line 663 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
char vm_newpassword[80] = "vm-newpassword" [static] |
Definition at line 660 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
| enum { ... } vm_option_args |
| enum { ... } vm_option_flags |
char vm_passchanged[80] = "vm-passchanged" [static] |
Definition at line 661 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
char vm_password[80] = "vm-password" [static] |
Definition at line 659 of file app_voicemail.c.
Referenced by load_config(), and vm_authenticate().
char vm_reenterpassword[80] = "vm-reenterpassword" [static] |
Definition at line 662 of file app_voicemail.c.
Referenced by load_config(), vm_newuser(), and vm_options().
char VM_SPOOL_DIR[PATH_MAX] [static] |
Definition at line 481 of file app_voicemail.c.
char vmfmts[80] [static] |
Definition at line 597 of file app_voicemail.c.
int vmmaxsecs [static] |
Definition at line 600 of file app_voicemail.c.
int vmminsecs [static] |
Definition at line 599 of file app_voicemail.c.
double volgain [static] |
Definition at line 598 of file app_voicemail.c.
char zonetag[80] [static] |
Definition at line 588 of file app_voicemail.c.
Referenced by build_peer().
1.6.1