150 #include <sys/time.h> 151 #include <sys/stat.h> 152 #include <sys/mman.h> 525 #define MVM_REVIEW (1 << 0) 526 #define MVM_OPERATOR (1 << 1) 527 #define MVM_REALTIME (1 << 2) 528 #define MVM_SVMAIL (1 << 3) 529 #define MVM_ENVELOPE (1 << 4) 530 #define MVM_PBXSKIP (1 << 9) 531 #define MVM_ALLOCED (1 << 13) 535 #define SENDMAIL "/usr/sbin/sendmail -t" 537 #define SOUND_INTRO "vm-intro" 538 #define B64_BASEMAXINLINE 256 539 #define B64_BASELINELEN 72 542 #define MAX_DATETIME_FORMAT 512 543 #define MAX_NUM_CID_CONTEXTS 10 545 #define ERROR_LOCK_PATH -100 546 #define VOICEMAIL_DIR_MODE 0700 548 #define VOICEMAIL_CONFIG "minivm.conf" 549 #define ASTERISK_USERNAME "asterisk" 636 char fromaddress[100];
668 char msg_format[BUFSIZ];
681 struct timeval reset;
683 struct timeval lastreceived;
711 #define DEFAULT_DATEFORMAT "%A, %B %d, %Y at %r" 712 #define DEFAULT_CHARSET "ISO-8859-1" 735 ast_copy_string(template->subject,
"New message in mailbox ${MVM_USERNAME}@${MVM_DOMAIN}",
sizeof(template->subject));
736 template->attachment =
TRUE;
760 ast_log(
LOG_ERROR,
"Out of memory, can't allocate message template object %s.\n", name);
765 ast_debug(3,
"Configuring template option %s = \"%s\" for template %s\n", var->
name, var->
value, name);
766 if (!strcasecmp(var->
name,
"fromaddress")) {
768 }
else if (!strcasecmp(var->
name,
"fromemail")) {
770 }
else if (!strcasecmp(var->
name,
"subject")) {
772 }
else if (!strcasecmp(var->
name,
"locale")) {
774 }
else if (!strcasecmp(var->
name,
"attachmedia")) {
776 }
else if (!strcasecmp(var->
name,
"dateformat")) {
778 }
else if (!strcasecmp(var->
name,
"charset")) {
780 }
else if (!strcasecmp(var->
name,
"templatefile")) {
784 if (!template->body) {
788 }
else if (!strcasecmp(var->
name,
"messagebody")) {
792 if (!template->body) {
803 ast_log(
LOG_ERROR,
"-- %d errors found parsing message template definition %s\n", error, name);
825 if (!strcasecmp(this->name, name)) {
889 if (fputs(
EOL,so) == EOF)
895 if (putc(((
unsigned char) c), so) == EOF)
912 memset(&bio, 0,
sizeof(bio));
915 if (!(fi = fopen(filename,
"rb"))) {
920 for (i= 0; i<9; i++) {
924 dtable[26+i+9]=
'j'+i;
926 for (i= 0; i < 8; i++) {
928 dtable[26+i+18]=
's'+i;
930 for (i= 0; i < 10; i++) {
937 unsigned char igroup[3], ogroup[4];
940 igroup[0]= igroup[1]= igroup[2]= 0;
942 for (n= 0; n < 3; n++) {
947 igroup[n]= (
unsigned char)c;
951 ogroup[0]= dtable[igroup[0]>>2];
952 ogroup[1]= dtable[((igroup[0]&3)<<4) | (igroup[1]>>4)];
953 ogroup[2]= dtable[((igroup[1]&0xF)<<2) | (igroup[2]>>6)];
954 ogroup[3]= dtable[igroup[2]&0x3F];
969 if (fputs(
EOL, so) == EOF)
1076 ast_debug(3,
"Looking for voicemail user %s in domain %s\n", username, domain);
1081 if (!strcasecmp(domain, cur->domain) && !strcasecmp(username, cur->username))
1087 ast_debug(3,
"Found account for %s@%s\n", username, domain);
1093 if (createtemp && !vmu) {
1100 ast_debug(1,
"Created temporary account\n");
1132 snprintf(name,
sizeof(name),
"%s@%s", username, domain);
1146 for (; *
str; str++) {
1147 if (*str > 126 || *str < 32 || strchr(
"()<>@,:;/\"[]?.=", *str)) {
1176 int first_section = 1;
1180 for (; *start; start++) {
1181 int need_encoding = 0;
1182 if (*start < 33 || *start > 126 || strchr(
"()<>@,:;/\"[]?.=_", *start)) {
1185 if ((first_section && need_encoding && preamble +
ast_str_strlen(tmp) > 70) ||
1186 (first_section && !need_encoding && preamble +
ast_str_strlen(tmp) > 72) ||
1188 (!first_section && !need_encoding &&
ast_str_strlen(tmp) > 72)) {
1194 if (need_encoding && *start ==
' ') {
1196 }
else if (need_encoding) {
1220 for (ptr = from; *ptr; ptr++) {
1221 if (*ptr ==
'"' || *ptr ==
'\\') {
1240 char email[256] =
"";
1246 char tmp[80] =
"/tmp/astmail-XXXXXX";
1248 char sox_gain_tmpdir[
PATH_MAX] =
"";
1249 char *file_to_delete =
NULL, *dir_to_delete =
NULL;
1258 if (!str1 || !str2) {
1266 snprintf(email,
sizeof(email),
"%s@%s", vmu->
username, vmu->
domain);
1278 if (!strcmp(format,
"wav49"))
1285 ast_copy_string(sox_gain_tmpdir,
"/tmp/minivm-gain-XXXXXX",
sizeof(sox_gain_tmpdir));
1286 ast_debug(3,
"sox_gain_tmpdir: %s\n", sox_gain_tmpdir);
1287 if (!
mkdtemp(sox_gain_tmpdir)) {
1291 snprintf(fname,
sizeof(fname),
"%s/output.%s", sox_gain_tmpdir, format);
1292 snprintf(sox_gain_cmd,
sizeof(sox_gain_cmd),
"sox -v %.4f %s.%s %s", vmu->
volgain, filename, format, fname);
1294 ast_debug(3,
"VOLGAIN: Stored at: %s.%s - Level: %.4f - Mailbox: %s\n", filename, format, vmu->
volgain, vmu->
username);
1297 file_to_delete = fname;
1298 dir_to_delete = sox_gain_tmpdir;
1300 snprintf(fname,
sizeof(fname),
"%s.%s", filename, format);
1303 if (template->attachment)
1304 ast_debug(1,
"Attaching file '%s', format '%s', uservm is '%d'\n", fname, format, attach_user_voicemail);
1310 p = fdopen(pfd,
"w");
1315 ast_debug(1,
"Opening temp file for e-mail: %s\n", tmp);
1327 snprintf(dur,
sizeof(dur),
"%d:%02d", duration / 60, duration % 60);
1344 ast_strftime(date,
sizeof(date),
"%a, %d %b %Y %H:%M:%S %z", &tm);
1347 fprintf(p,
"Date: %s\n", date);
1350 ast_strftime(date,
sizeof(date), template->dateformat, &tm);
1360 fromaddress =
ast_strlen_zero(template->fromaddress) ?
"" :
template->fromaddress;
1364 fromemail =
"asterisk";
1366 if (strchr(fromemail,
'@'))
1370 gethostname(host,
sizeof(host)-1);
1371 snprintf(who,
sizeof(who),
"%s@%s", fromemail, host);
1375 fprintf(p,
"From: Asterisk PBX <%s>\n", who);
1377 ast_debug(4,
"Fromaddress template: %s\n", fromaddress);
1385 fprintf(p,
"%s %s\n", first_line ?
"From:" :
"",
ast_str_buffer(str2));
1390 fprintf(p,
"%s %s <%s>\n", first_line ?
"From:" :
"",
ast_str_buffer(str2), who);
1396 fprintf(p,
"Message-ID: <Asterisk-%u-%s-%d-%s>\n", (
unsigned int)
ast_random(), vmu->
username, (
int)getpid(), who);
1399 snprintf(email,
sizeof(email),
"%s@%s", vmu->
username, vmu->
domain);
1410 fprintf(p,
"%s %s\n", first_line ?
"To:" :
"",
ast_str_buffer(str2));
1415 fprintf(p,
"%s %s <%s>\n", first_line ?
"To:" :
"",
ast_str_buffer(str2), email);
1428 fprintf(p,
"%s %s\n", first_line ?
"Subject:" :
"",
ast_str_buffer(str2));
1433 fprintf(p,
"%s %s\n", first_line ?
"Subject:" :
"",
ast_str_buffer(str2));
1438 fprintf(p,
"Subject: New message in mailbox %s@%s\n", vmu->
username, vmu->
domain);
1439 ast_debug(1,
"Using default subject for this email \n");
1443 fprintf(p,
"X-Asterisk-debug: template %s user account %s@%s\n", template->name, vmu->
username, vmu->
domain);
1444 fprintf(p,
"MIME-Version: 1.0\n");
1447 snprintf(bound,
sizeof(bound),
"voicemail_%s%d%u", vmu->
username, (
int)getpid(), (
unsigned int)
ast_random());
1449 fprintf(p,
"Content-Type: multipart/mixed; boundary=\"%s\"\n\n\n", bound);
1451 fprintf(p,
"--%s\n", bound);
1452 fprintf(p,
"Content-Type: text/plain; charset=%s\nContent-Transfer-Encoding: 8bit\n\n", template->charset);
1458 fprintf(p,
"Dear %s:\n\n\tJust wanted to let you know you were just left a %s long message \n" 1459 "in mailbox %s from %s, on %s so you might\n" 1460 "want to check it when you get a chance. Thanks!\n\n\t\t\t\t--Asterisk\n\n", vmu->
fullname,
1461 dur, vmu->
username, (cidname ? cidname : (cidnum ? cidnum :
"an unknown caller")), date);
1462 ast_debug(3,
"Using default message body (no template)\n-----\n");
1465 if (template->attachment) {
1466 char *ctype =
"audio/x-";
1467 ast_debug(3,
"Attaching file to message: %s\n", fname);
1468 if (!strcasecmp(format,
"ogg"))
1469 ctype =
"application/";
1471 fprintf(p,
"--%s\n", bound);
1472 fprintf(p,
"Content-Type: %s%s; name=\"voicemailmsg.%s\"\n", ctype, format, format);
1473 fprintf(p,
"Content-Transfer-Encoding: base64\n");
1474 fprintf(p,
"Content-Description: Voicemail sound attachment.\n");
1475 fprintf(p,
"Content-Disposition: attachment; filename=\"voicemail%s.%s\"\n\n", counter ? counter :
"", format);
1478 fprintf(p,
"\n\n--%s--\n.\n", bound);
1484 if (file_to_delete && dir_to_delete) {
1487 res = snprintf(mail_cmd_buffer,
sizeof(mail_cmd_buffer),
1488 "( %s < %s ; rm -f %s %s ; rmdir %s ) &",
1489 global_mailcmd, tmp, tmp, file_to_delete, dir_to_delete);
1491 res = snprintf(mail_cmd_buffer,
sizeof(mail_cmd_buffer),
1492 "( %s < %s ; rm -f %s ) &",
1493 global_mailcmd, tmp, tmp);
1496 if (res <
sizeof(mail_cmd_buffer)) {
1497 file_to_delete = dir_to_delete =
NULL;
1505 ast_debug(1,
"Sent message to %s with command '%s'%s\n", vmu->
email, global_mailcmd, template->attachment ?
" - (media attachment)" :
"");
1506 ast_debug(3,
"Actual command used: %s\n", mail_cmd_buffer);
1511 if (file_to_delete) {
1512 unlink(file_to_delete);
1515 if (dir_to_delete) {
1516 rmdir(dir_to_delete);
1540 struct stat filestat;
1541 make_dir(dest, len, domain, username, folder ? folder :
"");
1542 if (stat(dest, &filestat)== -1)
1560 make_dir(dest, len, domain, username, folder);
1565 ast_debug(2,
"Creating directory for %s@%s folder %s : %s\n", username, domain, folder, dest);
1578 ast_debug(2,
"Still preparing to play message ...\n");
1580 snprintf(fn,
sizeof(fn),
"%s%s/%s/greet",
MVM_SPOOL_DIR, domain, username);
1590 int numericusername = 1;
1593 ast_debug(2,
"No personal prompts. Using default prompt set for language\n");
1596 ast_debug(2,
"Numeric? Checking %c\n", *i);
1598 numericusername =
FALSE;
1604 if (numericusername) {
1634 ast_debug(1,
"Deleting voicemail file %s\n", file);
1645 int outsidecaller,
struct minivm_account *vmu,
int *duration,
int *sound_duration,
const char *unlockdir,
1646 signed char record_gain)
1649 int max_attempts = 3;
1652 int message_exists = 0;
1653 signed char zero_gain = 0;
1654 char *acceptdtmf =
"#";
1655 char *canceldtmf =
"";
1660 if (duration ==
NULL) {
1667 while ((cmd >= 0) && (cmd !=
't')) {
1670 ast_verb(3,
"Saving message as is\n");
1676 ast_verb(3,
"Reviewing the message\n");
1684 ast_verb(3,
"Re-recording the message\n");
1686 ast_verb(3,
"Recording the message\n");
1687 if (recorded && outsidecaller)
1695 cmd =
ast_play_and_record_full(chan, playfile, recordfile, maxtime, fmt, duration, sound_duration, 0, global_silencethreshold, global_maxsilence, unlockdir, acceptdtmf, canceldtmf, 0,
AST_RECORD_IF_EXISTS_OVERWRITE);
1702 else if (cmd ==
'*')
1725 if (message_exists || recorded) {
1745 if (message_exists) {
1763 if (attempts > max_attempts) {
1779 char *argv[5] = {
NULL };
1788 snprintf(fquser,
sizeof(fquser),
"%s@%s", vmu->
username, vmu->
domain);
1793 argv[idx++] = fquser;
1804 ast_debug(1,
"Executing: %s %s %s %s\n",
1805 argv[0], argv[1], argv[2] ?:
"", argv[3] ?:
"");
1818 char *messageformat;
1820 char oldlocale[100];
1821 const char *counter;
1844 ast_debug(2,
"Changing locale from %s to %s\n", oldlocale, etemplate->
locale);
1845 new_locale = setlocale(LC_TIME, etemplate->
locale);
1846 if (new_locale ==
NULL) {
1861 ast_debug(2,
"MVM_COUNTER not found\n");
1863 ast_debug(2,
"MVM_COUNTER found - will use it with value %s\n", counter);
1875 ast_copy_string(oldlocale, setlocale(LC_TIME,
""),
sizeof(oldlocale));
1876 setlocale(LC_TIME, etemplate->
locale);
1884 goto notify_cleanup;
1889 "Event",
"MiniVoiceMail",
1890 "Action",
"SentNotification",
1891 "Counter", counter ?:
"");
1893 goto notify_cleanup;
1897 goto notify_cleanup;
1904 setlocale(LC_TIME, oldlocale);
1917 int res = 0, txtdes;
1919 int sound_duration = 0;
1922 char ext_context[256] =
"";
1931 domain = strchr(tmp,
'@');
1939 ast_log(
LOG_ERROR,
"Can't allocate temporary account for '%s@%s'\n", username, domain);
1945 if (strcmp(vmu->
domain,
"localhost"))
1946 snprintf(ext_context,
sizeof(ext_context),
"%s@%s", username, vmu->
domain);
1957 ast_log(
LOG_WARNING,
"No format for saving voicemail? Default %s\n", default_vmformat);
1966 create_dirpath(tmpdir,
sizeof(tmpdir),
"0000_minivm_temp",
"mediafiles",
"");
1967 ast_debug(3,
"Creating temporary directory %s\n", tmpdir);
1971 snprintf(tmptxtfile,
sizeof(tmptxtfile),
"%s/XXXXXX", tmpdir);
1974 txtdes = mkstemp(tmptxtfile);
1993 ast_debug(2,
"Open file for metadata: %s\n", tmptxtfile);
1995 res =
play_record_review(chan,
NULL, tmptxtfile, global_vmmaxmessage, fmt, 1, vmu, &duration, &sound_duration,
NULL, options->
record_gain);
1997 txt = fdopen(txtdes,
"w+");
2004 char logbuf[BUFSIZ];
2007 ast_strftime(timebuf,
sizeof(timebuf),
"%H:%M:%S", &tm);
2013 snprintf(logbuf,
sizeof(logbuf),
2015 "%s:%s:%s:%s:%d:%s:%s:%s:%s:%d:%s:%s\n",
2026 duration < global_vmminmessage ?
"IGNORED" :
"OK",
2029 fprintf(txt,
"%s", logbuf);
2030 if (minivmlogfile) {
2032 fprintf(minivmlogfile,
"%s", logbuf);
2036 if (sound_duration < global_vmminmessage) {
2037 ast_verb(3,
"Recording was %d seconds long but needs to be at least %d - abandoning\n", sound_duration, global_vmminmessage);
2046 ast_debug(1,
"The recorded media file is gone, so we should remove the .txt file too!\n");
2056 snprintf(timebuf,
sizeof(timebuf),
"%d", duration);
2068 ast_debug(2,
"-_-_- Deleted audio file after notification :: %s \n", tmptxtfile);
2084 static void queue_mwi_event(
const char *channel_id,
const char *mbx,
const char *ctx,
int urgent,
int new,
int old)
2091 context =
"default";
2120 domain = strchr(tmp,
'@');
2126 ast_log(
LOG_ERROR,
"Need mailbox@context as argument. Sorry. Argument 0 %s\n", argv[0]);
2147 const char *
template =
"";
2148 const char *filename;
2150 const char *duration_string;
2163 domain = strchr(tmp,
'@');
2169 ast_log(
LOG_ERROR,
"Need username@domain as argument. Sorry. Argument 0 %s\n", argv[0]);
2175 ast_log(
LOG_WARNING,
"Could not allocate temporary memory for '%s@%s'\n", username, domain);
2225 memset(&leave_options, 0,
sizeof(leave_options));
2246 ast_log(
LOG_WARNING,
"Invalid value '%s' provided for record gain option\n", opts[OPT_ARG_RECORDGAIN]);
2257 ast_log(
LOG_ERROR,
"Could not leave voicemail. The path is already locked.\n");
2283 char ext_context[256] =
"";
2285 char ecodes[16] =
"#";
2305 domain = strchr(tmp,
'@');
2311 ast_log(
LOG_ERROR,
"Need username@domain as argument. Sorry. Argument: %s\n", argv[0]);
2314 ast_debug(1,
"Trying to find configuration for user %s in domain %s\n", username, domain);
2326 if (strcmp(vmu->
domain,
"localhost"))
2327 snprintf(ext_context,
sizeof(ext_context),
"%s@%s", username, vmu->
domain);
2338 snprintf(prefile,
sizeof(prefile),
"%s%s/%s/unavail",
MVM_SPOOL_DIR, vmu->
domain, username);
2341 snprintf(tempfile,
sizeof(tempfile),
"%s%s/%s/temp",
MVM_SPOOL_DIR, vmu->
domain, username);
2343 ast_debug(2,
"Temporary message directory does not exist, using default (%s)\n", tempfile);
2346 ast_debug(2,
"Preparing to play message ...\n");
2353 strncat(ecodes,
"0",
sizeof(ecodes) - strlen(ecodes) - 1);
2358 strncat(ecodes,
"0",
sizeof(ecodes) - strlen(ecodes) - 1);
2364 strncat(ecodes,
"0",
sizeof(ecodes) - strlen(ecodes) - 1);
2372 strncat(ecodes,
"*",
sizeof(ecodes) - strlen(ecodes) - 1);
2376 strncat(ecodes,
"*",
sizeof(ecodes) - strlen(ecodes) - 1);
2380 strncat(ecodes,
"*",
sizeof(ecodes) - strlen(ecodes) - 1);
2390 ast_debug(2,
"%s doesn't exist, doing what we can\n", prefile);
2394 ast_debug(2,
"Hang up during prefile playback\n");
2428 }
else if (res ==
'0') {
2429 if(ouseexten || ousemacro) {
2441 }
else if (res < 0) {
2461 char filename[BUFSIZ];
2472 ast_log(
LOG_ERROR,
"No filename given in application arguments or channel variable MVM_FILENAME\n");
2481 ast_debug(2,
"Can't delete file: %s\n", filename);
2484 ast_debug(2,
"Deleted voicemail file :: %s \n", filename);
2488 ast_debug(2,
"Filename does not exist: %s\n", filename);
2503 char *tmpptr =
NULL;
2514 ast_log(
LOG_ERROR,
"MinivmAccmess needs at least two arguments: account and option\n");
2522 ast_log(
LOG_ERROR,
"MinivmAccmess needs at least two arguments: account and option\n");
2525 if (!error && strlen(argv[1]) > 1) {
2526 ast_log(
LOG_ERROR,
"MinivmAccmess can only handle one option at a time. Bad option string: %s\n", argv[1]);
2542 domain = strchr(tmp,
'@');
2548 ast_log(
LOG_ERROR,
"Need username@domain as argument. Sorry. Argument 0 %s\n", argv[0]);
2555 ast_log(
LOG_WARNING,
"Could not allocate temporary memory for '%s@%s'\n", username, domain);
2567 prompt =
"vm-rec-busy";
2569 message =
"unavailable";
2570 prompt =
"vm-rec-unv";
2573 prompt =
"vm-rec-temp";
2576 prompt =
"vm-rec-name";
2580 play_record_review(chan, prompt, filename, global_maxgreet, default_vmformat, 0, vmu, &duration,
NULL,
NULL,
FALSE);
2582 ast_debug(1,
"Recorded new %s message in %s (duration %d)\n", message, filename, duration);
2599 char accbuf[BUFSIZ];
2601 ast_debug(3,
"Creating %s account for [%s]\n", realtime ?
"realtime" :
"static", name);
2605 domain = strchr(accbuf,
'@');
2611 ast_log(
LOG_ERROR,
"No domain given for mini-voicemail account %s. Not configured.\n", name);
2615 ast_debug(3,
"Creating static account for user %s domain %s\n", username, domain);
2627 ast_debug(3,
"...Configuring account %s\n", name);
2630 ast_debug(3,
"Configuring %s = \"%s\" for account %s\n", var->
name, var->
value, name);
2631 if (!strcasecmp(var->
name,
"serveremail")) {
2633 }
else if (!strcasecmp(var->
name,
"email")) {
2635 }
else if (!strcasecmp(var->
name,
"accountcode")) {
2637 }
else if (!strcasecmp(var->
name,
"pincode")) {
2639 }
else if (!strcasecmp(var->
name,
"domain")) {
2641 }
else if (!strcasecmp(var->
name,
"language")) {
2643 }
else if (!strcasecmp(var->
name,
"timezone")) {
2645 }
else if (!strcasecmp(var->
name,
"externnotify")) {
2647 }
else if (!strcasecmp(var->
name,
"etemplate")) {
2649 }
else if (!strcasecmp(var->
name,
"ptemplate")) {
2651 }
else if (!strcasecmp(var->
name,
"fullname")) {
2653 }
else if (!strcasecmp(var->
name,
"setvar")) {
2655 char varname[strlen(var->
value) + 1];
2658 strcpy(varname, var->
value);
2659 if ((varval = strchr(varname,
'='))) {
2667 }
else if (!strcasecmp(var->
name,
"pager")) {
2669 }
else if (!strcasecmp(var->
name,
"volgain")) {
2672 ast_log(
LOG_ERROR,
"Unknown configuration option for minivm account %s : %s\n", name, var->
name);
2676 ast_debug(3,
"...Linking account %s\n", name);
2713 if (newzone ==
NULL)
2718 timezone_str =
strsep(&msg_format,
"|");
2740 char buf[BUFSIZ * 6];
2741 char readbuf[BUFSIZ];
2742 char filenamebuf[BUFSIZ];
2750 if (*filename ==
'/')
2755 if (!(fi = fopen(filenamebuf,
"r"))) {
2756 ast_log(
LOG_ERROR,
"Can't read message template from file: %s\n", filenamebuf);
2760 while (fgets(readbuf,
sizeof(readbuf), fi)) {
2762 if (writepos != buf) {
2767 writepos += strlen(readbuf) - 1;
2770 messagebody =
ast_calloc(1, strlen(buf + 1));
2772 ast_debug(4,
"---> Size of allocation %d\n", (
int) strlen(buf + 1) );
2773 ast_debug(4,
"---> Done reading message template : \n%s\n---- END message template--- \n", messagebody);
2781 char *tmpread, *tmpwrite;
2786 while ((tmpwrite = strchr(tmpread,
'\\'))) {
2787 int len = strlen(
"\n");
2788 switch (tmpwrite[1]) {
2790 memmove(tmpwrite + len, tmpwrite + 2, strlen(tmpwrite + 2) + 1);
2794 memmove(tmpwrite + len, tmpwrite + 2, strlen(tmpwrite + 2) + 1);
2798 ast_log(
LOG_NOTICE,
"Substitution routine does not support this character: %c\n", tmpwrite[1]);
2800 tmpread = tmpwrite +
len;
2812 if (!strcmp(var->
name,
"mailcmd")) {
2814 }
else if (!strcmp(var->
name,
"maxgreet")) {
2815 global_maxgreet = atoi(var->
value);
2816 }
else if (!strcmp(var->
name,
"maxsilence")) {
2817 global_maxsilence = atoi(var->
value);
2818 if (global_maxsilence > 0)
2819 global_maxsilence *= 1000;
2820 }
else if (!strcmp(var->
name,
"logfile")) {
2822 if(*(var->
value) ==
'/')
2827 }
else if (!strcmp(var->
name,
"externnotify")) {
2830 }
else if (!strcmp(var->
name,
"silencetreshold")) {
2832 global_silencethreshold = atoi(var->
value);
2833 }
else if (!strcmp(var->
name,
"maxmessage")) {
2835 if (sscanf(var->
value,
"%30d", &x) == 1) {
2836 global_vmmaxmessage = x;
2841 }
else if (!strcmp(var->
name,
"minmessage")) {
2843 if (sscanf(var->
value,
"%30d", &x) == 1) {
2844 global_vmminmessage = x;
2845 if (global_maxsilence <= global_vmminmessage)
2846 ast_log(
LOG_WARNING,
"maxsilence should be less than minmessage or you may get empty messages\n");
2851 }
else if (!strcmp(var->
name,
"format")) {
2853 }
else if (!strcmp(var->
name,
"review")) {
2855 }
else if (!strcmp(var->
name,
"operator")) {
2888 ast_debug(2,
"Destroyed memory objects...\n");
2891 global_externnotify[0] =
'\0';
2892 global_logfile[0] =
'\0';
2893 global_vmmaxmessage = 2000;
2894 global_maxgreet = 2000;
2895 global_vmminmessage = 0;
2897 global_maxsilence = 0;
2898 global_saydurationminfo = 2;
2910 ast_log(
LOG_WARNING,
"Failed to load configuration file. Module activated with default settings.\n");
2915 ast_debug(2,
"Loaded configuration file, now parsing\n");
2921 ast_debug(3,
"Found configuration section [%s]\n", cat);
2922 if (!strcasecmp(cat,
"general")) {
2925 }
else if (!strncasecmp(cat,
"template-", 9)) {
2927 char *
name = cat + 9;
2933 if (!strcasecmp(cat,
"zonemessages")) {
2954 ast_copy_string(template->dateformat, chanvar,
sizeof(template->dateformat));
2956 ast_copy_string(template->fromaddress, chanvar,
sizeof(template->fromaddress));
2958 ast_copy_string(template->serveremail, chanvar,
sizeof(template->serveremail));
2960 ast_copy_string(template->charset, chanvar,
sizeof(template->charset));
2962 ast_copy_string(template->subject, chanvar,
sizeof(template->subject));
2965 template->attachment =
TRUE;
2970 ast_copy_string(template->fromaddress, chanvar,
sizeof(template->fromaddress));
2972 ast_copy_string(template->serveremail, chanvar,
sizeof(template->serveremail));
2974 ast_copy_string(template->charset, chanvar,
sizeof(template->charset));
2976 ast_copy_string(template->subject, chanvar,
sizeof(template->subject));
2979 template->attachment =
FALSE;
2982 ast_log(
LOG_ERROR,
"--- A total of %d errors found in mini-voicemail configuration\n", error);
2989 fclose(minivmlogfile);
2993 minivmlogfile = fopen(global_logfile,
"a");
2997 ast_debug(3,
"Opened log file %s \n", global_logfile);
3007 #define HVLT_OUTPUT_FORMAT "%-15s %-10s %-10s %-15.15s %-50s\n" 3012 e->
command =
"minivm list templates";
3014 "Usage: minivm list templates\n" 3015 " Lists message templates for e-mail, paging and IM\n";
3026 ast_cli(a->
fd,
"There are no message templates defined\n");
3036 this->attachment ?
"Yes" :
"No",
3037 S_OR(this->subject,
"-"));
3041 ast_cli(a->
fd,
"\n * Total: %d minivoicemail message templates\n", count);
3055 wordlen = strlen(word);
3057 if (!strncasecmp(word, vmu->
domain, wordlen)) {
3058 if (domain && strcmp(domain, vmu->
domain) && ++which > state)
3071 #define HMSU_OUTPUT_FORMAT "%-23s %-15s %-15s %-10s %-10s %-50s\n" 3076 e->
command =
"minivm list accounts [for]";
3078 "Usage: minivm list accounts [for <domain>]\n" 3079 " Lists all mailboxes currently set up\n";
3087 if ((a->
argc == 5) && strcmp(a->
argv[3],
"for"))
3092 ast_cli(a->
fd,
"There are no voicemail users currently defined\n");
3111 ast_cli(a->
fd,
"\n * Total: %d minivoicemail accounts\n", count);
3119 #define HMSZ_OUTPUT_FORMAT "%-15s %-20s %-45s\n" 3124 e->
command =
"minivm list zones";
3126 "Usage: minivm list zones\n" 3127 " Lists zone message formats\n";
3144 ast_cli(a->
fd,
"There are no voicemail zones currently defined\n");
3157 e->
command =
"minivm show settings";
3159 "Usage: minivm show settings\n" 3160 " Display Mini-Voicemail general settings\n";
3166 ast_cli(a->
fd,
"* Mini-Voicemail general settings\n");
3167 ast_cli(a->
fd,
" -------------------------------\n");
3169 ast_cli(a->
fd,
" Mail command (shell): %s\n", global_mailcmd);
3170 ast_cli(a->
fd,
" Max silence: %d\n", global_maxsilence);
3171 ast_cli(a->
fd,
" Silence threshold: %d\n", global_silencethreshold);
3172 ast_cli(a->
fd,
" Max message length (secs): %d\n", global_vmmaxmessage);
3173 ast_cli(a->
fd,
" Min message length (secs): %d\n", global_vmminmessage);
3174 ast_cli(a->
fd,
" Default format: %s\n", default_vmformat);
3175 ast_cli(a->
fd,
" Extern notify (shell): %s\n", global_externnotify);
3176 ast_cli(a->
fd,
" Logfile: %s\n", global_logfile[0] ? global_logfile :
"<disabled>");
3193 e->
command =
"minivm show stats";
3195 "Usage: minivm show stats\n" 3196 " Display Mini-Voicemail counters\n";
3202 ast_cli(a->
fd,
"* Mini-Voicemail statistics\n");
3203 ast_cli(a->
fd,
" -------------------------\n");
3209 ast_cli(a->
fd,
" Received messages since last reset: <none>\n");
3213 ast_strftime(buf,
sizeof(buf),
"%a %b %e %r %Z %Y", &timebuf);
3214 ast_cli(a->
fd,
" Last received voicemail: %s\n", buf);
3217 ast_strftime(buf,
sizeof(buf),
"%a %b %e %r %Z %Y", &timebuf);
3218 ast_cli(a->
fd,
" Last reset: %s\n", buf);
3232 if ((colname = strchr(username,
':'))) {
3238 if ((domain = strchr(username,
'@'))) {
3243 ast_log(
LOG_ERROR,
"This function needs a username and a domain: username@domain\n");
3250 if (!strcasecmp(colname,
"hasaccount")) {
3252 }
else if (!strcasecmp(colname,
"fullname")) {
3254 }
else if (!strcasecmp(colname,
"email")) {
3259 }
else if (!strcasecmp(colname,
"pager")) {
3261 }
else if (!strcasecmp(colname,
"etemplate")) {
3266 }
else if (!strcasecmp(colname,
"language")) {
3268 }
else if (!strcasecmp(colname,
"timezone")) {
3270 }
else if (!strcasecmp(colname,
"ptemplate")) {
3275 }
else if (!strcasecmp(colname,
"accountcode")) {
3277 }
else if (!strcasecmp(colname,
"pincode")) {
3279 }
else if (!strcasecmp(colname,
"path")) {
3285 if (!strcmp(var->
name, colname)) {
3321 char filename[BUFSIZ];
3322 char readbuf[BUFSIZ];
3324 int old = 0, counter = 0;
3330 snprintf(filename,
sizeof(filename),
"%s/%s.counter", directory, countername);
3332 counterfile = fopen(filename,
"r");
3334 if(fgets(readbuf,
sizeof(readbuf), counterfile)) {
3335 ast_debug(3,
"Read this string from counter file: %s\n", readbuf);
3336 old = counter = atoi(readbuf);
3338 fclose(counterfile);
3344 ast_debug(2,
"MINIVM Counter %s/%s: Value %d\n", directory, countername, counter);
3358 counterfile = fopen(filename,
"w");
3360 ast_log(
LOG_ERROR,
"Could not open counter file for writing : %s - %s\n", filename, strerror(
errno));
3364 fprintf(counterfile,
"%d\n\n", counter);
3365 fclose(counterfile);
3367 ast_debug(2,
"MINIVM Counter %s/%s: Old value %d New value %d\n", directory, countername, old, counter);
3375 char userpath[BUFSIZ];
3382 if ((countername = strchr(username,
':'))) {
3383 *countername =
'\0';
3387 if ((domain = strchr(username,
'@'))) {
3399 ast_log(
LOG_ERROR,
"This function needs two arguments: Account:countername\n");
3411 ast_log(
LOG_ERROR,
"Minivm account does not exist: %s@%s\n", username, domain);
3420 snprintf(buf, len,
"%d", res);
3428 char userpath[BUFSIZ];
3434 change = atoi(value);
3438 if ((countername = strchr(username,
':'))) {
3439 *countername =
'\0';
3442 if ((operand = strchr(countername,
':'))) {
3447 if ((domain = strchr(username,
'@'))) {
3465 ast_log(
LOG_ERROR,
"Writing to this function requires three arguments: Account:countername:operand\n");
3471 ast_log(
LOG_ERROR,
"Minivm account does not exist: %s@%s\n", username, domain);
3477 if (*operand ==
'i')
3479 else if (*operand ==
'd') {
3480 change = change * -1;
3482 }
else if (*operand ==
's')
3506 .
name =
"MINIVMCOUNTER",
3512 .
name =
"MINIVMACCOUNT",
3558 "Usage: minivm reload\n" 3559 " Reload mini-voicemail configuration and reset statistics\n";
3566 ast_cli(a->
fd,
"\n-- Mini voicemail re-configured \n");
#define DEFAULT_DATEFORMAT
struct ast_party_caller * ast_channel_caller(struct ast_channel *chan)
struct ast_variable * ast_load_realtime(const char *family,...) attribute_sentinel
static struct minivm_template * message_template_find(const char *name)
struct ast_variable * next
static int reload(void)
Reload mini voicemail module.
static int get_date(char *s, int len)
#define ast_channel_lock(chan)
Main Channel structure associated with a channel.
static int vm_delete(char *file)
#define AST_CLI_DEFINE(fn, txt,...)
char * str
Subscriber phone number (Malloced)
int ast_streamfile(struct ast_channel *c, const char *filename, const char *preflang)
Streams a file.
#define AST_LIST_LOCK(head)
Locks a list.
Asterisk locking-related definitions:
Asterisk main include file. File version handling, generic pbx functions.
static char * handle_minivm_show_users(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
CLI command to list voicemail accounts.
static struct minivm_account * find_user_realtime(const char *domain, const char *username)
struct ast_json * ast_json_pack(char const *format,...)
Helper for creating complex JSON values.
static int create_vmaccount(char *name, struct ast_variable *var, int realtime)
Append new mailbox to mailbox list from configuration file.
CallerID (and other GR30) management and generation Includes code and algorithms from the Zapata libr...
void ast_variables_destroy(struct ast_variable *var)
Free variable list.
static struct ast_custom_function minivm_counter_function
int ast_cli_unregister_multiple(struct ast_cli_entry *e, int len)
Unregister multiple commands.
static int b64_inchar(struct b64_baseio *bio, FILE *fi)
#define ast_channel_unref(c)
Decrease channel reference count.
static char * handle_minivm_list_templates(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
CLI routine for listing templates.
static int message_template_build(const char *name, struct ast_variable *var)
#define ast_set2_flag(p, value, flag)
#define ast_test_flag(p, flag)
struct ast_variable * ast_variable_browse(const struct ast_config *config, const char *category_name)
Time-related functions and macros.
void ast_json_unref(struct ast_json *value)
Decrease refcount on value. If refcount reaches zero, value is freed.
struct ast_party_name name
Subscriber name.
Convenient Signal Processing routines.
static int global_vmminmessage
#define ast_set_flag(p, flag)
struct ast_mwi_state * ast_mwi_create(const char *mailbox, const char *context)
Create a ast_mwi_state object.
Stasis Message Bus API. See Stasis Message Bus API for detailed documentation.
descriptor for a cli entry.
#define HMSU_OUTPUT_FORMAT
static char * handle_minivm_reload(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
Reload cofiguration.
#define AST_LIST_UNLOCK(head)
Attempts to unlock a list.
struct stasis_message * ast_mwi_blob_create(struct ast_mwi_state *mwi_state, struct stasis_message_type *message_type, struct ast_json *blob)
Creates a ast_mwi_blob message.
static int play_record_review(struct ast_channel *chan, char *playfile, char *recordfile, int maxtime, char *fmt, int outsidecaller, struct minivm_account *vmu, int *duration, int *sound_duration, const char *unlockdir, signed char record_gain)
static int minivm_counter_func_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
${MINIVMCOUNTER()} Dialplan function - read counters
char * ast_str_buffer(const struct ast_str *buf)
Returns the string buffer within the ast_str buf.
#define CONFIG_STATUS_FILEINVALID
static void free_user(struct minivm_account *vmu)
char language[MAX_LANGUAGE]
struct ast_tm * ast_localtime(const struct timeval *timep, struct ast_tm *p_tm, const char *zone)
Timezone-independent version of localtime_r(3).
static const struct ast_app_option minivm_accmess_options[128]
mvm_messagetype
Message types for notification.
Structure for variables, used for configurations and for channel variables.
static char * app_minivm_notify
char username[AST_MAX_CONTEXT]
static int timezone_add(const char *zonename, const char *config)
Add time zone to memory list.
void ast_str_substitute_variables(struct ast_str **buf, ssize_t maxlen, struct ast_channel *chan, const char *templ)
int ast_say_digit_str(struct ast_channel *chan, const char *num, const char *ints, const char *lang)
says digits of a string
static void vmaccounts_destroy_list(void)
ast_channel_state
ast_channel states
char * str
Subscriber name (Malloced)
static void free_zone(struct minivm_zone *z)
Free Mini Voicemail timezone.
int ast_str_append(struct ast_str **buf, ssize_t max_len, const char *fmt,...)
Append to a thread local dynamic string.
#define ast_cli_register_multiple(e, len)
Register multiple commands.
struct timeval ast_tvnow(void)
Returns current timeval. Meant to replace calls to gettimeofday().
#define AST_LIST_EMPTY(head)
Checks whether the specified list contains any entries.
static int global_vmmaxmessage
#define ast_mutex_lock(a)
#define ast_copy_flags(dest, src, flagz)
#define ast_str_alloca(init_len)
static int global_silencethreshold
#define ast_strdup(str)
A wrapper for strdup()
static char global_mailcmd[160]
char accountcode[AST_MAX_ACCOUNT_CODE]
Generic File Format Support. Should be included by clients of the file handling routines. File service providers should instead include mod_format.h.
char * ast_category_browse(struct ast_config *config, const char *prev_name)
Browse categories.
static int base_encode(char *filename, FILE *so)
int ast_unlock_path(const char *path)
Unlock a path.
static char * handle_minivm_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 minivm_mwi_exec(struct ast_channel *chan, const char *data)
int ast_filedelete(const char *filename, const char *fmt)
Deletes a file.
void ast_cli(int fd, const char *fmt,...)
int ast_channel_setoption(struct ast_channel *channel, int option, void *data, int datalen, int block)
Sets an option on a channel.
static int notify_new_message(struct ast_channel *chan, const char *templatename, struct minivm_account *vmu, const char *filename, long duration, const char *format, char *cidnum, char *cidname)
struct timeval lastreceived
static int create_dirpath(char *dest, int len, char *domain, char *username, char *folder)
int ast_unregister_application(const char *app)
Unregister an application.
int ast_channel_priority(const struct ast_channel *chan)
#define ast_verb(level,...)
char domain[AST_MAX_CONTEXT]
int ast_custom_function_unregister(struct ast_custom_function *acf)
Unregister a custom function.
const char * pbx_builtin_getvar_helper(struct ast_channel *chan, const char *name)
Return a pointer to the value of the corresponding channel variable.
int args
This gets set in ast_cli_register()
#define ast_strlen_zero(foo)
static int leave_voicemail(struct ast_channel *chan, char *username, struct leave_vm_options *options)
#define AST_APP_OPTIONS(holder, options...)
Declares an array of options for an application.
static void message_template_free(struct minivm_template *template)
static int b64_ochar(struct b64_baseio *bio, int c, FILE *so)
#define AST_MAX_ACCOUNT_CODE
Custom localtime functions for multiple timezones.
int ast_str_set(struct ast_str **buf, ssize_t max_len, const char *fmt,...)
Set a dynamic string using variable arguments.
static struct minivm_stats global_stats
Statistics for voicemail.
struct ast_party_id id
Caller party ID.
enum AST_LOCK_RESULT ast_lock_path(const char *path)
Lock a filesystem path.
Configuration File Parser.
static char mailbox[AST_MAX_MAILBOX_UNIQUEID]
#define ast_debug(level,...)
Log a DEBUG message.
static int check_dirpath(char *dest, int len, char *domain, char *username, char *folder)
static void timezone_destroy_list(void)
Clear list of timezones.
static int invent_message(struct ast_channel *chan, char *domain, char *username, int busy, char *ecodes)
static char * app_minivm_record
#define ast_config_load(filename, flags)
Load a config file.
char * ast_callerid_merge(char *buf, int bufsiz, const char *name, const char *num, const char *unknown)
General Asterisk PBX channel definitions.
Asterisk JSON abstraction layer.
static int minivm_notify_exec(struct ast_channel *chan, const char *data)
Asterisk file paths, configured in asterisk.conf.
#define B64_BASEMAXINLINE
#define RAII_VAR(vartype, varname, initval, dtor)
Declare a variable that will call a destructor function when it goes out of scope.
static int unload_module(void)
Unload mini voicemail module.
#define ast_dummy_channel_alloc()
Create a fake channel structure.
struct minivm_account::@54 list
Data structure associated with a custom dialplan function.
static int global_maxgreet
Caller Party information.
int ast_play_and_wait(struct ast_channel *chan, const char *fn)
Play a stream and wait for a digit, returning the digit that was pressed.
#define S_COR(a, b, c)
returns the equivalent of logic or for strings, with an additional boolean check: second one if not e...
static struct ast_cli_entry cli_minivm[]
CLI commands for Mini-voicemail.
int ast_play_and_record_full(struct ast_channel *chan, const char *playfile, const char *recordfile, int maxtime_sec, const char *fmt, int *duration, int *sound_duration, int beep, int silencethreshold, int maxsilence_ms, const char *path, const char *acceptdtmf, const char *canceldtmf, int skip_confirmation_sound, enum ast_record_if_exists if_exists)
Record a file based on input from a channel This function will play "auth-thankyou" upon successful r...
void ast_config_destroy(struct ast_config *config)
Destroys a config.
long int ast_random(void)
#define ast_strdupa(s)
duplicate a string in memory from the stack
A set of macros to manage forward-linked lists.
static struct minivm_account * find_account(const char *domain, const char *username, int createtemp)
#define ast_variable_new(name, value, filename)
#define AST_LIST_REMOVE_HEAD(head, field)
Removes and returns the head entry from a list.
static char * handle_minivm_show_settings(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
CLI Show settings.
static const struct ast_app_option minivm_app_options[128]
static void populate_defaults(struct minivm_account *vmu)
static char * message_template_parse_filebody(const char *filename)
Read message template from file.
int ast_exists_extension(struct ast_channel *c, const char *context, const char *exten, int priority, const char *callerid)
Determine whether an extension exists.
static const char * ast_str_quote(struct ast_str **buf, ssize_t maxlen, const char *from)
int ast_app_parse_options(const struct ast_app_option *options, struct ast_flags *flags, char **args, char *optstr)
Parses a string containing application options and sets flags/arguments.
static struct minivm_template * message_template_create(const char *name)
const char * ast_channel_exten(const struct ast_channel *chan)
Core PBX routines and definitions.
static int load_module(void)
Load mini voicemail module.
static int global_maxsilence
#define CONFIG_STATUS_FILEUNCHANGED
#define AST_LIST_HEAD_STATIC(name, type)
Defines a structure to be used to hold a list of specified type, statically initialized.
static struct minivm_account * mvm_user_alloc(void)
const char * ast_channel_uniqueid(const struct ast_channel *chan)
static FILE * minivmlogfile
static char * complete_minivm_show_users(const char *line, const char *word, int pos, int state)
#define HMSZ_OUTPUT_FORMAT
static char default_vmformat[80]
static int sendmail(struct minivm_template *template, struct minivm_account *vmu, char *cidnum, char *cidname, const char *filename, char *format, int duration, int attach_user_voicemail, enum mvm_messagetype type, const char *counter)
#define AST_LIST_INSERT_TAIL(head, elm, field)
Appends a list entry to the tail of a list.
struct ast_variable * chanvars
static int check_mime(const char *str)
static char * handle_minivm_show_stats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
Show stats.
int attribute_pure ast_true(const char *val)
Make sure something is true. Determine if a string containing a boolean value is "true". This function checks to see whether a string passed to it is an indication of an "true" value. It checks to see if the string is "yes", "true", "y", "t", "on" or "1".
The descriptor of a dynamic string XXX storage will be optimized later if needed We use the ts field ...
unsigned char iobuf[B64_BASEMAXINLINE]
int ast_safe_system(const char *s)
Safely spawn an OS shell command while closing file descriptors.
#define AST_OPTION_RXGAIN
char * mkdtemp(char *template_s)
#define AST_APP_OPTION_ARG(option, flagno, argno)
Declares an application option that accepts an argument.
const char * ast_config_AST_CONFIG_DIR
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
const char * ast_config_AST_LOG_DIR
static char * app_minivm_mwi
#define AST_LIST_TRAVERSE(head, var, field)
Loops over (traverses) the entries in a list.
#define AST_LIST_ENTRY(type)
Declare a forward link structure inside a list entry.
#define ast_channel_unlock(chan)
static int global_saydurationminfo
void stasis_publish(struct stasis_topic *topic, struct stasis_message *message)
Publish a message to a topic's subscribers.
static ast_mutex_t minivmloglock
#define ast_calloc(num, len)
A wrapper for calloc()
int ast_stream_and_wait(struct ast_channel *chan, const char *file, const char *digits)
stream file until digit If the file name is non-empty, try to play it.
static char * message_template_parse_emailbody(const char *body)
Parse emailbody template from configuration file.
const char * ast_config_AST_SPOOL_DIR
int ast_strftime(char *buf, size_t len, const char *format, const struct ast_tm *tm)
Special version of strftime(3) that handles fractions of a second. Takes the same arguments as strfti...
#define ast_publish_mwi_state_channel(mailbox, context, new_msgs, old_msgs, channel_id)
Publish a MWI state update associated with some channel.
static char global_externnotify[160]
static double global_volgain
Structure used to handle boolean flags.
The list of e-mail time zones.
AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS|AST_MODFLAG_LOAD_ORDER, "HTTP Phone Provisioning",.support_level=AST_MODULE_SUPPORT_EXTENDED,.load=load_module,.unload=unload_module,.reload=reload,.load_pri=AST_MODPRI_CHANNEL_DEPEND,.requires="http",)
static int vm_lock_path(const char *path)
lock directory
Options for leaving voicemail with the voicemail() application.
void ast_channel_exten_set(struct ast_channel *chan, const char *value)
Structure for base64 encoding.
int pbx_builtin_setvar_helper(struct ast_channel *chan, const char *name, const char *value)
Add a variable to the channel variable stack, removing the most recently set value for the same name...
#define SENDMAIL
Default mail command to mail voicemail. Change it with the mailcmd= command in voicemail.conf.
int ast_waitfordigit(struct ast_channel *c, int ms)
Waits for a digit.
The list of e-mail templates.
void ast_str_reset(struct ast_str *buf)
Reset the content of a dynamic string. Useful before a series of ast_str_append.
const char * ast_variable_retrieve(struct ast_config *config, const char *category, const char *variable)
size_t ast_str_strlen(const struct ast_str *buf)
Returns the current length of the string stored within buf.
static int minivm_counter_func_write(struct ast_channel *chan, const char *cmd, char *data, const char *value)
${MINIVMCOUNTER()} Dialplan function - changes counter data
static char dateformat[256]
char * strsep(char **str, const char *delims)
struct ast_channel_snapshot * ast_channel_snapshot_get_latest(const char *uniqueid)
Obtain the latest ast_channel_snapshot from the Stasis Message Bus API cache. This is an ao2 object...
Standard Command Line Interface.
static int load_config(int reload)
Load minivoicemail configuration.
void ast_channel_context_set(struct ast_channel *chan, const char *value)
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
#define S_OR(a, b)
returns the equivalent of logic or for strings: first one if not empty, otherwise second one...
static void queue_mwi_event(const char *channel_id, const char *mbx, const char *ctx, int urgent, int new, int old)
const char * ast_channel_name(const struct ast_channel *chan)
static int minivm_account_func_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
${MINIVMACCOUNT()} Dialplan function - reads account data
int ast_waitstream(struct ast_channel *c, const char *breakon)
Waits for a stream to stop or digit to be pressed.
int ast_fileexists(const char *filename, const char *fmt, const char *preflang)
Checks for the existence of a given file.
int ast_answer(struct ast_channel *chan)
Answer a channel.
static int minivm_accmess_exec(struct ast_channel *chan, const char *data)
Record specific messages for voicemail account.
static char * app_minivm_accmess
const char * ast_channel_language(const struct ast_channel *chan)
Abstract JSON element (object, array, string, int, ...).
const char * ast_channel_context(const struct ast_channel *chan)
int error(const char *format,...)
static const char * ast_str_encode_mime(struct ast_str **end, ssize_t maxlen, const char *charset, const char *start, size_t preamble, size_t postamble)
static int access_counter_file(char *directory, char *countername, int value, int operand)
Access counter file, lock directory, read and possibly write it again changed.
static int minivm_greet_exec(struct ast_channel *chan, const char *data)
unsigned char valid
TRUE if the name information is valid/present.
static struct ast_str * prompt
static char context[AST_MAX_CONTEXT]
static int b64_inbuf(struct b64_baseio *bio, FILE *fi)
#define AST_APP_OPTION(option, flagno)
Declares an application option that does not accept an argument.
static char * app_minivm_greet
Structure for gathering statistics.
static void run_externnotify(struct ast_channel *chan, struct minivm_account *vmu)
Run external notification for voicemail message.
const char * ast_channel_macrocontext(const struct ast_channel *chan)
static ast_mutex_t minivmlock
static int make_dir(char *dest, int len, const char *domain, const char *username, const char *folder)
The structure that contains MWI state.
Say numbers and dates (maybe words one day too)
struct stasis_topic * ast_mwi_topic(const char *uniqueid)
Get the Stasis Message Bus API topic for MWI messages on a unique ID.
#define HVLT_OUTPUT_FORMAT
#define ASTERISK_GPL_KEY
The text the key() function should return.
#define DEBUG_ATLEAST(level)
void ast_channel_priority_set(struct ast_channel *chan, int value)
int ast_dsp_get_threshold_from_settings(enum threshold which)
Get silence threshold from dsp.conf.
Asterisk module definitions.
static void message_destroy_list(void)
static snd_pcm_format_t format
static struct ast_flags globalflags
int ast_safe_execvp(int dualfork, const char *file, char *const argv[])
Safely spawn an external program while closing file descriptors.
Application convenience functions, designed to give consistent look and feel to Asterisk apps...
unsigned char valid
TRUE if the number information is valid/present.
#define ast_custom_function_register(acf)
Register a custom function.
static int minivm_record_exec(struct ast_channel *chan, const char *data)
static void prep_email_sub_vars(struct ast_channel *channel, const struct minivm_account *vmu, const char *cidnum, const char *cidname, const char *dur, const char *date, const char *counter)
#define AST_MUTEX_DEFINE_STATIC(mutex)
int ast_stopstream(struct ast_channel *c)
Stops a stream.
#define ast_register_application_xml(app, execute)
Register an application using XML documentation.
static char * app_minivm_delete
static int apply_general_options(struct ast_variable *var)
Apply general configuration options.
#define ast_app_separate_args(a, b, c, d)
static int minivm_delete_exec(struct ast_channel *chan, const char *data)
static char global_logfile[PATH_MAX]
#define ast_str_create(init_len)
Create a malloc'ed dynamic length string.
#define ast_mutex_unlock(a)
int ast_mkdir(const char *path, int mode)
Recursively create directory path.
struct ast_party_number number
Subscriber phone number.
static struct ast_custom_function minivm_account_function
static char MVM_SPOOL_DIR[PATH_MAX]
struct stasis_message_type * ast_mwi_vm_app_type(void)
Get the Stasis Message Bus API message type for voicemail application specific messages.