Index: app.c =================================================================== --- app.c (revision 24834) +++ app.c (working copy) @@ -537,7 +537,7 @@ static int global_silence_threshold = 128; static int global_maxsilence = 0; -int ast_play_and_record(struct ast_channel *chan, const char *playfile, const char *recordfile, int maxtime, const char *fmt, int *duration, int silencethreshold, int maxsilence, const char *path) +int ast_play_and_record(struct ast_channel *chan, const char *playfile, const char *recordfile, int maxtime, const char *fmt, int *duration, int silencethreshold, int maxsilence, const char *path, const char *acceptdtmf, const char *canceldtmf) { int d; char *fmts; @@ -688,19 +688,18 @@ /* Write only once */ ast_writestream(others[0], f); } else if (f->frametype == AST_FRAME_DTMF) { - if (f->subclass == '#') { + if (strchr(acceptdtmf, f->subclass)) { if (option_verbose > 2) - ast_verbose( VERBOSE_PREFIX_3 "User ended message by pressing %c\n", f->subclass); - res = '#'; + ast_verbose(VERBOSE_PREFIX_3 "User ended message by pressing %c\n", f->subclass); + res = f->subclass; outmsg = 2; ast_frfree(f); break; } - if (f->subclass == '0') { - /* Check for a '0' during message recording also, in case caller wants operator */ + if (strchr(canceldtmf, f->subclass)) { if (option_verbose > 2) - ast_verbose(VERBOSE_PREFIX_3 "User cancelled by pressing %c\n", f->subclass); - res = '0'; + ast_verbose(VERBOSE_PREFIX_3 "User cancelled message by pressing %c\n", f->subclass); + res = f->subclass; outmsg = 0; ast_frfree(f); break; @@ -1191,6 +1190,8 @@ int attempts = 0; int recorded = 0; int message_exists = 0; + char *acceptdtmf = "#"; + char *canceldtmf = ""; /* Note that urgent and private are for flagging messages as such in the future */ /* barf if no pointer passed to store duration in */ @@ -1228,7 +1229,7 @@ else ast_verbose(VERBOSE_PREFIX_3 "Recording\n"); recorded = 1; - cmd = ast_play_and_record(chan, playfile, recordfile, maxtime, fmt, duration, silencethreshold, maxsilence, path); + cmd = ast_play_and_record(chan, playfile, recordfile, maxtime, fmt, duration, silencethreshold, maxsilence, path, acceptdtmf, canceldtmf); if (cmd == -1) { /* User has hung up, no options to give */ return cmd; Index: apps/app_voicemail.c =================================================================== --- apps/app_voicemail.c (revision 24834) +++ apps/app_voicemail.c (working copy) @@ -668,14 +668,10 @@ char *user = NULL, *pass = NULL, *rest = NULL, *comment = NULL, *tmpctx = NULL, *tmpctxend = NULL; /* Read in the line */ - fgets(inbuf, sizeof(inbuf), configin); + if (fgets(inbuf, sizeof(inbuf), configin) == NULL) + continue; linenum++; - if (ast_strlen_zero(inbuf)) { - fprintf(configout, "\n"); - continue; - } - /* Make a backup of it */ ast_copy_string(orig, inbuf, sizeof(orig)); @@ -2375,6 +2371,7 @@ int duration = 0; int ausemacro = 0; int ousemacro = 0; + int ouseexten = 0; char date[256]; char dir[256]; char fn[256]; @@ -2433,14 +2430,20 @@ create_dirpath(dir, sizeof(dir), vmu->context, ext, "INBOX"); /* Check current or macro-calling context for special extensions */ - if (!ast_strlen_zero(vmu->exit)) { - if (ast_exists_extension(chan, vmu->exit, "o", 1, chan->cid.cid_num)) + if (ast_test_flag(vmu, VM_OPERATOR)) { + if (!ast_strlen_zero(vmu->exit)) { + if (ast_exists_extension(chan, vmu->exit, "o", 1, chan->cid.cid_num)) { + strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); + ouseexten = 1; + } + } else if (ast_exists_extension(chan, chan->context, "o", 1, chan->cid.cid_num)) { strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); - } else if (ast_exists_extension(chan, chan->context, "o", 1, chan->cid.cid_num)) - strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); - else if (!ast_strlen_zero(chan->macrocontext) && ast_exists_extension(chan, chan->macrocontext, "o", 1, chan->cid.cid_num)) { - strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); - ousemacro = 1; + ouseexten = 1; + } + else if (!ast_strlen_zero(chan->macrocontext) && ast_exists_extension(chan, chan->macrocontext, "o", 1, chan->cid.cid_num)) { + strncat(ecodes, "0", sizeof(ecodes) - strlen(ecodes) - 1); + ousemacro = 1; + } } if (!ast_strlen_zero(vmu->exit)) { @@ -2502,10 +2505,11 @@ pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); return 0; } + /* Check for a '0' here */ if (res == '0') { transfer: - if (ast_test_flag(vmu, VM_OPERATOR)) { + if(ouseexten || ousemacro) { chan->exten[0] = 'o'; chan->exten[1] = '\0'; if (!ast_strlen_zero(vmu->exit)) { @@ -2517,12 +2521,8 @@ chan->priority = 0; free_user(vmu); pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); - return 0; - } else { - ast_play_and_wait(chan, "vm-sorry"); - pbx_builtin_setvar_helper(chan, "VMSTATUS", "USEREXIT"); - return 0; } + return 0; } if (res < 0) { free_user(vmu); @@ -5248,7 +5248,7 @@ while ((cmd > -1) && (cmd != 't') && (cmd != '#')) { switch(cmd) { case '1': /* Reply */ - if (vms.lastmsg > -1) { + if (vms.lastmsg > -1 && !vms.starting) { cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 1, record_gain); if (cmd == ERROR_LOCK_PATH) { res = cmd; @@ -5259,9 +5259,9 @@ cmd = 't'; break; case '2': /* Callback */ - if (option_verbose > 2) + if (option_verbose > 2 && !vms.starting) ast_verbose( VERBOSE_PREFIX_3 "Callback Requested\n"); - if (!ast_strlen_zero(vmu->callback) && vms.lastmsg > -1) { + if (!ast_strlen_zero(vmu->callback) && vms.lastmsg > -1 && !vms.starting) { cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 2, record_gain); if (cmd == 9) { silentexit = 1; @@ -5276,7 +5276,7 @@ cmd = 't'; break; case '3': /* Envelope */ - if (vms.lastmsg > -1) { + if (vms.lastmsg > -1 && !vms.starting) { cmd = advanced_options(chan, vmu, &vms, vms.curmsg, 3, record_gain); if (cmd == ERROR_LOCK_PATH) { res = cmd; @@ -6440,6 +6440,9 @@ res = play_message_datetime(chan, vmu, origtime, filename); if (!res) res = play_message_callerid(chan, vms, cid, context, 0); + + res = 't'; + } else if (option == 2) { /* Call back */ if (!ast_strlen_zero(cid)) { @@ -6584,6 +6587,9 @@ int recorded = 0; int message_exists = 0; signed char zero_gain = 0; + char *acceptdtmf = "#"; + char *canceldtmf = ""; + /* Note that urgent and private are for flagging messages as such in the future */ /* barf if no pointer passed to store duration in */ @@ -6637,7 +6643,9 @@ /* 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 */ if (record_gain) ast_channel_setoption(chan, AST_OPTION_RXGAIN, &record_gain, sizeof(record_gain), 0); - cmd = ast_play_and_record(chan, playfile, recordfile, maxtime, fmt, duration, silencethreshold, maxsilence, unlockdir); + if (ast_test_flag(vmu, VM_OPERATOR)) + canceldtmf = "0"; + cmd = ast_play_and_record(chan, playfile, recordfile, maxtime, fmt, duration, silencethreshold, maxsilence, unlockdir, acceptdtmf, canceldtmf); if (record_gain) ast_channel_setoption(chan, AST_OPTION_RXGAIN, &zero_gain, sizeof(zero_gain), 0); if (cmd == -1) { @@ -6700,6 +6708,10 @@ return 1; #endif case '0': + if(!ast_test_flag(vmu, VM_OPERATOR)) { + cmd = ast_play_and_wait(chan, "vm-sorry"); + break; + } if (message_exists || recorded) { cmd = ast_play_and_wait(chan, "vm-saveoper"); if (!cmd) Index: apps/app_dial.c =================================================================== --- apps/app_dial.c (revision 24834) +++ apps/app_dial.c (working copy) @@ -764,6 +764,8 @@ int digit = 0, result = 0; time_t start_time, answer_time, end_time; struct ast_app *app = NULL; + char *acceptdtmf = "#"; + char *canceldtmf = ""; char *parse; AST_DECLARE_APP_ARGS(args, @@ -974,9 +976,10 @@ "At the tone, please say your name:" */ - ast_play_and_record(chan, "priv-recordintro", privintro, 4, "gsm", &duration, 128, 2000, 0); /* NOTE: I've reduced the total time to 4 sec */ - /* don't think we'll need a lock removed, we took care of - conflicts by naming the privintro file */ + ast_play_and_record(chan, "priv-recordintro", privintro, 4, "gsm", &duration, 128, 2000, 0, acceptdtmf, canceldtmf); + /* NOTE: I've reduced the total time to 4 sec don't think we'll need + * a lock removed, we took care of conflicts by naming the privintro + * file */ } } } Index: include/asterisk/app.h =================================================================== --- include/asterisk/app.h (revision 24834) +++ include/asterisk/app.h (working copy) @@ -134,7 +134,7 @@ \n permitted silence time in milliseconds of 'maxsilence' under 'silencethreshold' or use '-1' for either or both parameters for defaults. calls ast_unlock_path() on 'path' if passed */ -int ast_play_and_record(struct ast_channel *chan, const char *playfile, const char *recordfile, int maxtime_sec, const char *fmt, int *duration, int silencethreshold, int maxsilence_ms, const char *path); +int ast_play_and_record(struct ast_channel *chan, const char *playfile, const char *recordfile, int maxtime_sec, const char *fmt, int *duration, int silencethreshold, int maxsilence_ms, const char *path, const char *acceptdtmf, const char *canceldtmf); /*! Record a message and prepend the message to the given record file after playing the optional playfile (or a beep), storing the duration in