static char rcsid[] = "@(#)$Id: elm.c,v 1.122 2006/07/01 06:26:52 hurtta Exp $";
/*****************************************************************************
* The Elm (ME+) Mail System - $Revision: 1.122 $ $State: Exp $
*
* Modified by: Kari Hurtta <hurtta+elm@posti.FMI.FI>
* (was hurtta+elm@ozone.FMI.FI)
* or Kari Hurtta <elm@elmme-mailer.org>
*****************************************************************************
* The Elm Mail System
*
* This file and all associated files and documentation:
* Copyright (c) 1988-1992 USENET Community Trust
* Copyright (c) 1986,1987 Dave Taylor
*****************************************************************************/
/* Main program of the ELM mail system!
*/
#include "patchlevel.h"
#include "elm.h"
#include "mailerlib.h"
#include "mboxlib.h"
#include "s_elm.h"
#ifdef BSD_TYPE
# include <sys/timeb.h>
#endif
#include "mime.h"
#include "me.h"
DEBUG_VAR(Debug,__FILE__,"ELM");
static unsigned char * s2us P_((char *str));
static unsigned char * s2us(str)
char *str;
{
return (unsigned char *)str;
}
static void do_check_only P_((char *argv[],
struct AliasView *aview));
static void debug_screen P_((struct MailboxView *mailbox,
struct screen_parts *LOC));
static void debug_message P_((struct header_rec *hdr, int current,
struct folder_view *index));
static void elm_panic_prepare P_((CONST int interrupt,
CONST char * title,
CONST char * ms));
static void elm_panic_prepare(interrupt,title,ms)
CONST int interrupt;
CONST char * title;
CONST char * ms;
{
int do_cursor = RawState();
if (do_cursor && !interrupt) {
lib_error(FRM("%s: %s"),title,ms);
sleep(1);
}
if (do_cursor) {
/* MoveCursor() is not safe on interrupt */
if (interrupt) {
ClearScreen(1); /* 1 == is called from interrupt */
Raw(OFF|RAW_FROM_SIGNAL);
} else {
int LINES, COLUMNS;
menu_get_sizes(default_context, &LINES, &COLUMNS);
MoveCursor(LINES-1,0);
Raw(OFF);
}
}
}
static void elm_panic_exit P_((CONST int interrupt));
static void elm_panic_exit(interrupt)
CONST int interrupt;
{
emergency_exit(interrupt);
}
void forget_passphrase()
{
#ifdef USE_PGP
if (pgp_void_passphrase())
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmPGPPassphraseForgotten,
"PGP passphrase forgotten!"));
#endif
#ifdef REMOTE_MBX
if(close_cached_connections())
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmCachedConenctionsClosed,
"Cached connections closed!"));
#endif
error_sleep(1);
}
#include <errno.h>
#ifndef ANSI_C
extern int errno;
#endif
int mailbox_command(mailbox, ch, LOC, cmdX, aview,
page)
struct MailboxView *mailbox;
int ch;
struct screen_parts *LOC;
showmsg_cmd cmdX;
struct AliasView *aview;
struct menu_context *page;
{
struct menu_common MENU;
int LINES, COLUMNS;
menu_get_sizes(page, &LINES, &COLUMNS);
set_mcommon_from_mbxview(&MENU,mailbox);
switch (ch) {
#ifdef ALLOW_SUBSHELL
case '!' :
menu_Writechar(LOC->prompt_page,'!');
subshell(mailbox, page,LOC->prompt_page);
break;
#endif
case '<' : {
/* scan current message for calendar information */
#ifdef ENABLE_CALENDAR
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat,
ElmSet,
ElmScanForCalendar,
"Scan message for calendar entries..."));
if (current < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToScan,
"No mail to scan!"));
} else if (give_message_data(mailbox,current-1,
NULL,NULL,NULL,NO_mime_parse)) {
/* FIX: mime sctructure is not
currently used */
scan_calendar(mailbox);
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
#else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmSorryNoCalendar,
"Sorry. Calendar function disabled."));
#endif
}
break;
case 'a' :
alias(mailbox, aview);
menu_trigger_redraw(page);
/* define_softkeys(MAIN); */
break;
case 'b' : {
int current = get_current(mailbox);
struct header_rec *hdr;
FILE *F;
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat,
ElmSet, ElmBounceMessage,
"Bounce message"));
FlushBuffer();
if (current < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToBounce,
"No mail to bounce!"));
} else if (give_message_data(mailbox,current-1,
&hdr,&F,NULL,
NO_mime_parse)) {
remail(hdr,F, aview, page, LOC->prompt_page);
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
}
break;
#ifdef USE_PGP
case ctrl('E'): {
int current = get_current(mailbox);
struct header_rec *hdr;
FILE *F;
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet, ElmExtractPGPKey,
"Extract PGP public key"));
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet, ElmNoMailInFolder,
"There is no mail in this folder!"));
else if (give_message_data(mailbox,current-1,
&hdr,&F,NULL,NO_mime_parse)) {
if (hdr->pgp & PGP_PUBLIC_KEY) {
/* FIXME: mime structure is not currently used */
pgp_extract_public_key(hdr,F,page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoPgpPublicKeys,
"This message does not contain PGP public keys!"));
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
}
break;
#endif
case 'E':
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmExtendedCommand,
"Extended command"));
FlushBuffer();
extended_command(mailbox,
aview,
page,
LOC);
break;
case ctrl('F'):
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmPassphraseForget,
"Forget passphrase"));
forget_passphrase();
break;
case 'f' : {
int current = get_current(mailbox);
struct header_rec *hdr;
FILE *F;
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmForward,
"Forward"));
/* define_softkeys(YESNO); */
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToForward,
"No mail to forward!"));
else {
forward(current-1,mailbox, aview,
page,
LOC->prompt_page,
LOC->header_page);
}
/* define_softkeys(MAIN); */
}
break;
case 'g' : {
int current = get_current(mailbox);
struct header_rec *hdr;
FILE *F;
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmGroupReply,
"Group reply"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToReply,
"No mail to reply to!"));
else if (give_message_data(mailbox,current-1,
&hdr,NULL,NULL,
mime_parse_routine)) {
if (hdr->status & FORM_LETTER) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmCantGroupReplyForm,
"Can't group reply to a Form!!"));
} else {
int vis;
/* define_softkeys(YESNO); */
reply_to_everyone(current-1, mailbox, aview,
page,
LOC->prompt_page,
LOC->header_page);
/* define_softkeys(MAIN); */
}
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
FlushBuffer();
}
break;
case 'h' : {
int current = get_current(mailbox);
if (elm_filter)
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat,
ElmSet,
ElmMessageWithHeaders,
"Message with headers..."));
else
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat,
ElmSet,
ElmDisplayMessage,
"Display message"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToRead,
"No mail to read!"));
else {
int x = show_message_with_headers(mailbox,cmdX,aview,page,
LOC->header_page);
if (x != 0)
return x; /* "call" parent or EOF */
current = get_current(mailbox);
}
}
break;
case 'I' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmMailingListInfo,
"Mailing List Info"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToViewInfo,
"No mail to view list info!"));
else {
list_info(current-1,mailbox, aview, page,LOC->prompt_page);
}
/* softkeys_on(); */
}
break;
#ifdef USE_PGP
case ctrl('K'):
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmMailPGPPublicKey,
"Mail PGP public key"));
FlushBuffer();
pgp_mail_public_key(mailbox, aview,
page,
LOC->prompt_page);
break;
#endif
case 'm' :
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmMail,
"Mail"));
FlushBuffer();
send_msg_l(-1, NULL, NULL, NULL,
MAIL_EDIT_MSG,allow_forms,
mailbox, aview,page, LOC->prompt_page);
break;
case ' ' :
case ctrl('J'):
case ctrl('M'): {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmDisplayMessage,
"Display message"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToRead,
"No mail to read!"));
else {
int x = show_message_normal(mailbox,cmdX,aview,page,
LOC->header_page);
if (x != 0)
return x; /* "call" parent or EOF */
current = get_current(mailbox);
}
}
break;
case 'n' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmNextMessage,
"Next Message"));
FlushBuffer();
/* define_softkeys(READ); */
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToRead,
"No mail to read!"));
else {
int x = show_next_message(mailbox,cmdX,aview,page,
LOC->header_page);
if (x != 0)
return x; /* "call" parent or EOF */
current = get_current(mailbox);
}
}
break;
case ctrl('N'): {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmNextUMessage,
"Next Unread Message"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToRead,
"No mail to read!"));
else {
int mc;
int i = 0;
struct pager_page * PP = init_pager_page(&MENU);
if(ison_status_message(mailbox,current-1,status_basic,UNREAD)) {
i = mbx_show_msg(mailbox,current-1,PP);
} else
i = ctrl('N');
while (i >0) {
i = process_showmsg_cmd(i, mailbox, cmdX, aview,
PP);
switch (i) {
case EOF:
exit_pager_page(&PP,page);
return EOF;/* Read failed, control tty died? */
case 'X': /* Quick Exit */
case 'x': /* Exit */
exit_pager_page(&PP,page);
return i; /* "call" parent */
case 0:
break;
default:
DPRINT(Debug,3,(&Debug,
"Looping showmsg command %d (%c)\n",
i,i));
}
}
exit_pager_page(&PP,page);
current = get_current(mailbox);
menu_trigger_redraw(page);
if (++current > (mc = get_message_count(mailbox)))
current = mc;
set_current(mailbox,current);
get_page(&MENU, LOC->header_page);
}
}
break;
case 'O' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmOverrideCharset,
"Override charset"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToOverride,
"No mail to override!"));
else
OverrideCharset(mailbox, page,
LOC->prompt_page,
LOC->header_page);
}
break;
case 'P' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmPrintTextMail,
"Print text of mail"));
FlushBuffer();
if (current < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToPrint,
"No mail to print!"));
} else if (give_message_data(mailbox,current-1,
NULL,NULL,NULL,
mime_parse_routine)) {
int vis;
print_text(TRUE, mailbox, page, LOC->header_page);
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
}
break;
case 'R' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmGenericReply,
"Generic Reply"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToReplyTo,
"No mail to reply to!"));
else {
generic_reply(current-1,mailbox, aview,
page,LOC->prompt_page);
}
/* softkeys_on(); */
}
break;
case 'r' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmReplyToMessage,
"Reply to message"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToReplyTo,
"No mail to reply to!"));
else {
reply(current-1,mailbox, aview,
page,
LOC->prompt_page,
LOC->header_page);
}
/* softkeys_on(); */
}
break;
case '>' : /** backwards compatibility **/
case 'C' :
case 's' : {
int current = get_current(mailbox);
if (ch != 'C')
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmSaveToFolder,
"Save to folder"));
else
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmCopyToFolder,
"Copy to folder"));
FlushBuffer();
if (current < 1) {
if (ch != 'C')
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToSave,
"No mail to save!"));
else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToCopy,
"No mail to copy!"));
} else if (give_message_data(mailbox,current-1,
NULL,NULL,NULL,NO_mime_parse)) {
if (save(FALSE, (ch != 'C'), 0,mailbox, aview,
page,
LOC->prompt_page,
LOC->header_page)
&& resolve_mode && ch != 'C') {
int i;
if((i=next_message(current-1, TRUE, &MENU)) != -1) {
int current = get_current(mailbox);
current = i+1;
set_current(mailbox,current);
get_page(&MENU, LOC->header_page);
}
}
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
ClearLine(LINES-3);
}
break;
case 'S' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmSaveTextToFileorFolder,
"Save (copy) text to file or folder"));
FlushBuffer();
if (current < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToCopy,
"No mail to copy!"));
} else if (give_message_data(mailbox,current-1,
NULL,NULL,NULL,
mime_parse_routine)) {
int vis;
save(FALSE, 0, 1, mailbox, aview,
page,
LOC->prompt_page,
LOC->header_page);
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
ClearLine(LINES-3);
}
break;
case 'U' : {
if (get_message_count(mailbox) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToMarkUnread,
"No %S to mark as unread!"),
mcommon_give_item(&MENU,m_items));
}
else
unread_msg(mailbox, LOC->header_page);
}
break;
case 'v' : {
struct header_rec *hdr;
FILE *F;
int current = get_current(mailbox);
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMessages,
"There are no messages!"));
else {
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmViewParts,
"View parts of message"));
if (give_message_data(mailbox,current-1,
&hdr,&F,NULL,mime_parse_routine)) {
int vis;
if ((hdr->status & MIME_MESSAGE)) {
mime_warnings(hdr);
attach_menu(F,& (hdr->mime_rec),
NULL,
hdr->header_charset, NULL,
hdr,
aview,
& (hdr->header_error));
menu_trigger_redraw(page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMIMEMessage,
"This is not a MIME message!"));
/* FIXME ? */
vis = compute_visible(current, &MENU);
menu_header_status_update(LOC->header_page,vis-1);
} else {
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
}
}
}
break;
case 'V': {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmViewDigest,
"View digest as mailbox"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToView,
"No mail to view!"));
else if (give_message_data(mailbox,current-1,
NULL,NULL,NULL,mime_parse_routine)) {
ViewDigest(mailbox,aview,page);
current = get_current(mailbox);
get_page(&MENU, LOC->header_page);
} else {
int vis;
DPRINT(Debug,3,(&Debug,
"give_message_data [%d] fails",current-1));
/* FIXME? */
vis = compute_visible(current, &MENU);
menu_header_status_update(LOC->header_page,vis-1);
}
}
break;
case EOF :
return EOF;/* Read failed, control tty died? */
case '@' :
debug_screen(mailbox,LOC);
menu_trigger_redraw(page);
break;
case '#' : {
int current = get_current(mailbox);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmCheckMessage,
"Check message"));
FlushBuffer();
if (current < 1)
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMailToCheck,
"No mail to check."));
else {
struct header_rec * hdr = give_header(mailbox,
current-1);
if (hdr) {
struct folder_view index;
give_index_number(mailbox,current-1,
&index);
debug_message(hdr, current, &index);
menu_trigger_redraw(page);
}
}
}
break;
default:
/* Maybe motion command */
ch = motion(ch,&MENU,LOC, page);
/* motion() may already set, menu_trigger_redraw(page),
we do not examine it */
return ch;
}
return 0; /* Command OK */
}
void new_mail_check (mailbox, page, LOC)
struct MailboxView *mailbox;
struct menu_context *page;
struct screen_parts *LOC;
{
int idx, mbxcount;
struct menu_common MENU;
int LINES, COLUMNS;
menu_get_sizes(page,&LINES, &COLUMNS);
set_mcommon_from_mbxview(&MENU,mailbox);
mbxcount = get_storage_count(mailbox);
for (idx = 0 ; idx < mbxcount; idx++) {
int bytes;
struct current_storage * storage = get_storage(mailbox, idx);
if (!storage ||
!storage->current_folder)
continue;
flush_folder(storage->current_folder);
if (new_mail_on_folder(storage->current_folder,
&bytes)) {
int current = get_current(mailbox);
int last_in_folder = storage->message_count;
int selected = get_selected(mailbox);
int ok;
DPRINT(Debug,2,(&Debug,
"Just received %d bytes more mail (elm), storage idx %d\n",
bytes, idx));
lib_transient(CATGETS(elm_msg_cat, ElmSet, ElmNewMailHangOn,
"New mail has arrived! Hang on..."));
ok = read_new_mails(storage, page);
if (ok)
clear_error();
if (selected) {
/* update count of selected messages */
selected += storage->message_count - last_in_folder;
set_selected(mailbox,selected);
}
menu_trigger_redraw(LOC->header_page);
menu_trigger_redraw(LOC->title_page);
ClearLine(LINES-2); /* remove reading message... */
if (ok) {
if ((storage->message_count - last_in_folder) == 1)
lib_error(CATGETS(elm_msg_cat, ElmSet, ElmNewMessageRecv,
"1 new message received."));
else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNewMessageRecvPlural,
"%d new messages received."),
storage->message_count - last_in_folder);
} else
show_last_error();
} else if (bytes < 0) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmALERTMailfileShrinken,
"ALERT: Mailfile shrinken %d bytes!"),
-bytes);
DPRINT(Debug,1,(&Debug,
"ALERT: Mailfile shrinken %d bytes!",
-bytes));
sleep_message();
}
}
}
void mailbox_screen_common(page,LOC, LIST)
struct menu_context *page;
struct screen_parts *LOC;
struct menu_param *LIST;
{
int LINES, COLUMNS;
int headers_per_page;
menu_get_sizes(page,&LINES, &COLUMNS);
/* 3) prompt part */
if (LOC->prompt_page)
menu_subpage_relocate(LOC->prompt_page,page,LINES-4,4);
else
LOC->prompt_page = new_menu_subpage(page,LINES-4,4,
subpage_simple_noredraw,LIST);
headers_per_page = LOC->menu_page ? LINES-13 : LINES-9;
if (headers_per_page < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet, ElmWindowSizeTooSmall,
"The window is too small to run Elm. It must have at least %d rows"),
LINES - headers_per_page);
headers_per_page = 1;
}
/* 4) headers of screen */
if (! LOC->header_page)
LOC->header_page = new_menu_header(page,4,
headers_per_page,
hdr_show_header,
hdr_show_current,
null_header_param_changed,
hdr_show_status,
LIST);
else
menu_header_relocate(LOC->header_page,page,
4,headers_per_page);
}
void free_mailbox_screen(LOC)
struct screen_parts *LOC;
{
erase_menu_context (&(LOC->title_page));
if (LOC->menu_page)
erase_menu_context (&(LOC->menu_page));
erase_menu_context (&(LOC->prompt_page));
if (LOC->header_page)
erase_menu_context (&(LOC->header_page));
}
#if ANSI_C
static subpage_simple_redraw sb_update_sendtitle;
#endif
static int sb_update_sendtitle(ptr,list)
struct menu_context *ptr;
struct menu_param *list;
{
menu_ClearScreen(ptr);
menu_print_format_center(ptr,1,
CATGETS(elm_msg_cat, ElmSet, ElmSendOnlyMode,
"Send only mode [ELM %s]"),
version_buff);
return 1; /* Redraw completely done */
}
static void set_sendmode_screen P_((struct menu_context *page,
struct screen_parts *LOC,
struct menu_param *LIST));
static void set_sendmode_screen(page,LOC, LIST)
struct menu_context *page;
struct screen_parts *LOC;
struct menu_param *LIST;
{
int LINES, COLUMNS;
menu_get_sizes(page,&LINES, &COLUMNS);
/* 1) Title part of screen */
if (! LOC->title_page)
LOC->title_page = new_menu_subpage(page,0,4,sb_update_sendtitle,LIST);
else
menu_subpage_relocate(LOC->title_page,page,0,4);
/* 2) menu part */
LOC->menu_page = NULL;
/* 3) prompt part */
if (LOC->prompt_page)
menu_subpage_relocate(LOC->prompt_page,page,LINES-4,4);
else
LOC->prompt_page = new_menu_subpage(page,LINES-4,4,
subpage_simple_noredraw,LIST);
/* 4) headers of screen */
LOC->header_page = NULL;
}
int main P_((int argc, char *argv[]));
int main(argc, argv)
int argc;
char *argv[];
{
int ch;
char **req_mfile_vector = NULL; /* Malloced */
char **to_whom = NULL;
int i,j; /** Random counting variables (etc) **/
struct menu_context *page = NULL;
struct AliasView * cur_aliaslist = NULL;
enum check_mode check_mode = chk_none;
char * url_mode = NULL;
set_panic_prepare(elm_panic_prepare);
set_panic_exit(elm_panic_exit);
#if DEBUG
init_debugfile("ELM");
/* HACK ....
USER may want enable debug output for locale_init()
This gives wrong result if some options value start
with "-d"
*/
for (i = 1; i < argc; i++) {
if ('-' == argv[i][0] &&
'd' == argv[i][1] &&
argv[i][2]) {
set_debugging(& (argv[i][2]));
}
}
#endif
locale_init();
req_mfile_vector = parse_arguments(argc, argv, &to_whom,
&check_mode, &url_mode);
initialize(&cur_aliaslist, &page);
if (url_mode) {
struct string * s = new_string2(system_charset,s2us(url_mode));
struct url * url = url_from_raw(s,NULL,NULL);
enum url_type T;
DPRINT(Debug,2,(&Debug,
"Elm: Url-mode\n"));
/* Be sure that errors are visible */
error_wait();
if (!url) {
free_string(&s);
goto fail_1;
}
T = get_url_type(url);
switch (T) {
int r;
case url_unknown:
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmUnknownUrl,
"Unsupported URL type. Can not open %S"),
s);
free_url(&url);
free_string(&s);
goto fail_1;
case url_mailing:
DPRINT(Debug,2,(&Debug,
"Mail-only: mailing to URL\n"));
if(!batch_only) {
struct screen_parts LOC = { NULL, NULL, NULL, NULL };
set_sendmode_screen(page,&LOC,NULL);
sb_update_sendtitle(LOC.title_page,NULL);
r = send_msg_url(url, batch_subject,
MAIL_EDIT_MSG |
(confirm_url ? MAIL_ASK_SEND : 0),
(batch_only ? NO : allow_forms),
cur_aliaslist, page,
LOC.prompt_page);
free_mailbox_screen(&LOC);
if (!r) {
free_url(&url);
free_string(&s);
goto fail_1;
}
} else {
if (confirm_url) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmConfirmUrlBatch,
"Can't confirm url on batch mode."));
free_url(&url);
free_string(&s);
goto fail_1;
}
r = send_msg_url(url, batch_subject, MAIL_EDIT_MSG,
(batch_only ? NO : allow_forms),
cur_aliaslist, page,
NULL);
if (!r) {
free_url(&url);
free_string(&s);
goto fail_1;
}
}
break;
case url_mailbox_list:
DPRINT(Debug,2,(&Debug,
"Selecting mailbox from URL\n"));
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmMailboxListUnsUrl,
"Mailbox list is unsupported. Can not open %S"),
s);
free_url(&url);
free_string(&s);
goto fail_1;
case url_mailbox:
DPRINT(Debug,2,(&Debug,
"Viewing mailbox from URL\n"));
if (batch_only) {
DPRINT(Debug,2,(&Debug,
"Batch-only\n"));
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmBatchOnlyMailbox,
"Can't browse mailbox on batch-only mode!"));
goto fail_1;
}
r = url_messages_menu(page,url,cur_aliaslist, check_mode);
if (!r) {
free_url(&url);
free_string(&s);
goto fail_1;
}
break;
}
free_url(&url);
free_string(&s);
} else if (mail_only) {
DPRINT(Debug,2,(&Debug,
"Elm: Mail-only: mailing to\n"));
if(!batch_only) {
struct screen_parts LOC = { NULL, NULL, NULL, NULL };
int r;
set_sendmode_screen(page,&LOC,NULL);
sb_update_sendtitle(LOC.title_page,NULL);
r = send_msg_argv(to_whom, batch_subject, MAIL_EDIT_MSG,
(batch_only ? NO : allow_forms),
cur_aliaslist, page,
LOC.prompt_page);
free_mailbox_screen(&LOC);
if (!r)
goto fail_1;
} else {
int r = send_msg_argv(to_whom, batch_subject, MAIL_EDIT_MSG,
(batch_only ? NO : allow_forms),
cur_aliaslist, page,
NULL);
if (EOF == r)
goto fail_EOF;
if (!r)
goto fail_1;
}
} else if (check_only) {
DPRINT(Debug,2,(&Debug,
"Elm: Check-only\n"));
do_check_only(to_whom, cur_aliaslist);
} else if (batch_only) {
DPRINT(Debug,2,(&Debug,
"Elm: Batch-only\n"));
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmBatchOnlyMailbox,
"Can't browse mailbox on batch-only mode!"));
goto fail_1;
} else {
int r;
DPRINT(Debug,2,(&Debug,
"Elm: Normal mode\n"));
r = main_messages_menu(page,req_mfile_vector,
cur_aliaslist, check_mode);
if (req_mfile_vector) {
int i;
for (i = 0; req_mfile_vector[i]; i++) {
free(req_mfile_vector[i]);
req_mfile_vector[i] = NULL;
}
free(req_mfile_vector);
req_mfile_vector = NULL;
}
if (EOF == r)
goto fail_EOF;
if (!r)
goto fail_1;
}
if (cur_aliaslist) {
DPRINT(Debug,9, (&Debug,
"main: freeing cur_aliaslist\n"));
free_aliasview(&cur_aliaslist);
}
erase_menu_context(&page);
leave(0);
return 0;
fail_1:
fail_EOF:
if (cur_aliaslist) {
DPRINT(Debug,9, (&Debug,
"main: freeing cur_aliaslist\n"));
free_aliasview(&cur_aliaslist);
}
erase_menu_context(&page);
if(!batch_only)
Raw_OFF(1); /* Raw(OFF) and reprint error message */
#ifdef REMOTE_MBX
close_cached_connections();
#endif
return 1;
}
static void debug_screen(mailbox,LOC)
struct MailboxView *mailbox;
struct screen_parts *LOC;
{
/**** spit out all the current variable settings and the table
entries for the current 'n' items displayed. ****/
int i, j;
int LINES, COLUMNS;
int li,co;
struct menu_context *page = new_menu_context();
redraw:
if (menu_resized(page) ||
menu_need_redraw(page))
/* Nothing */;
menu_get_sizes(page, &LINES, &COLUMNS);
menu_ClearScreen(page);
menu_PutLineX(page,
0,0,CATGETS(elm_msg_cat, ElmSet,
ElmDbxCurrMsgNum,
"Current message number = %d\t\t%d message(s) total\n"),
get_current(mailbox),
get_message_count(mailbox));
{
struct folder_info * f = get_main_folder(mailbox);
if (f) {
menu_PutLineX(page,
4,0,CATGETS(elm_msg_cat, ElmSet,
ElmDbxCurrMailFile,
"\nCurrent mail file is %S.\n\r\n"),
f->cur_folder_disp);
}
}
i = menu_header_get(LOC->header_page,header_top_line); /* starting header */
menu_get_sizes(LOC->header_page, &li, &co);
if ((j = i + li-1) >= get_message_count(mailbox))
j = get_message_count(mailbox)-1;
/* FIXME -- selected */
menu_Write_to_screen(page,
CATGETS(elm_msg_cat, ElmSet, ElmDebugHeader,
"Num From Subject Lines Offset Content\n\r\n\r"));
for (;i <= j; i++) {
struct header_rec * hdr = give_header(mailbox,i);
struct string * x = NULL;
struct string * temp = NULL;
if (! hdr)
continue;
x = hdr->subject;
if (!x) {
temp = new_string2(ASCII_SET,s2us("<-- NO SUBJECT -->"));
x = temp;
}
if (hdr->from &&
hdr->from->fullname &&
string_len(hdr->from->fullname))
menu_Write_to_screen(page,
FRM("%3d %-16.16S %-35.35S %4d %8d %8d\n\r"),
i+1,
hdr->from->fullname,
x,
hdr->lines,
hdr->offset,
hdr->content_length);
else
menu_Write_to_screen(page,
FRM("%3d %-16.16s %-35.35S %4d %8d %8d\n\r"),
i+1,
hdr->from &&
hdr->from->addr &&
hdr->from->addr[0] ?
hdr->from->addr :
hdr->env_from,
x,
hdr->lines,
hdr->offset,
hdr->content_length);
if (temp)
free_string(&temp);
}
menu_PutLineX(page,
LINES-1,0,CATGETS(elm_msg_cat, ElmSet,
ElmDbxPressAnyKey,"Press any key to return."));
if (REDRAW_MARK == menu_ReadCh(page, REDRAW_MARK))
goto redraw;
erase_menu_context(&page);
return;
}
static void debug_message(current_header,current,index)
struct header_rec *current_header;
int current;
struct folder_view *index;
{
/**** Spit out the current message record. Include EVERYTHING
in the record structure. **/
time_t header_time;
int LINES, COLUMNS;
struct menu_context *page = new_menu_context();
redraw:
if (menu_resized(page) ||
menu_need_redraw(page))
/* Nothing */;
menu_get_sizes(page, &LINES, &COLUMNS);
menu_ClearScreen(page);
menu_Write_to_screen(page,
FRM("\t\t\t----- Message %d -----\n\r\n\r\n\r\n\r"),
current);
menu_Write_to_screen(page,
FRM("Lines: %-17dStatus: A C D E F N P T U V O R M P U N\n\r"),
current_header->lines);
menu_Write_to_screen(page,
FRM("Content-Length: %-16dc o e x o e r a r i l e i r s H\n\r"),
current_header->content_length);
menu_Write_to_screen(page,
FRM("Binary: %-24dt n l p r w i g g s d p m e u d\n\r"),
current_header->binary);
menu_Write_to_screen(page,
FRM("'From ' on body: %-15dn f d d m v d n i l e M p r\n\r"),
current_header->have_from);
menu_Write_to_screen(page,
FRM("\n\rOffset: %-22ld%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d%3d\n"),
current_header->offset,
(current_header->status & ACTION) != 0,
(current_header->status & CONFIDENTIAL) != 0,
(current_header->status & DELETED) != 0,
(current_header->status & EXPIRED) != 0,
(current_header->status & FORM_LETTER) != 0,
(current_header->status & NEW) != 0,
(current_header->status & PRIVATE_MAIL) != 0,
(current_header->status & TAGGED) != 0,
(current_header->status & URGENT) != 0,
(current_header->status & VISIBLE) != 0,
(current_header->status & UNREAD) != 0,
(current_header->status & REPLIED) != 0,
(current_header->status & MIME_MESSAGE) != 0,
(current_header->status & PRE_MIME_CONTENT) != 0,
(current_header->status & MIME_UNSUPPORTED) != 0,
(current_header->status & NOHDRENCODING) != 0);
menu_Write_to_screen(page,
FRM("\n\rReceived on: %s\r"),
asctime(localtime(¤t_header->received_time)));
header_time = current_header->time_sent + current_header->tz_offset;
menu_Write_to_screen(page,
FRM("\rMessage sent on: %s\r\nFrom timezone: %s (%d)\n\r"),
asctime(gmtime(&header_time)),
current_header->time_zone,
current_header->tz_offset);
menu_Write_to_screen(page,
FRM("(Env) From: %s\n\r"),
current_header->env_from);
if (current_header->from) {
int first = 1;
struct addr_item *p;
for (p = current_header->from;
p->fullname && p->addr && p->comment;
p++) {
if (first)
menu_Write_to_screen(page,
FRM( "From: "));
else
menu_Write_to_screen(page,
FRM(",\r\n "));
menu_Write_to_screen(page,
FRM("%-30S <%s>"),p->fullname,p->addr);
first = 0;
if (string_len(p->comment))
menu_Write_to_screen(page,
FRM(" (%S)"),p->comment);
}
menu_Write_to_screen(page,
FRM("\r\n"));
}
menu_Write_to_screen(page,
FRM("Subject: %S\n\rInternal Index Reference Number = %d/%d (hdr index %d)\n\r"),
current_header->subject,
index->mailbox_number,
index->index,
current_header->index_number_X);
menu_Write_to_screen(page,FRM("Thread number = %d\r\n"),
index->thread_number);
if (current_header->to) {
int first = 1;
struct addr_item *p;
for (p = current_header->to;
p->fullname && p->addr && p->comment;
p++) {
if (first)
menu_Write_to_screen(page,
FRM( "To: "));
else
menu_Write_to_screen(page,
FRM(",\r\n "));
menu_Write_to_screen(page,
FRM("%-30S <%s>"),p->fullname,p->addr);
first = 0;
if (string_len(p->comment))
menu_Write_to_screen(page,
FRM(" (%S)"),p->comment);
}
menu_Write_to_screen(page,
FRM("\r\n"));
}
if (current_header->cc) {
int first = 1;
struct addr_item *p;
for (p = current_header->cc;
p->fullname && p->addr && p->comment;
p++) {
if (first)
menu_Write_to_screen(page,
FRM( "CC: "));
else
menu_Write_to_screen(page,
FRM(",\r\n "));
menu_Write_to_screen(page,
FRM("%-30S <%s>"),p->fullname,p->addr);
first = 0;
if (string_len(p->comment))
menu_Write_to_screen(page,
FRM(" (%S)"),p->comment);
}
menu_Write_to_screen(page,
FRM("\r\n"));
}
menu_Write_to_screen(page,
FRM("Message-ID: %s\n\r"),
strlen(current_header->messageid) > 0 ?
current_header->messageid : "<none>");
menu_Write_to_screen(page,
FRM("Status: %s\n\r"),
current_header->mailx_status);
menu_Write_to_screen(page,
FRM("Content-Transfer-Encoding: %s\n\r"),
ENCODING(current_header->mime_rec.encoding));
menu_PutLineX(page,
LINES-1,0,CATGETS(elm_msg_cat, ElmSet,
ElmDbxPressAnyKey,
"Please Press any key to return."));
if (REDRAW_MARK == menu_ReadCh(page, REDRAW_MARK))
goto redraw;
erase_menu_context(&page);
return;
}
static void do_check_only(to_whom,aview)
char *to_whom[];
struct AliasView *aview;
{
struct expanded_address A;
zero_expanded_address(&A);
dump_expanded_address(3,"Check-only: checking",A);
if (to_whom) {
struct mailer_info *mailer_info = get_mailer_info();
if (argv_to_expanded(&A,to_whom,mailer_info,aview)) {
struct string * addr_string = hdr_to_expval(A);
if (addr_string) {
elm_fprintf(stdout,
CATGETS(elm_msg_cat, ElmSet, ElmExpandsTo,
"Expands to: %S\n"),
addr_string);
free_string(&addr_string);
}
}
free_expanded_address(&A);
free_mailer_info(&mailer_info);
}
}
void check_range(mc,LOC)
struct menu_common *mc;
struct screen_parts *LOC;
{
int i;
int current = mcommon_get_current(mc);
int selected = mcommon_get_selected(mc);
i = compute_visible(current, mc);
if ((current < 1) || (selected && i < 1)) {
if (mcommon_get_count(mc) > 0) {
/* We are out of range! Get to first message! */
if (selected)
current = compute_visible(1,mc);
else
current = 1;
}
else
current = 0;
}
else if ((current > mcommon_get_count(mc))
|| (selected && i > selected)) {
if (mcommon_get_count(mc) > 0) {
/* We are out of range! Get to last (visible) message! */
if (selected)
current = visible_to_index(selected,mc)+1;
else
current = mcommon_get_count(mc);
} else
current = 0;
}
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
}
/* Return key if unknown */
int motion(ch,mc, LOC, page)
int ch;
struct menu_common *mc;
struct screen_parts *LOC;
struct menu_context *page;
{
/* Consolidated the standard menu navigation and delete/tag
* commands to a function. */
int i;
int current = mcommon_get_current(mc);
switch (ch) {
case FIND_MARK:
case '/' : /* scan mbox or aliases for string */
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToScan, "No %S to scan!"),
mcommon_give_item(mc,m_items));
}
else {
int x = pattern_match(mc, page, LOC);
if (EOF == x) {
return EOF; /* ERROR */
}
if (x) {
current = mcommon_get_current(mc);
get_page(mc, LOC->header_page);
} else {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmPatternNotFound,
"pattern not found!"));
}
}
break;
case PAGEDOWN_MARK :
case RIGHT_MARK :
case '+' : {
int selected = mcommon_get_selected(mc);
int top = menu_header_get(LOC->header_page,header_top_line);
int li,co;
menu_get_sizes(LOC->header_page, &li, &co);
/* move to next page if we're not on the last */
if ((selected && (top+li < selected))
||
(!selected && (top+li < mcommon_get_count(mc)))) {
top += li;
menu_header_change(LOC->header_page, header_top_line,top);
if(move_when_paged) {
/* move to first message of new page */
if(selected)
current = visible_to_index(top+1,mc) + 1;
else
current = top+1;
mcommon_set_current(mc,current);
menu_header_change(LOC->header_page,
header_current,top);
}
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmAlreadyOnLastPage,
"Already on last page."));
}
break;
case PAGEUP_MARK :
case LEFT_MARK :
case '-' : {
int selected = mcommon_get_selected(mc);
int top = menu_header_get(LOC->header_page,header_top_line);
int li,co;
menu_get_sizes(LOC->header_page, &li, &co);
/* move to prev page if we're not on the first */
if(top > 0) {
top -= li;
if (top < 0)
top = 0;
menu_header_change(LOC->header_page, header_top_line,top);
if(move_when_paged) {
/* move to first message of new page */
if(selected)
current = visible_to_index(top + 1, mc) + 1;
else
current = top + 1;
mcommon_set_current(mc,current);
menu_header_change(LOC->header_page,
header_current,top);
}
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmAlreadyOnFirstPage,
"Already on first page."));
}
break;
case HOME_MARK:
case '=' : {
int selected = mcommon_get_selected(mc);
if (selected)
current = visible_to_index(1,mc)+1;
else
current = 1;
mcommon_set_current(mc,current);
menu_header_change(LOC->header_page, header_current,0);
get_page(mc, LOC->header_page);
}
break;
case END_MARK:
case '*' : {
int selected = mcommon_get_selected(mc);
int i;
if (selected) {
current = (visible_to_index(selected,mc)+1);
} else {
current = mcommon_get_count(mc);
}
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
}
break;
case EOF : return EOF; /* ERROR */
case ctrl('D') :
case '^' :
case 'd' :
case DELETE_MARK:
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToDelete,
"No %S to delete!"),
mcommon_give_item(mc,m_item));
} else {
if (DELETE_MARK == ch)
ch = 'd'; /* Translate */
if(ch == ctrl('D')) {
/* if current item did not become deleted,
* don't to move to the next undeleted item */
if(!meta_match(DELETED, mc, page, LOC))
break;
} else
delete_msg((ch == 'd'), mc, LOC);
/* If given '^' command (toggle delete flag)
go to next command regagdles is next command
marked for deletion or not on resolve mode.
In other words works same way than u)undelete
command works.
*/
if (resolve_mode) /* move after mail resolved */
if((i=next_message(current-1,
(ch == 'd') ? TRUE : FALSE,
mc)) != -1) {
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
}
}
break;
case 'F': { /* Actually this works only for messages
* and not aliases
*/
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToFlag,
"No %S to flag!"),
mcommon_give_item(mc,m_items));
} else
flag_message(mc, LOC->header_page);
}
break;
case 'J' :
if (current > 0) {
if((i=next_message(current-1, FALSE,
mc)) != -1) {
int j;
DPRINT(Debug,5,(&Debug,
" current %d => %d\n",
current,i+1));
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMoreItemBelow,
"No more %S below."),
mcommon_give_item(mc,m_items));
} else
lib_error(FRM("%S"),
mcommon_give_item(mc,m_no_item));
break;
next_undel_msg:
case DOWN_MARK :
case 'j' :
if (current > 0) {
if((i=next_message(current-1, TRUE,
mc)) != -1) {
DPRINT(Debug,5,(&Debug,
" current %d => %d\n",
current,i+1));
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemUndeletedBelow,
"No more undeleted %S below."),
mcommon_give_item(mc,m_items));
} else
lib_error(FRM("%S"),
mcommon_give_item(mc,m_no_item));
break;
case 'K' :
if (current > 0) {
if((i=prev_message(current-1, FALSE,
mc)) != -1) {
DPRINT(Debug,5,(&Debug,
" current %d => %d\n",
current,i+1));
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMoreItemAbove,
"No more %S above."),
mcommon_give_item(mc,m_items));
} else
lib_error(FRM("%S"),
mcommon_give_item(mc,m_no_item));
break;
case UP_MARK :
case 'k' :
if (current > 0) {
if((i=prev_message(current-1, TRUE,
mc)) != -1) {
DPRINT(Debug,5,(&Debug,
" current %d => %d\n",
current,i+1));
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
} else
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoMoreUndeletedAbove,
"No more undeleted %S above."),
mcommon_give_item(mc,m_items));
} else
lib_error(FRM("%S"),
mcommon_give_item(mc,m_no_item));
break;
case 'l' :
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmLimitDisplayBy,
"Limit displayed %S by..."),
mcommon_give_item(mc,m_items));
clear_error();
limit(mc, page,LOC);
break;
case ctrl('T') :
case 'T' :
case 't' :
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToTag,
"No %S to tag!"),
mcommon_give_item(mc,m_items));
} else if (ch == 't')
tag_message(mc, LOC->header_page);
else if (ch == 'T') {
tag_message(mc, LOC->header_page);
goto next_undel_msg;
} else
meta_match(TAGGED, mc, page, LOC);
break;
case 'u' :
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToMarkUndeleted,
"No %S to mark as undeleted!"),
mcommon_give_item(mc,m_items));
} else {
undelete_msg(mc, LOC->header_page);
if (resolve_mode) /* move after mail resolved */
if((i=next_message(current-1, FALSE, mc)) != -1) {
current = i+1;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
}
/*************************************************************************
** What we've done here is to special case the "U)ndelete" command to
** ignore whether the next message is marked for deletion or not. The
** reason is obvious upon usage - it's a real pain to undelete a series
** of messages without this quirk. Thanks to Jim Davis @ HPLabs for
** suggesting this more intuitive behaviour.
**
** The old way, for those people that might want to see what the previous
** behaviour was to call next_message with TRUE, not FALSE.
**************************************************************************/
}
break;
case ctrl('U') :
if (mcommon_get_count(mc) < 1) {
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNoItemToUndelete,
"No %S to undelete!"),
mcommon_give_item(mc,m_items));
} else
meta_match(UNDELETE, mc, page, LOC);
break;
case ctrl('L') :
menu_trigger_redraw(page);
break;
case NO_OP_COMMAND : break; /* noop for timeout loop */
default :
if (ch > '0' && ch <= '9') {
int selected = mcommon_get_selected(mc);
menu_Write_to_screen(LOC->prompt_page,
CATGETS(elm_msg_cat, ElmSet,
ElmNewCurrentItem,
"New Current %S"),
mcommon_give_item(mc,m_Item));
i = read_number(ch,
mcommon_give_item(mc,m_item),
current, page, LOC->prompt_page);
DPRINT(Debug,5,(&Debug,
" current %d => %d (?)\n",
current,i));
if( i > mcommon_get_count(mc))
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNotThatMany,
"Not that many %S."),
mcommon_give_item(mc,m_items));
else if(selected
&& mcommon_isoff_status(mc,i-1,
status_basic,VISIBLE))
lib_error(CATGETS(elm_msg_cat, ElmSet,
ElmNotInLimitedDisplay,
"%S not in limited display."),
mcommon_give_item(mc,m_Item));
else {
current = i;
mcommon_set_current(mc,current);
copy_current(mc,LOC->header_page);
get_page(mc, LOC->header_page);
}
} else {
return ch; /* UNKNOWN command */
}
break;
}
return 0; /* COmmand OK */
}
/*
* Local Variables:
* mode:c
* c-basic-offset:4
* buffer-file-coding-system: iso-8859-1
* End:
*/
syntax highlighted by Code2HTML, v. 0.9.1