/*
 *	Copyright (C) 1984, 1985  SRI International
 *	Copyright (C) 1989, 1990  TGV, Incorporated
 *
 *	Message listing commands
 *
 */
#include <stdio.h>
#include <file.h>
#include "vax-mm.h"

extern char *strchr();

static Get_Options_And_Msg_Sequence(), List();
/*
 *	Options
 */
static int Headers_Only;
static int Separate_Pages;
static struct {
	int current_entries;
	int maximum_entries;
	struct tbluk_keyword keywords[2];
	} Options = {
	2,
	2,
/* 0 */{{0,		"headers-only",		(int)&Headers_Only},
/* 1 */ {0,		"separate-pages",	(int)&Separate_Pages}}};


/*
 *	List messages to the lineprinter
 */
CMD_List()
{
	int fd;
	FILE *f;

	/*
	 *	Noise
	 */
	if (Read_Mode)
		Noise("on listing device");
	else
		Noise("options");
	/*
	 *	Get options and Message sequence
	 */
	Get_Options_And_Msg_Sequence();
	/*
	 *	Do confirmation if necessary
	 */
	if (!List_Confirm_Suppress) {
		static struct {
			int current_entries;
			int maximum_entries;
			struct tbluk_keyword keywords[2];
			} Table = {
			2,
			2,
			{{0,	"no",		0},
			 {0,	"yes",		1}}};
		static struct comnd_function yesno =
			{COMND_KEYWORD,
			 COMND_HELP_VALID|COMND_SUPPRESS_DEFAULT_HELP,
			 0,
			 (int)&Table,
			 "YES or NO"};
		int Status;
		struct tbluk_keyword *t;

		Command_State.prompt =
			"Do you really want to output to the lineprinter? ";
		while(1) {
			COMMAND_PARSE_INIT(&Command_State);
			Status = COMND(&Command_State,&yesno,&t,0);
			if (Status >= 0) break;
		}
		Confirm();
		if (t->user_data == 0) return;
	}
	/*
	 *	Do the listing
	 */
	{
		if (Spool_To_List_Device)
			/* creat() with "SPOOL" bit on */
			fd = creat(List_Device,0777,"rfm=var","rat=cr","fop=spl,dlt");
		else
			/* creat() with "SPOOL" bit off */
			fd = creat(List_Device,0777,"rfm=var","rat=cr");
		if (fd < 0) {
			printf("Couldn't create %s\n",List_Device);
			return;
		}
		f = fdopen(fd,"w");
		List(f);
		fclose(f);
	}
}



/*
 *	List messages to a file
 */
CMD_File_List()
{
	static struct comnd_function filename =
		{COMND_OUTPUT_FILE};
	int fd;
	FILE *f;
	int Status;
	int i;
	char File_Name[128];

	/*
	 *	Noise
	 */
	Noise("into file");
	/*
	 *	Get the filename
	 */
	Command_State.gtjfn = 0;
	Status = comnd_jsys(&Command_State,&filename,&i,0);
	if (Status < 0) {
		printf("\n***PARSE ERROR***\n");
		return;
	}
	if (local_jfns_jsys(File_Name,i) < 0) return;
	tops_free_jfn(i);	/* TEMP */
	/*
	 *	Get the options and message sequence
	 */
	Get_Options_And_Msg_Sequence();
	/*
	 *	Do the listing
	 */
	fd = Xcreat(File_Name,Mail_File_Mode,"txt");
	if (fd < 0) {
		printf("Couldn't create %s\n",File_Name);
		return;
	}
	f = fdopen(fd,"w");
	List(f);
	fclose(f);
}


/*
 *	List messages to a file, appending
 */
CMD_Append()
{
	static struct comnd_function filename =
		{COMND_INPUT_FILE};
	FILE *f;
	int Status;
	int i;
	char File_Name[128], tmp[256];
    	extern FILE *Xfopen();

	/*
	 *	Noise
	 */
	Noise("into file");
	/*
	 *	Get the filename
	 */
	Command_State.gtjfn = 0;
	Status = comnd_jsys(&Command_State,&filename,&i,0);
	if (Status < 0) {
		printf("\n***PARSE ERROR***\n");
		return;
	}
	if (local_jfns_jsys(File_Name,i) < 0) return;
	tops_free_jfn(i);	/* TEMP */
	/*
	 *	Get the options and message sequence
	 */
	Get_Options_And_Msg_Sequence();
	/*
	 *	Append to the listing file
	 */
    	f = Xfopen(File_Name, "a");
	if (f == 0) {
		sprintf(tmp, "Append: couldn't open %s\n",File_Name);
    	    	perror(tmp);
		return;
	}
	List(f);
	fclose(f);
}


/*
 *	Get options and message sequence
 */
static Get_Options_And_Msg_Sequence()
{
	static struct comnd_function f =
		{COMND_SWITCH,
		 COMND_HELP_VALID,
		 0,
		 (int)&Options,
		 "message sequence\n  or optional LIST switch,"};
	struct tbluk_keyword *t;
	int Status;

	/*
	 *	Set defaults
	 */
	Separate_Pages = List_On_Separate_Pages;
	Headers_Only = 0;
	/*
	 *	If in Read mode, just confirm
	 */
	if (Read_Mode) {
		Confirm();
		return;
	}
	/*
	 *	Try to get option
	 */
	Command_State.flags &= ~COMND_HANDLE_ERRORS;
	Status = comnd_jsys(&Command_State,&f,&t,0);
	Command_State.flags |=	COMND_HANDLE_ERRORS;
	/*
	 *	If OK, set that flag ON
	 */
	if (Status >= 0)
		*((int *)t->user_data) = 1;
	/*
	 *	Not Ok: try to parse the message list
	 */
	Parse_Message_List("CURRENT");
	/*
	 *	Confirm
	 */
	Confirm();
}


/*
 *	Generate the list
 */
static List(Stream)
FILE *Stream;
{
	register struct Msg *Msg;
	int Message, i, len;
	int Number_Of_Messages = 0;
	char Buffer[128], *cp, *cp1;

	/*
	 *	If read mode, just list the message all by itself
	 */
	if (Read_Mode) {
		Msg = &Messages[Current_Message-1];
		fprintf(Stream,"Message %d -- ************************\n",
							Current_Message);
		fflush(Stream);
		cp = MESSAGE_HEADER(Current_Message);
		i = Msg->Real_Size;
		while (i > 0) {
			cp1 = strchr(cp, '\n');
			if (cp == 0) len = i;
			else len = (cp1 - cp) + 1;
			write(fileno(Stream), cp, len);
			cp += len;
			i -= len;
		}
		fprintf(Stream,"\n");
		if (Separate_Pages) fprintf(Stream,"\n");
		return;
	}
	/*
	 *	Generate the listing header
	 */
	Get_DayTime(Buffer);
	fprintf(Stream,"-- Message from file: %s --\n",Current_Mail_File);
	fprintf(Stream,"   %s %s\n\n",Buffer,Timezone_String(0));
	/*
	 *	Check the number of messages and generate the message headers
	 */
	while(1) {
		Message = Next_Message(0);
		if (Message <= 0) break;
		Number_Of_Messages++;
		Current_Message = Message;
		if (List_Include_Headers || Headers_Only)
			Print_Header(Stream,&Messages[Message-1],Message);
	}
	fprintf(Stream,"\n");
	/*
	 *	List the messages
	 */
	Re_Init_Next_Message();
	while(1) {
		Message = Next_Message(1);
		if (Message <= 0) break;
		if (Separate_Pages && !Headers_Only) fprintf(Stream,"\n");
		Number_Of_Messages++;
		Current_Message = Message;
		Msg = &Messages[Message-1];
		if (!Headers_Only) {
			fprintf(Stream,"Message %d -- ************************\n",Message);
			fflush(Stream);
			cp = MESSAGE_HEADER(Current_Message);
			i = Msg->Real_Size;
			while (i > 0) {
				cp1 = strchr(cp, '\n');
				if (cp == 0) len = i;
				else len = (cp1 - cp) + 1;
				write(fileno(Stream), cp, len);
				cp += len;
				i -= len;
			}
			fprintf(Stream,"\n");
		}
	}
	/*
	 *	Done
	 */
	if (Number_Of_Messages) printf("\n");
}
