/*  Insert_returns (C) Copyright 1987 by Russell Wallace. This program is in
	the public domain and may be freely distributed. It may not be used
	commercially without the author's permission. If you find this program
	useful,please send a small donation to the author at:
		24 Lower Georges St.
		Dunlaoghaire
		Co. Dublin
		Ireland
	to help finance further software development. Contributions in kind i.e.
	Amiga disks welcome. If you wish to discuss any aspect of the Amiga or
	computers in general,write or phone 807094.

	Returns_insert takes a file produced on a screen-oriented text editor
	e.g. Notepad and inserts carriage returns at appropriate intervals to
	make it usable with a line-oriented editor e.g. Ed. Arguments are as
	follows:
		insert_returns [>outputfile] inputfile SCREENWIDTH
	Output may be sent to a file; default is to the screen. SCREENWIDTH is a
	number indicating what screen width you want the output formatted for.
	Remember that in the Amiga's "80-column" screen,a few columns are taken
	up by window borders etc.
	Existing carriage returns are retained as paragraph markers. New
	carriage returns are inserted to avoid breaking up words; this program
	could therefore be used to format text files for that purpose.
	If you give copies of this program to anyone,please distribute source
	code with object code to allow examination of programming techniques;
	the Amiga programming environment is so complex that source code is
	very valuable as an information source */

#include <libraries/dos.h>
#include <exec/types.h>

#define MAXBUFFER 256L		/* length of I/O buffers */
#define MAXWORD 64L			/* length of word buffer */
#define EOF '\0'

char *inbuffer,*outbuffer;	/* buffers for input & output */
char wordbuffer[MAXWORD];	/* buffer to store word as read in */

char charin (fp)			/* input a character */
struct FileInfoBlock *fp;
{
	static LONG inpoint=MAXBUFFER-1;
	static LONG maxin  =MAXBUFFER-1;
	LONG Read ();
	char ch;
	if (++inpoint>=maxin)
	{
		maxin=Read (fp,inbuffer,MAXBUFFER);
		inpoint=0;
	}
	if (maxin==0)
		return (EOF);
	return (inbuffer[inpoint]);
}

charout (ch,fp)				/* output a character */
char ch;
struct FileInfoBlock *fp;
{
	static LONG outpoint=0;
	LONG Write ();
	if ((++outpoint>=MAXBUFFER)||(ch==EOF))
	{
		Write (fp,outbuffer,outpoint+(ch!=EOF));
		outpoint=0;
	}
	outbuffer[outpoint]=ch;
}

main (argc,argv)
int argc;		/* number of arguments input by user */
char *argv[];	/* pointers to each argument */
{
	int i,letter,screenwidth;
	int column=0;
	struct FileInfoBlock *fp;
	struct FileInfoBlock *stdout;
	struct FileInfoBlock *Open ();
	struct FileInfoBlock *Output ();
	char ch,oldch,charin (),*AllocMem ();
	stdout=Output ();
	inbuffer=AllocMem (MAXBUFFER,0L);
	outbuffer=AllocMem (MAXBUFFER,0L);
	if ((argc<3)||(*argv[1]=='?'))	/* If no arguments or ?,give help */
	{
		Write (stdout,"Usage: insert_returns [>outputfile] inputfile SCREENWIDTH\n",58L);
		exit (10);
	}
	if ((fp=Open (argv[1],MODE_OLDFILE))==0)	/* Can't open file */
	{
		Write (stdout,"Couldn't open file for insert_returns\n",38L);
		exit (10);
	}
	if ((screenwidth=atoi (argv[2]))<5)
	{
		Write (stdout,"Please give a reasonable SCREENWIDTH value\n",43L);
		exit (10);
	}
Loop:				/* come back to here as long as not EOF */
	letter=0;		/* Start at first letter of word */
	for (;;)
	{
		if ((ch=charin (fp))==EOF)
			break;
		wordbuffer[letter++]=ch;
		if (ch=='\n' || ch==' ' || letter==MAXWORD)
			break;
	}
	if (letter)		/* if there's any word to output */
	{
		if (letter+column>=screenwidth)
		{
			charout ('\n',stdout);	/* insert RETURN where necessary */
			column=0;
		}
		for (i=0;i<letter;i++)
		{
			charout (wordbuffer[i],stdout);
			column++;
			if (wordbuffer[i]=='\n')
				column=0;	/* if output RETURN,back to column zero */
		}
	}
	if (ch)			/* if not EOF i.e. zero */
		goto Loop;	/* You don't like GOTO? Well,up yours! */
	charout (EOF,stdout);	/* EOF character at end of file */
	Close (fp);
	FreeMem (inbuffer,MAXBUFFER);
	FreeMem (outbuffer,MAXBUFFER);
}
