[comp.sources.amiga] v89i058: shell - csh-like command interpreter v3.02a, Part01/03

page@swan.ulowell.edu (Bob Page) (03/16/89)

Submitted-by: PERUGIA@ICNUCEVM.BITNET (Cesare Dieni)
Posting-number: Volume 89, Issue 58
Archive-name: unix/shell302a.1

New to 3.02A:

- New commands: fornum, forline, strleft, strright, strmid, strlen, exec.
- Improved commands: foreach, pri.
- New system variable _clinumber.
- You can now split long lines in source files (see source for details).
- window -q now lists also position of screens/windows, not only dimension.
- Since strings are handled directly from Shell with new commands,
  rpn is now used only for calculations; string commands are gone.
  However, now RPN is really usable.
- Changed rawgets() to fix some problems with function keys, multi-line
  editing and window resizing; also, fixed bug with ^E.
- cat now warns you if it can't find any file matching your pattern.
- Now uses DOS packets to get ptr to CLI window; this fixes a bug that
  caused problems if Shell was run on unactive windows.
- Fixed minor bugs (htype printed some more ASCII bytes, some commands
  returned random values, history didn't print CR's).

#	This is a shell archive.
#	Remove everything above and including the cut line.
#	Then run the rest of the file through sh.
#----cut here-----cut here-----cut here-----cut here----#
#!/bin/sh
# shar:    Shell Archiver
#	Run the following text with /bin/sh to create:
#	comm3.c
#	globals.c
#	main.c
#	makefile
#	rawconsole.c
#	run.c
#	set.c
#	shell.h
#	shellfunctions.h
# This archive created: Wed Mar 15 14:13:36 1989
cat << \SHAR_EOF > comm3.c
/*
 * COMM3.C
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

do_assign() {
switch(ac) {
	case 1:  assignlist();
		 break;
	case 2:  doassign(av[1], NULL);
		 break;
	case 3:  doassign(av[1], av[2]);
		 break;
	default: ierror(NULL, 500);
		 break;
	}
return 0;
}

char *assign_errors[4]={
	"",
	"Name %s is not valid\n",
	"Weird error\n",
	"Can't cancel %s\n"
	};

doassign(log, phy)
char *log, *phy;
{
int last=strlen(log) - 1;

if (log[last] != ':') fprintf(stderr, "Bad name %s\n", log);
else {
	log[last] = 0;
	fprintf(stderr,assign_errors[Assign(log, phy)],log);
	}
}

assignlist()
{
struct DirectoryEntry *de_head=NULL, *de;
char buf[256];
BPTR lock;
int ctr=0;

AddDADevs(&de_head, DLF_DEVICES | DLF_VOLUMES | DLF_DIRS);
printf("Devices:\n");
for (de=de_head; de && de->de_Type==DLX_DEVICE; de=de->de_Next) {
	printf("%-8s",de->de_Name);
	if (ctr++ == 5) { ctr=0; printf("\n"); }
	}
printf("\n\nVolumes:\n");
for (	;
	de && (de->de_Type==DLX_VOLUME || de->de_Type==DLX_UNMOUNTED);
	de=de->de_Next
	)
	printf( "%-16s %s\n",
		de->de_Name,
		de->de_Type == DLX_VOLUME ? "[Mounted]" : ""
		);
printf("\nDirectories:\n");
for (; de && de->de_Type==DLX_ASSIGN; de=de->de_Next) {
	if (lock=Lock(de->de_Name, ACCESS_READ)) {
		PathName(lock, buf, 256L);
		UnLock(lock);
		}
	else
		strcpy(buf,"Unexisting lock");
	printf("%-20s%s\n",de->de_Name,buf);
	}
FreeDAList(&de_head);
}

do_join()
{
BPTR sou, dest;
char *buffer;
unsigned int i;
long n;
char *namedest=av[--ac];

get_opt("r", &i);
if (options==0 && exists(namedest)) { ierror(namedest,203); return 20; }
if ( (buffer=malloc(8192)) == NULL ) { ierror(NULL,103); return 20; }
if ( (dest=Open(namedest, MODE_NEWFILE)) == NULL )
	{ pError(namedest); goto fail1; }
for (i=1; i<ac; i++) {
	if ( (sou=Open(av[i], MODE_OLDFILE)) == NULL ) pError(av[i]);
	else
		while( (n=Read(sou, buffer, 8192L)) > 0 )
			if (Write(dest, buffer, n) != n)
				{ pError(namedest); Close(sou); goto fail2; }
	Close(sou);
	}
fail2:
	Close(dest);
fail1:
	free(buffer);
	return 0;
}

#define BUFDIM 512L
#define MAXSTR 256

int minstr;

strings_in_file(s)
char *s;
{
char c;
char readbuf[BUFDIM+1], strbuf[MAXSTR+1];
register unsigned int i, strctr=0;
BPTR fh;
int out, n;

if ( fh=Open(s, MODE_OLDFILE) ) {
	fprintf(stderr, "Strings in %s (len>=%d):\n",s,minstr);
	while ( (n=(int)Read(fh, readbuf, BUFDIM)) > 0 && !CHECKBREAK() )
	    for (i=0; i<n; i++) {
		c=readbuf[i];
		if (c<0x20 || c>0x7f) {
			out=(strctr>=minstr);
			if (!out) strctr=0;
			}
		else {
			strbuf[strctr++]=c;
			out=(strctr>=BUFDIM);
			}
		if (out) {
			strbuf[strctr]='\0';
			puts(strbuf);
			strctr=0;
			}
		}
	Close(fh);
	}
else pError(s);
}

do_strings()
{
minstr=myatoi(av[--ac],1,255);
all_args("r", strings_in_file, 0);
return 0;
}

BPTR myfile[MAXMYFILES];

do_open()
{
long mode;
unsigned int n;

switch (av[2][0]) {
	case 'r': mode=MODE_OLDFILE; break;
	case 'w': mode=MODE_NEWFILE; break;
	default : ierror(NULL,500); return;
	}
Errno=0;
n=(unsigned int)myatoi(av[3],0,MAXMYFILES); if (Errno) return 20;
myfile[n]=Open(av[1],mode);
return (myfile[n]==NULL);
}

do_close()
{
register unsigned int i;
int n;

for (i=1; i<ac; i++) {
	Errno=0;
	n=myatoi(av[i],0,MAXMYFILES); if (Errno) return 20;
	myclose(n);
	}
return 0;
}

myclose(n)
{
if (myfile[n]) { Close(myfile[n]); myfile[n]=NULL; }
}

do_fileslist()
{
register unsigned short i;
int flag=0;

printf("Open files:");
for (i=0; i<MAXMYFILES; i++)
	if (myfile[i]) { printf(" %d",i); flag=1; }
if (!flag) printf(" None!");
printf("\n");
return 0;
}

BPTR extOpen(name,mode)
char *name;
long mode;
{
if (name[0]=='.') return myfile[atoi(name+1)];
return Open(name,mode);
}

extClose(fh)
BPTR fh;
{
register unsigned short i;

for (i=0; i<MAXMYFILES; i++)
	if (myfile[i]==fh) return;
Close(fh);
}

do_resident(avline)
char *avline;
{
unsigned int i;
BPTR seg;
struct ResidentPrgNode *p;
char *args;

get_opt("ar", &i);
switch (options) {
    case 0:
	ObtainSemaphore (& (ArpBase->ResPrgProtection) );
	if (p=ArpBase->ResidentPrgList) {
		printf("Name             Users\n");
		for (; p; p=p->rpn_Next)
			printf("%-16s %-3ld\n",p->rpn_Name,p->rpn_Usage);
		}
	else printf("No resident program(s)\n");
	ReleaseSemaphore(& (ArpBase->ResPrgProtection) );
	break;
    case 1:
	for (; i<ac; i++)
		if ( (seg=(BPTR)LoadPrg(av[i])) && AddResidentPrg(seg,av[i]) )
			printf("OK! %s is now resident\n", BaseName(av[i]));
		else pError(av[i]);
	break;
    case 2:
	for (; i<ac; i++)
		if (RemResidentPrg(av[i])) ierror(av[i],202);
		else printf("Removed %s\n",av[i]);
	break;
    default:
	ierror(NULL,500);
	break;
    }
return 0;
}

struct ProcessControlBlock pcb={
	4000,		/* pcb_StackSize	*/
	0,		/* pcb_Pri		*/
	};
/* remaining field are NULL */
	
do_truerun(avline, backflag)
char *avline;
{
char name[200];
char *FindIt();

if (backflag) {
	pcb.pcb_Control=NULL;
	pcb.pcb_Input=pcb.p_Output=Open("NIL:",MODE_OLDFILE);
	}
else {
	pcb.pcb_Control=PRB_SAVEIO;
	pcb.pcb_Input=pcb.p_Output =NULL;
	}
if (FindIt(av[1], "", name))
	ASyncRun(name,next_word(next_word(avline)),&pcb);
else
	ierror(av[1],205);
return 0;
}

int exists(name)
char *name;
{
BPTR lock;

if (lock=Lock(name,ACCESS_READ)) {
	UnLock(lock);
	return 1;
	}
return 0;
}

do_aset()
{
Setenv(av[1],av[2]);
return 0;
}

#define HTYPELINE 16L

htype_a_file(s)
char *s;
{
BPTR fh;
long n, filesize=0;
char buf[HTYPELINE+1];
register unsigned int i;

if ( (fh=Open(s,MODE_OLDFILE))==NULL ) { pError(s); return 20; }
while ( (n=Read(fh,buf,HTYPELINE))>0 && !dobreak()) {
	printf("%06lx: ",filesize);
	filesize+=n;
	for (i=0; i<n; i++) {
		printf( (i&3) ? "%02x" : " %02x",(int)(unsigned char)buf[i]);
		if (buf[i]<=0x20) buf[i]='.';
		}
	for ( ; i<HTYPELINE; i++) {
		printf( (i&3) ? "  " : "   ");
		buf[i]=' ';
		}
	buf[i]=0;
	printf("    %s\n",buf);
	}
Close(fh);
return 0;
}

do_htype()
{
all_args("", htype_a_file, 0);
return 0;
}

do_stack()
{
long n;

if (ac>1) {
	Errno=0;
	n=Atol(av[1]);
	if (!Errno) Mycli->cli_DefaultStack=(long)(n >> 2L);
	}
else printf("current stack size is %ld bytes\n",
				(long)Mycli->cli_DefaultStack << 2L);
return 0;
}

do_fault()
{
struct PERROR *p;
register unsigned int i;
int n;

for (i=1; i<ac; i++) {
	n=myatoi(av[i],0,32767);
	if (!Errno) {
		for (p=Perror; p->errnum && p->errnum!=n; p++);
		if (p->errnum)
			printf("Fault %d: %s\n",n,p->errstr);
		else
			printf("Fault %d not recognized\n",n);
		}
	}
return 0;
}

struct rpncommand {
	char *str;
	int parsin, parsout;
	};

struct rpncommand rpn[]={
	"+",	2,	1,
	"-",	2,	1,
	"*",	2,	1,
	"/",	2,	1,
	"%",	2,	1,
	"&",	2,	1,
	"|",	2,	1,
	"~",	1,	1,
	">",	2,	1,
	"<",	2,	1,
	"==",	2,	1,
	"!",	1,	1,
	"DUP",	1,	2,
	"DROP",	1,	0,
	"SWAP",	2,	2,
	"HELP",	0,	0,
	NULL,	0,	1,	/* this looks for a number */
};

do_rpn(garbage,ifflag) /* ifflag!=0 if called from if */
char *garbage;
{
register long n0, n1;
long t;
unsigned int i, j;
int sp=0;
long stack[100];
struct rpncommand *temp;

i=1;
if (ifflag) get_opt("rn",&i);
for (; i<ac; i++) {
	for (j=0; rpn[j].str && Strcmp(rpn[j].str,av[i]); j++) ;
	n0=stack[sp-1];
	n1=stack[sp-2];
	sp -= (rpn[j].parsin);
	if (sp<0) { fprintf(stderr, "RPN: Empty stack\n"); return 1; }
	switch (j) {
	  case 0:	n0 += n1;		break;
	  case 1:	n0 = n1-n0;		break;
	  case 2:	n0 *= n1;		break;
	  case 3:	n0 = n1/n0;		break;
	  case 4:	n0 = n1%n0;		break;
	  case 5:	n0 &= n1;		break;
	  case 6:	n0 |= n1;		break;
	  case 7:	n0 =  ~n0;		break;
	  case 8:	n0 = (n1 > n0);		break;
	  case 9:	n0 = (n1 < n0);		break;
	  case 10:	n0 = (n0 == n1);	break;
	  case 11:	n0 = !n0;		break;
	  case 12:	n1=n0;			break;
	  case 13:	t=n0; n0=n1; n1=t;	break;
	  case 14:				break;
	  case 15:	printf("In Commands Out\n");
			for (temp=rpn; temp->str; temp++)
			    printf(" %d %-10s%d\n",
				temp->parsin,temp->str,temp->parsout);
			break;
	  default:	Errno=0;
			n0=Atol(av[i]);
			if (Errno) {
				fprintf(stderr, "Bad RPN cmd: %s\n",av[i]);
				return 20;
				}
			break;
	  }
	stack[sp]=n0;
	stack[sp+1]=n1;
	sp += rpn[j].parsout;
	}
if (ifflag) return (int)(stack[sp-1]);	/* called from if: return top value */
for (i=sp-1;(int)i>=0;i--) printf("%ld\n", stack[i]); /* else print stack */
return 0;
}

do_path()
{
union {	long *lp; long ll; } l;
BPTR lock;
char buf[256];

puts("Current dir");
l.lp = (long *) Mycli->cli_CommandDir;
while (l.ll) {
	l.ll <<= 2;
	PathName(l.lp[1], buf, 256L);
	puts(buf);
	l.ll = *l.lp;
	}
puts("C:");
return 0;
}

do_pri()
{
int t, pri;
struct Process *proc;

t=myatoi(av[1],0,20); if (Errno) return 20;
pri=myatoi(av[2],-128,127); if (Errno) return 20;
Forbid();
proc=(t==0 ? Myprocess : FindCLI((long)t));
if (proc==NULL) fprintf(stderr, "process not found\n");
	else SetTaskPri(proc, (long)pri);
Permit();
return 0;
}

do_strleft()
{
char buf[256];
int n;

strcpy(buf,av[2]);
n=myatoi(av[3],1,strlen(buf)); if (Errno) return 20;
buf[n]='\0';
set_var(LEVEL_SET, av[1], buf);
return 0;
}

do_strright()
{
char buf[256];
int n;

strcpy(buf, av[2]);
n=myatoi(av[3],1,strlen(buf)); if (Errno) return 20;
set_var(LEVEL_SET, av[1], buf+strlen(buf)-n);
return 0;
}

do_strmid()
{
char buf[256];
int n1, n2;

strcpy(buf, av[2]);
n1=myatoi(av[3],1,strlen(buf))-1; if (Errno) return 20;
if (ac>4) {
	n2=myatoi(av[4],1,strlen(buf)-n1);
	if (Errno) return 20;
	buf[n1+n2]='\0';
	}
set_var(LEVEL_SET, av[1], buf+n1);
return 0;
}

do_strlen()
{
char buf[16];

sprintf(buf,"%d",strlen(av[2]));
set_var(LEVEL_SET, av[1], buf);
return 0;
}

myatoi(s,min,max)
char *s;
{
long n;

Errno=0;
n=Atol(s);
if (Errno==ERRBADINT) ierror(s,511);
	else if (n<min || n>max) {
		Errno=ERRBADINT;
		printf("%s not in (%d,%d)\n",s,min,max);
		}
return (int)n;
}
SHAR_EOF
cat << \SHAR_EOF > globals.c

/*
 * GLOBALS.C
 *
 * (c)1986 Matthew Dillon     9 October 1986
 *
 * Version 2.07M by Steve Drew 10-Sep-87
 *
 *    Most global variables.
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

char *v_titlebar="_titlebar";	/* Window title				*/
char *v_prompt	="_prompt";	/* your prompt (ascii command)		*/
char *v_hist	="_history";	/* set history depth (value)		*/
char *v_histnum	="_histnum";	/* set history numbering var		*/
char *v_debug	="_debug";	/* set debug mode			*/
char *v_verbose	="_verbose";	/* set verbose for source files		*/
char *v_stat	="_maxerr";	/* worst return value to date		*/
char *v_lasterr	="_lasterr";	/* return value from last comm.		*/
char *v_cwd	="_cwd";	/* current directory			*/
char *v_except	="_except";	/* "nnn;command"			*/
char *v_passed	="_passed";	/* passed arguments to source file	*/
char *v_path	="_path";	/* search path for external commands	*/
char *v_gotofwd	="_gtf";	/* set name for fwd goto name		*/

struct HIST *H_head, *H_tail;	/* HISTORY lists */

struct PERROR Perror[]= {	/* error code->string */
	103,	"Insufficient free storage",
	105,	"Task table full",
	120,	"Argument line invalid or too long",
	121,	"File is not an object module",
	122,	"Invalid resident library during load",
	201,	"No default directory",
	202,	"Object in use",
	203,	"Object already exists",
	204,	"Directory not found",
	205,	"Object not found",
	206,	"Bad stream name",
	207,	"Object too large",
	209,	"Action not known",
	210,	"Invalid stream component name",
	211,	"Invalid object lock",
	212,	"Object not of required type",
	213,	"Disk not validated",
	214,	"Disk write protected",
	215,	"Rename across devices",
	216,	"Directory not empty",
	217,	"Too many levels",
	218,	"Device not mounted",
	219,	"Seek error",
	220,	"Comment too long",
	221,	"Disk full",
	222,	"File delete protected",
	223,	"File write protected",
	224,	"File read protected",
	225,	"Not a DOS disk",
	226,	"No disk",

 /* custom error messages */

	500,	"Bad arguments",
	501,	"Label not found",
	502,	"Must be within source file",
	503,	"Syntax Error",
	504,	"Redirection error",
	505,	"Pipe error",
	506,	"Too many arguments",
	507,	"Destination not a directory",
	508,	"Cannot mv a filesystem",
	509,	"Error in command name",
	510,	"Bad drive name",
	511,	"Illegal number",
	0,	NULL
};

char *av[MAXAV];		/* Internal argument list		*/
long Src_base[MAXSRC];		/* file pointers for source files	*/
long Src_pos[MAXSRC];		/* seek position storage for same	*/
char If_base[MAXIF];		/* If/Else stack for conditionals	*/
int H_len, H_tail_base;		/* History associated stuff		*/
int H_stack;			/* AddHistory disable stack		*/
int E_stack;			/* Exception disable stack		*/
int Src_stack, If_stack;	/* Stack Indexes			*/
int forward_goto;		/* Flag for searching for foward lables	*/
int ac;				/* Internal argc			*/
int debug;			/* Debug mode				*/
int disable;			/* Disable com. execution (conditionals)*/
int Verbose;			/* Verbose mode for source files	*/
int Lastresult;			/* Last return code			*/
int Exec_abortline;		/* flag to abort rest of line		*/
int Quit;			/* Quit flag				*/
long Cout, Cin;			/* Current input and output file handles*/
long Cout_append;		/* append flag for Cout			*/
char *Cin_name, *Cout_name;	/* redirection input/output name or NULL*/
char *Pipe1, *Pipe2;		/* the two pipe temp. files		*/
struct Process *Myprocess;
struct CommandLineInterface *Mycli;
int S_histlen = 20;		/* Max # history entries		*/
unsigned int options;
SHAR_EOF
cat << \SHAR_EOF > main.c
/*
 * MAIN.C
 *
 * Matthew Dillon, 24 Feb 1986
 * (c)1986 Matthew Dillon     9 October 1986
 *
 * Version 2.07M by Steve Drew 10-Sep-87
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

char *shellctr="CshCounter";

extern char *v_titlebar, *v_prompt, *v_hist, *v_lasterr, *v_path;

int aux; /* for use with aux: driver */
char *oldtitle;
char trueprompt[100];
char Inline[260];
struct IntuitionBase *IntuitionBase;
struct Window *w;
struct ArpBase *ArpBase;

main(argc, argv)
register char *argv[];
{
#if RAW_CONSOLE
	char *rawgets();
#endif

register unsigned int i;
extern int Enable_Abort;
char buf[10];

ArpBase=(struct ArpBase *)OpenLibrary("arp.library",34L);
if (ArpBase==NULL) { printf("No arp library\n"); exit(0); }

Forbid();
i=Errno=0;
if (Getenv(shellctr,buf,10L)) {
	i=(int)(long)Atol(buf);
	if (Errno) i=0;
	}
sprintf(buf,"%d",i+1);
Setenv(shellctr,buf);
Permit();

IntuitionBase=(struct IntuitionBase *)ArpBase->IntuiBase;

init();

sprintf(buf,"%ld",Myprocess->pr_TaskNum);
set_var(LEVEL_SET, "_clinumber", buf);

oldtitle=(char *)(w->Title);

set_var(LEVEL_SET, v_titlebar, "CShell V3.02A");
set_var(LEVEL_SET, v_prompt,
	(IsInteractive(Input())) ? "\23337m%p> \2330m" : "");
set_var(LEVEL_SET, v_hist, "20");
set_var(LEVEL_SET, v_lasterr, "0");
set_var(LEVEL_SET, v_path, "RAM:,RAM:c/,df0:c/,df1:c/,sys:system/");
set_var(LEVEL_SET, "_insert", "1");
set_var(LEVEL_SET, "f1", "cdir df0:\15");
set_var(LEVEL_SET, "F1", "cdir df1:\15");
set_var(LEVEL_SET, "f3", "cdir RAM:\15");
set_var(LEVEL_SET, "F3", "cdir vd0:\15");
set_var(LEVEL_SET, "f4", "cd df0:\15");
set_var(LEVEL_SET, "F4", "cd df1:\15");
set_var(LEVEL_SET, "f5", "cls; ls\15");
set_var(LEVEL_SET, "F5", "cdir ");
set_var(LEVEL_SET, "f6", "lc\15");
set_var(LEVEL_SET, "f7", "info\15");
set_var(LEVEL_SET, "F7", "assign \15");
set_var(LEVEL_SET, "f8", "window -lf\15");
set_var(LEVEL_SET, "F8", "window -sb\15");
set_var(LEVEL_SET, "f10", "cls\15");
set_var(LEVEL_SET, "F10", "exit\15");
set_var(LEVEL_ALIAS, "cls", "echo -n ^l");
set_var(LEVEL_ALIAS, "lc", "ls -s");
set_var(LEVEL_ALIAS, "kr", "rm -r RAM:* >NIL:");
set_var(LEVEL_ALIAS, "cdir", "%q cd $q; cls; dir");
set_var(LEVEL_ALIAS, "exit", "endcli;quit");
set_var(LEVEL_ALIAS, "lp", "cat >PRT:");
seterr();
do_pwd(NULL); /* set $_cwd */
Enable_Abort = 0;
for (i = 1; i < argc; ++i) {
	if (!strcmp(argv[i],"-c")) {
		Inline[0] = ' ';
		Inline[1] = '\0';
		while (++i < argc)
			{ strcat(Inline,argv[i]); strcat(Inline," "); }
		exec_command(Inline);
		main_exit(Lastresult);
		}
	if (!strcmp(argv[i],"-a")) { aux = 1; continue; }
	sprintf (Inline, "source %s",argv[i]);
	av[1] = argv[i];
	do_source (Inline);
	}
for (;;) {
   if (breakcheck())
	while (WaitForChar(Input(), 100L) || stdin->_bp < stdin->_bend)
		gets(Inline);
   clearerr(stdin);  /* prevent acidental quit */
#if RAW_CONSOLE
   if (Quit || !rawgets(Inline, disable ? "_ " : trueprompt)) main_exit(0);
#else
   printf("%s", disable ? "_ " : trueprompt);
   fflush(stdout);
   if (Quit || !gets(Inline)) main_exit(0);
#endif
   breakreset();
   if (*Inline) exec_command(Inline);
   }
}

main_exit(n)
{
register unsigned short i;
char buf[10];

Getenv(shellctr,buf,10L);
i=(int)Atol(buf);
sprintf(buf,"%d",i-1);
Setenv(shellctr,buf);
SetWindowTitles(w,oldtitle,-1L);
for (i=1; i<MAXMYFILES; i++) myclose(i);
ArpExit(0L,0L);			/* Intuition need not to be closed */
}

init()
{
static char pipe1[32], pipe2[32];
struct Window *getwindow();

stdin->_flags	|= 0x80;	/* make sure we're set as a tty */
stdout->_flags	|= 0x80;	/* in case of redirection in .login */
Close(_devtab[2].fd);
_devtab[2].mode |= O_STDIO;
_devtab[2].fd = _devtab[1].fd;	/* set stderr to Output() otherwise */
				/* don't work with aux driver */
Myprocess = (struct Process *)FindTask(0L);
Mycli=(struct CommandLineInterface *)((long)Myprocess->pr_CLI << 2);
w=getwindow();
Pipe1 = pipe1;
Pipe2 = pipe2;
sprintf(pipe1, "ram:pipe1_%ld", Myprocess);
sprintf(pipe2, "ram:pipe2_%ld", Myprocess);
}

breakcheck()
{
return (int)(SetSignal(0L,0L) & SIGBREAKF_CTRL_C);
}

breakreset()
{
SetSignal(0L, SIGBREAKF_CTRL_C);
}

dobreak()
{
if (breakcheck()) { printf("^C\n"); return(1); }
return(0);
}

/* this routine causes manx to use this Chk_Abort() rather than it's own */
/* otherwise it resets our ^C when doing any I/O (even when Enable_Abort */
/* is zero).  Since we want to check for our own ^C's			 */

Chk_Abort()
{
return(0);
}

_wb_parse()
{
}

do_howmany()
{
char buf[10];

Getenv(shellctr, buf, 10L);
printf("Shell(s) running: %s\n",buf);
}

struct Window *getwindow()
{
struct InfoData *infodata;
struct Window *win;
long args[8];

infodata=AllocMem((long)sizeof(struct InfoData),MEMF_CLEAR | MEMF_PUBLIC);
args[0]=(long)infodata >> 2;
SendPacket(ACTION_DISK_INFO,args,Myprocess->pr_ConsoleTask);
win=(struct Window *)infodata->id_VolumeNode;
FreeMem(infodata,(long)sizeof(struct InfoData));
return win;
}
SHAR_EOF
cat << \SHAR_EOF > makefile
######################################################################
#
# Makefile to build Shell 3.02A
# by Carlo Borreo & Cesare Dieni 20-Dec-88
#
######################################################################

OBJS	= run.o main.o comm1.o comm2.o comm3.o execom.o set.o sub.o \
	  globals.o rawconsole.o

INCL	= shell.h

Shell   : Shell.syms $(OBJS)
	ln  +q -m -o Shell $(OBJS) -la -lc

Shell.syms : $(INCL)
	cc +HShell.syms shell.h

rawconsole.o : rawconsole.c $(INCL)
	cc +IShell.syms rawconsole.c

run.o   : run.c $(INCL)
	cc +IShell.syms run.c

main.o  : main.c $(INCL)
	cc +IShell.syms main.c

comm1.o : comm1.c $(INCL)
	cc +IShell.syms comm1.c

comm2.o : comm2.c $(INCL)
	cc +IShell.syms comm2.c

comm3.o : comm3.c $(INCL)
	cc +IShell.syms comm3.c

set.o   : set.c $(INCL)
	cc +IShell.syms set.c

sub.o   : sub.c $(INCL)
	cc +IShell.syms sub.c

globals.o : globals.c $(INCL)
	cc +IShell.syms globals.c

execom.o : execom.c $(INCL)
	cc +IShell.syms execom.c
SHAR_EOF
cat << \SHAR_EOF > rawconsole.c
/*
 * RawConsole.c
 *
 * Shell 2.07M  17-Jun-87
 * console handling, command line editing support for Shell
 * using new console packets from 1.2.
 * Written by Steve Drew. (c) 14-Oct-86.
 * 16-Dec-86 Slight mods to rawgets() for Disktrashing.
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

char *tyahdptr;

myget()
{
if (*tyahdptr) return *tyahdptr++;
return getchar();
}

#if RAW_CONSOLE
extern int aux; /* for use with aux: */

#define SETRAW setrawcon(-1L);
#define SETCON setrawcon(0L);

int width;

newwidth()
{
extern struct Window *w;

width=(w->Width- (w->BorderLeft + w->BorderRight)) / w->RPort->TxWidth;
}

char *rawgets(line,prompt)
char *line, *prompt;
{
char *get_var();
char *gets();
register int n, pl;
register int max, i;
unsigned char c1,c2,c3;
char fkeys[5];
char *s;
char *ps;
char typeahd[256];
int fkey, savn;
int insert = 1;
char rep[20];
int recall = -1;
struct HIST *hist;

newwidth();

if (aux) {
	printf("%s",prompt);
	fflush(stdout);
	}
if (!IsInteractive(Input()) || aux ) return(gets(line));
if (WaitForChar((long)Input(), 100L) ||   /* don't switch to 1L ...*/
		stdin->_bp < stdin->_bend) {     /* else causes read err's*/
	gets(line);
	return(line);
	}
SETRAW;
printf("\015%s\2336n",prompt);
savn = pl = n = 0;
tyahdptr = typeahd;
while((typeahd[n]=getchar()) != 'R') {
	if ((unsigned char)typeahd[n] == 155) savn = n;
	n++;
	}
	/* typeahd now contains possible type a head chars
	   followed by <CSI> cursor position report.
	*/
typeahd[savn]  = '\0';
if (typeahd[n-2] != ';') pl = (typeahd[n-2] - 48) * 10;
pl += typeahd[n-1] - 49;
ps = line + pl;
line[max = i = pl] = '\0';

if (s = get_var (LEVEL_SET, "_insert")) insert = atoi(s) ? 1 : 0;

while( (c1 = myget()) != 255) {
        switch(c1) {
            case 155:
                 c2 = myget();
                 switch(c2) {
                     case 'A':                  /* up arrow   */
                        n = ++recall;
                     case 'B':                  /* down arrow */
                        line[pl] = '\0';
                        if (recall >= 0 || c2 == 'A') {
                            if (c2 == 'B') n = --recall;
                            if (recall >= 0) {
                                for(hist = H_head; hist && n--;
                                    hist = hist->next);
                                if (hist) strcpy(&line[pl],hist->line);
                                else recall = H_len;
                            }
                        }
                        if (i != pl)
                            printf("\233%dD",i);
                        printf("\015\233J%s%s",prompt,ps);
                        i = max = strlen(ps) + pl;
                        break;
                     case 'C':                  /* right arrow*/
                        if (i < max) {
                            i++;
                            printf("\233C");
                        }
                        break;
                     case 'D':                  /* left arrow */
                        if (i > pl) {
                            i--;
                            printf("\233D");
                        }
                        break;
                     case 'T':           /* shift-up   */
                       n = recall = H_len-1;
                     case 'S':           /* shift-down */
                       line[pl] = '\0';
                       if (c2 == 'S') {
                           n = recall = 0;
                           if (H_head) strcpy(&line[pl], H_head->line);
                       }
                       else if (H_tail) strcpy(&line[pl], H_tail->line);
                       printf("\015\233J%s%s",prompt,ps);
                       i = max = strlen(ps) + pl;
                       break;
                    case ' ':                   /* shift -> <-*/
                        c3 = myget();
                                     switch(c3) {
                    case('@'):      /* shift ->   */
                        while (ps[i-strlen(prompt)] == ' ' && i<max) {
                            i++;
                            printf("\233C");
                        }
                        while (ps[i-strlen(prompt)] != ' ' && i<max) {
                            i++;
                            printf("\233C");
                        }
                        break;
                    case('A'):      /* shift <-   */
                        while (ps[i-strlen(prompt)-1] == ' ' && i>pl) {
                            i--;
                            printf("\233D");
                        }
                        while (ps[i-strlen(prompt)-1] != ' ' && i>pl) {
                            i--;
                            printf("\233D");
                        }
                        break;
                        default:
                        break;
                    }
                        break;
                    default:
                        c3 = myget();
                        if (c3 == '~') {
                            fkey = c2;
                            fkeys[0] = 'f';
                            if (c2 == '?') {
                                strcpy(ps,"help");
                                goto done;
                            }
                        }
                        else if (myget() != '~') { /* window was resized */
                            while(myget() != '|');
                            newwidth();
                            break;
                        }
                        else {
                            fkey = c3;
                            fkeys[0] = 'F';
                        }
                        sprintf(fkeys+1,"%d",fkey - 47);
                        if (s = get_var(LEVEL_SET, fkeys))
                                tyahdptr = strcpy(typeahd,s);
                        break;
                    }
                break;
            case 8:
                if (i > pl) {
                    i--;
                    printf("\010");
                }
                else break;
            case 127:
                if (i < max) {
                    int j,t,l = 0;
                    movmem(&line[i+1],&line[i],max-i);
                    --max;
                    printf("\233P");
                    j = width - i % width - 1;   /* amount to end     */
                    t = max/width - i/width;     /* no of lines       */
                    for(n = 0; n < t; n++) {
                        l += j;                  /* no. of char moved */
                        if (j) printf("\233%dC",j); /* goto eol       */
                        printf("%c\233P",line[width*(i/width+n+1)-1]);
                        j = width-1;
                    }
                    if (t)
                    printf("\233%dD",l+t);   /* get back */
                }
                break;
            case 18:
                n = i/width;
                if (n) printf("\233%dF",n);
                printf("\015\233J%s%s",prompt,ps);
                i = max;
                break;
            case 27:
                break;
            case 1:
                insert ^= 1;
                break;
            case 21:
            case 24:
            case 26:
                if (i>pl) printf("\233%dD",i-pl);
                i = pl;
                if (c1 == 26) break;
            case 11:        /* ^K */
                printf("\233J");
                max = i;
                line[i] = '\0';
                break;
            case 28:        /* ^\ */
                SETCON;
                return(NULL);
            case 5:
                if (i!=max) printf("\233%dC",max - i);
                i = max;
                break;
            case 10:
            case 13:
                line[max] = '\0';
done:           printf("\233%dC\n",max - i);

                SETCON;
                strcpy(line, ps);
                return(line);
            default:
                c1 &= 0x7f;
                if (c1 == 9) c1 = 32;
                if (c1 > 31 & i < 256) {
                    if (i < max && insert) {
                        int j,t,l = 0;
                        movmem(&line[i], &line[i+1], max - i);
                        printf("\233@%c",c1);
                        t = max/width - i/width;
                        j = width - i % width - 1;
                        for(n = 0; n < t; n++) {
                            l += j;
                            if (j) printf("\233%dC",j);
                            printf("\233@%c",line[width*(i/width+n+1)]);
                            j = width-1;
                        }
                        if (t) printf("\233%dD",l + t);
                        ++max;
                    }
                    else {
                        if(i == pl && max == i) printf("\015%s%s",prompt,ps);
                        putchar(c1);
                    }
                    line[i++] = c1;
                    if (max < i) max = i;
                    line[max] = '\0';
                }
        }
	}
SETCON;
return(NULL);
}

setrawcon(flag) /* -1L=RAW:, 0L=CON: */
long flag;
{
long packargs[8];

packargs[0]=flag;
SendPacket(994L, packargs, Myprocess->pr_ConsoleTask);
}

#endif
SHAR_EOF
cat << \SHAR_EOF > run.c

/*
 * RUN.C
 *
 * (c)1986 Matthew Dillon     9 October 1986
 *
 *    RUN   handles running of external commands.
 *
 * Version 2.07M by Steve Drew 10-Sep-87
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

extern char *v_path;
char *FindIt();

do_run(str)
char *str;
{
int i, len, retcode;
char buf[200]; /* enough space for 100 char cmd name + path stuff */
char *path;

char *p = av[0];
char **args = av+1;

while(*p++) *p &= 0x7F;      /* allow "com mand" */

while(*args) {				/* if any arg contains a space then */
    if (index(*args,' ')) {		/* surround with quotes, since must */
	i = strlen(*args);		/* of specified via "arg u ment" on */
	movmem(*args,(*args)+1,i);	/* original command line.	    */
	args[0][0] = args[0][i+1] = '\"';	/* mpush in execom.c has    */
	args[0][i+2] = '\0';		/* allowed for these 2 extra bytes. */
	}
    ++args;
    }
if ((len = strlen(av[0])) > 100) { ierror(NULL,509); return -1; }
if (path = FindIt(av[0],"",buf)) retcode = myfexecv(path, av);
else {
	Myprocess->pr_WindowPtr = (APTR)(-1);
	/*
	 * manx's fexecv code only allows us 38
	 * chars for command name.
	 */
	if (len > 37) av[0][37] = '\0';
	retcode = myfexecv(av[0], av);
	Myprocess->pr_WindowPtr = NULL;
	}
if (retcode < 0) {
	char *copy;
	if ((path = FindIt(av[0],".sh",buf)) == NULL) {
		fprintf(stderr,"Command Not Found %s\n",av[0]);
		return -1;
		}
	av[1] = buf;               /* particular to do_source() */
	copy = malloc(strlen(str)+3);
	sprintf(copy,"x %s",str);
	retcode = do_source(copy);
	free(copy);
	}
return retcode;
}

char *dofind(cmd, ext, buf)
char *cmd, *ext, *buf;
{
char *ptr, *s;

sprintf(buf,"%s%s",cmd,ext);
if (exists(buf)) return buf;
if (BaseName(buf)==buf) {
	s = get_var(LEVEL_SET, v_path);
	while (*s) {
		for (ptr=buf; *s && *s!=','; ) *ptr++ = *s++;
		sprintf(ptr, "%s%s", cmd, ext);
		if (exists(buf)) return buf;
		if (*s) s++;
		}
	}
return NULL;
}

char *FindIt(cmd,ext,buf)
char *cmd, *ext, *buf;
{
char *response;

Myprocess->pr_WindowPtr = (APTR)(-1);
response=dofind(cmd,ext,buf);
Myprocess->pr_WindowPtr = NULL;
return response;
}

myfexecv(cmd, argv)
char *cmd, **argv;
{
long ret_val;
struct FileHandle *fhp;
APTR sav_ret;
register char **ap, *cp, *arg;
int i;
long len, seg, sav, stksiz;
char buf[40];
union {
	long *lp;
	long ll;
	} l, stk;
long oldcin, oldcout;
long doexec();
extern long _savsp;

if (seg = LoadPrg(cmd)) goto found;
l.lp = (long *) Mycli->cli_CommandDir;
while (l.ll) {
	l.ll <<= 2;
	sav = CurrentDir(l.lp[1]);
	seg = LoadPrg(cmd);
	CurrentDir(sav);
	if (seg) goto found;
	l.ll = *l.lp;
	}
sprintf(buf, "c:%s", cmd);
if (seg = LoadPrg(buf)) goto found;
return -1;

found:

stksiz = 4 * Mycli->cli_DefaultStack;
if ((stk.lp = AllocMem(stksiz+8, 0L)) == 0) {
	UnLoadPrg(seg);
	return -1;
	}
for (len=0,ap=argv+1;*ap;ap++)
	len += strlen(*ap) + 1;
if (len==0) len++;
if ((cp = arg = AllocMem(len, 0L)) == 0) {
	UnLoadPrg(seg);
	FreeMem(stk.lp, stksiz+8);
	return -1;
	}
*stk.lp = stksiz + 8;
stk.ll += stksiz;
stk.lp[0] = stksiz;
stk.lp[1] = ((long *)_savsp)[2];
sav_ret = Myprocess->pr_ReturnAddr;
Myprocess->pr_ReturnAddr = (APTR) stk.lp;

sav = Mycli->cli_Module;
Mycli->cli_Module = seg;

for (ap=argv+1;*ap;ap++) {
	strcpy(cp, *ap);
	if (ap[1]) strcat(cp, " ");
	cp += strlen(cp);
	}
if (len==1) arg[1]='\0';
arg[len-1] = '\n';

cp = (char *)((long)Mycli->cli_CommandName << 2);
movmem(cp, buf, 40);
strcpy(cp+1, cmd);
cp[0] = strlen(cmd);

fhp = (struct FileHandle *) (Myprocess->pr_CIS << 2);
strncpy(fhp->fh_Buf<<2, arg, (int)(len < 200?len:199));
fhp->fh_Pos = 0;
fhp->fh_End = len < 200?len:199;
oldcin  = Myprocess->pr_CIS;
oldcout = Myprocess->pr_COS;

ret_val = doexec(len, stksiz, stksiz+8, len, arg, (seg+1)<<2, stk.ll);

Myprocess->pr_CIS = oldcin;
Myprocess->pr_COS = oldcout;
fhp->fh_Pos = fhp->fh_End;
UnLoadPrg(Mycli->cli_Module);
Myprocess->pr_ReturnAddr = sav_ret;
Mycli->cli_Module = sav;
FreeMem(arg, len);
movmem(buf, cp, 40);
return ret_val;
}

static long doexec()
{
#asm
	movem.l	d3-d7/a2-a5,-(sp)		;save registers
	lea		savsp(pc),a0
	move.l	sp,(a0)					;save our sp
	movem.l	8(a5),d0/d2/d3/d4/a0/a4/a7	;load params
	move.l	4(sp),a3				;get old sp from CLI
	movem.l	4(a3),a1/a2/a5/a6		;get BCPL environment
	move.l	d0,12(a1)				;set length
	move.l	a0,d1					;copy to dreg
	lsr.l	#2,d1					;convert to BPTR
	move.l	d1,8(a1)				;set ptr
	move.l	a0,d1					;copy to d1 as well
	jsr		(a4)					;call new program
	movem.l	(sp)+,d2/d3				;get stk siz and old sp
	move.l	sp,a1					;save current sp
	move.l	savsp(pc),sp			;get back our sp
	movem.l	(sp)+,d3-d7/a2-a5		;get back registers
	move.l	d0,-(sp)				;save return code
	sub.l	d2,a1					;back up a bit
	sub.l	#8,a1					;back up over header
	move.l	(a1),d0					;get size to free
	move.l	4,a6					;get ExecBase
	jsr		-210(a6)				;free the memory
	move.l	(sp)+,d0				;get the return code
#endasm
}

#asm
savsp:
	dc.l	0
#endasm
SHAR_EOF
cat << \SHAR_EOF > set.c

/*
 * SET.C
 *
 * (c)1986 Matthew Dillon     9 October 1986
 *
 * Version 2.07M by Steve Drew 10-Sep-87
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

extern char *v_titlebar, *v_verbose, *v_hist, *v_debug, *v_prompt;
extern struct Window *w;

#define MAXLEVELS (3 + MAXSRC)

struct MASTER {
	struct MASTER *next;
	struct MASTER *last;
	char *name;
	char *text;
};

static struct MASTER *Mbase[MAXLEVELS];

char *set_var(level, name, str)
register char *name, *str;
{
   register struct MASTER *base = Mbase[level];
   register struct MASTER *last;
   register int len;

   for (len = 0; isalphanum(name[len]); ++len);
   while (base != NULL) {
      if (strlen(base->name) == len && strncmp (name, base->name, len) == 0) {
         Free (base->text);
         goto gotit;
      }
      last = base;
      base = base->next;
   }
   if (base == Mbase[level]) {
      base = Mbase[level] = (struct MASTER *)malloc (sizeof(struct MASTER));
      base->last = NULL;
   } else {
      base = (struct MASTER *)malloc (sizeof(struct MASTER));
      base->last = last;
      last->next = base;
   }
   base->name = malloc (len + 1);
   bmov (name, base->name, len);
   base->name[len] = 0;
   base->next = NULL;
gotit:
   base->text = malloc (strlen(str) + 1);
   strcpy (base->text, str);
   if (*name=='_') sys_vars();
   return (base->text);
}

char *get_var (level, name)
register char *name;
{
   register struct MASTER *base = Mbase[level];
   register unsigned char *scr;
   register int len;

   for (scr = (unsigned char *)name; *scr && *scr != 0x80 && *scr != ' ' && *scr != ';' && *scr != '|'; ++scr);
   len = scr - name;

   while (base != NULL) {
      if (strlen(base->name) == len && strncmp (name, base->name, len) == 0)
         return (base->text);
      base = base->next;
   }
   return (NULL);
}

unset_level(level)
{
   register struct MASTER *base = Mbase[level];

   while (base) {
      Free (base->name);
      Free (base->text);
      Free (base);
      base = base->next;
   }
   Mbase[level] = NULL;
}

unset_var(level, name)
char *name;
{
   register struct MASTER *base = Mbase[level];
   register struct MASTER *last = NULL;
   register int len;

   for (len = 0; isalphanum(name[len]); ++len);
   while (base) {
      if (strlen(base->name) == len && strncmp (name, base->name, len) == 0) {
         if (base != Mbase[level])
            last->next = base->next;
         else
            Mbase[level] = base->next;
         if (base->next != NULL)
            base->next->last = last;
         if (base == Mbase[level])
            Mbase[level] = base->next;
         Free (base->name);
         Free (base->text);
         Free (base);
         return (1);
      }
      last = base;
      base = base->next;
   }
   return (-1);
}

do_unset_var(str, level)
char *str;
{
register unsigned int i;

for (i = 1; i < ac; ++i) unset_var (level, av[i]);
sys_vars();
return 0;
}

do_set_var(command, level)
char *command;
{
register struct MASTER *base = Mbase[level];
register char *str;

switch (ac) {
case 1:
	while (base && !dobreak()) {
		printf ("\2330m%-10s %s\n", base->name, base->text);
		base = base->next;
		}
	break;
case 2:
	if (str=get_var(level,av[1])) printf ("%-10s %s\n", av[1], str);
	break;
default:
	set_var (level, av[1], next_word (next_word (command)));
	if (*av[1]=='_') sys_vars();
	break;
	}
return 0;
}

extern char trueprompt[100];

sys_vars()
{
register char *str, *t;

if (strcmp(w->Title, str=get_var(LEVEL_SET, v_titlebar)))
	SetWindowTitles(w, str, -1L);
S_histlen=(str = get_var(LEVEL_SET, v_hist)) ? atoi(str) : 0;
debug  =(get_var(LEVEL_SET, v_debug)  !=NULL);
Verbose=(get_var(LEVEL_SET, v_verbose)!=NULL);
if (S_histlen < 2) S_histlen=2;

if ( (str=get_var(LEVEL_SET,v_prompt)) ==NULL) str="$ ";
t=trueprompt;
while (*str)
	if (*str=='%' && Toupper(str[1])=='P') {
		str+=2;
		strcpy(t,get_var(LEVEL_SET,"_cwd"));
		t+=strlen(t);
		}
	else *t++=*str++;
strcpy(t,"\2330m");
}
SHAR_EOF
cat << \SHAR_EOF > shell.h

/*
 * SHELL.H
 *
 * (c)1986 Matthew Dillon     9 October 1986
 *
 *
 * SHELL include file.. contains shell parameters and extern's
 *
 * Version 2.07M by Steve Drew 10-Sep-87
 *
 * Version 3.02A by Carlo Borreo & Cesare Dieni 20-Dec-88
 *
 */

#define RAW_CONSOLE 1   /* Set to 0 to compile out Cmd Line Editing */

#include <stdio.h>
#include <exec/exec.h>
#include <time.h>
#include <libraries/dos.h>
#include <libraries/dosextens.h>
#include <intuition/intuition.h>
#include <intuition/intuitionbase.h>
#include "shellfunctions.h"
#include <fcntl.h>
#include <libraries/arpbase.h>
#include <arpfunctions.h>

typedef struct FileInfoBlock FIB;

#define bmov movmem

#define MAXAV		256		/* Max. # arguments		*/
#define MAXSRC		5		/* Max. # of source file levels */
#define MAXIF		10		/* Max. # of if levels		*/
#define MAXALIAS	20		/* Max. # of alias levels	*/
#define MAXMYFILES	9		/* Max. # of internal files	*/

#define LEVEL_SET	0		/* which variable list to use   */
#define LEVEL_ALIAS	1
#define LEVEL_LABEL	2

	/* EXECOM.C defines */

#define FL_DOLLAR	0x01  /* One of the following */
#define FL_BANG		0x02
#define FL_PERCENT	0x04
#define FL_QUOTE	0x08
#define FL_IDOLLAR	0x10  /* Any or all of the following may be set */
#define FL_EOC		0x20
#define FL_EOL		0x40
#define FL_OVERIDE	0x80
#define FL_WILD		0x100
#define FL_MASK		(FL_DOLLAR|FL_BANG|FL_PERCENT|FL_QUOTE)

#ifndef NULL
#define NULL 0L
#endif

#define CHECKBREAK() dobreak()

#ifndef AZTEC_C
struct _dev {
	long  fd;
	short mode;
	};
#endif

struct HIST {
	struct HIST *next, *prev;	/* doubly linked list */
	char *line;			/* line in history    */
};

struct PERROR {
	int errnum;			/* Format of global error lookup */
	char *errstr;
};

struct DPTR {				/* Format of directory fetch pointer */
	BPTR lock;			/* lock on directory   */
	FIB *fib;			/* mod'd fib for entry */
	};

extern struct HIST *H_head, *H_tail;
extern struct PERROR Perror[];
extern struct DPTR *dopen();
extern char *set_var(), *get_var(), *next_word();
extern char *get_history(), *compile_av(), *get_pwd();
extern char *malloc(), *strcpy(), *strcat(), *index();
extern char **expand();
extern char *av[];
extern char *Current;
extern int  H_len, H_tail_base, H_stack;
extern int  E_stack;
extern int  Src_stack, If_stack, forward_goto;
extern int  ac;
extern int  debug, Rval, Verbose, disable, Quit;
extern int  Lastresult;
extern int  Exec_abortline;
extern int   S_histlen;
extern unsigned int options;
extern long  Cin, Cout, Cout_append;
extern char *Cin_name, *Cout_name;
extern char  Cin_type,  Cout_type;  /* these variables are in transition */
extern char *Pipe1, *Pipe2;

extern long Errno;
extern long Src_base[MAXSRC];
extern long Src_pos[MAXSRC];
extern char If_base[MAXIF];
extern struct Process *Myprocess;
extern struct CommandLineInterface *Mycli;

extern long atol(), Atol(), myatol();
SHAR_EOF
cat << \SHAR_EOF > shellfunctions.h
typedef	long	cList;
extern int Enable_Abort;

long					AbleICR();
long					AbortIO();
long					ActivateGadget();
void					ActivateWindow();
void					AddAnimOb();
void					AddBob();
void					AddConfigDev();
void					AddDevice();
long					AddDosNode();
void					AddFont();
void					AddFreeList();
short					AddGadget();
unsigned short				AddGList();
void					AddHead();
struct Interrupt *			AddICRVector();
void					AddIntServer();
void					AddLibrary();
long					AddMemList();
void					AddPort();
void					AddResource();
void					AddSemaphore();
void					AddTail();
void					AddTask();
void					AddTime();
void					AddVSprite();
long					Alert();
void *					AllocAbs();
long					AllocBoardMem();
cList					AllocCList();
struct ConfigDev *			AllocConfigDev();
struct MemList *			AllocEntry();
unsigned long				AllocExpansionMem();
void *					AllocMem();
long					AllocPotBits();
void *					AllocRaster();
char *					AllocRemember();
long					AllocSignal();
long					AllocTrap();
struct WBObject *			AllocWBObject();
void *					Allocate();
void					AlohaWorkbench();
void					AndRectRegion();
long					AndRegionRegion();
void					Animate();
short					AreaDraw();
long					AreaEllipse();
void					AreaEnd();
short					AreaMove();
void					AskFont();
long					AskSoftStyle();
long					AttemptLockLayerRom();
long					AttemptSemaphore();
short					AutoRequest();
long					AvailFonts();
long					AvailMem();
void					BeginIO();
void					BeginRefresh();
void					BeginUpdate();
void					BeginLayer();
long					BltBitMap();
long					BltBitMapRastPort();
void					BltClear();
void					BltMaskBitMapRastPort();
void					BltPattern();
void					BltTemplate();
struct Window *				BuildSysRequest();
char *					BumpRevision();
void					Cause();
void					CBump();
struct Events *				CDInputHandler();
void					ChangeSprite();
struct IORequest *			CheckIO();
short					ClearDMRequest();
void					ClearEOL();
void					ClearMenuStrip();
void					ClearPointer();
void					ClearRegion();
long					ClearRectRegion();
void					ClearScreen();
void					ClipBit();
void					Close();
void					CloseDevice();
void					CloseFont();
void					CloseLibrary();
void					CloseScreen();
void					CloseWindow();
short					CloseWorkBench();
void					CMove();
short					CmpTime();
long					ConcatCList();
long					ConfigBoard();
long					ConfigChain();
long					ConsoleDevice();
long					CopperListInit();
cList					CopyCList();
void					CopyMem();
void					CopyMemQuick();
void					CopySBitMap();
struct Layer *				CreateBehindLayer();
BPTR		CreateDir();
struct MsgPort *			CreatePort();
struct Process *			CreateProc();
struct IOStdReq *			CreateStdIO();
struct Task *				CreateTask();
struct Layer *				CreateUpfrontLayer();
BPTR					CurrentDir();
void					CurrentTime();
void					CWait();
long *					DateStamp();
void					Deallocate();
void					Debug();
void					Delay();
short					DeleteFile();
void					DeleteLayer();
void					DeletePort();
void					DeleteStdIO();
void					DeleteTask();
struct Process *			DeviceProc();
void					Disable();
void					DisownBlitter();
short					DisplayAlert();
void					DisplayBeep();
void					DisposeRegion();
void					DoCollision();
long					DoIO();
short					DoubleClick();
void					Draw();
void					DrawBorder();
void					DrawEllipse();
void					DrawGList();
void					DrawImage();
BPTR					DupLock();
void					Enable();
void					EndRefresh();
void					EndRequest();
void					EndUpdate();
void					Enqueue();
short					ExNext();
short					Examine();
short					Execute();
void					Exit();
struct ConfigDev *			FindConfigDev();
struct Node *				FindName();
struct MsgPort *			FindPort();
struct Resident *			FindResident();
struct SignalSemaphore *		FindSemaphore();
struct Task *				FindTask();
char *					FindToolType();
short					Flood();
void					FlushCList();
void					Forbid();
void					FreeBoardMem();
void					FreeCList();
void					FreeColorMap();
void					FreeConfigDev();
void					FreeCopList();
void					FreeCprList();
void					FreeDiskObject();
void					FreeEntry();
void					FreeExpansionMem();
void					FreeFreeList();
void					FreeGBuffers();
void					FreeMem();
void					FreePotBits();
void					FreeRaster();
void					FreeRemember();
void					FreeSignal();
void					FreeSprite();
void					FreeSysRequest();
void					FreeTrap();
void					FreeVPortCopLists();
void					FreeWBObject();
long					GetCC();
long					GetCLBuf();
short					GetCLChar();
short					GetCLWord();
struct ColorMap *			GetColorMap();
long					GetCurrentBinding();
struct Preferences *			GetDefPrefs();
struct DiskObject *			GetDiskObject();
short					GetGBuffers();
long					GetIcon();
struct Message *			GetMsg();
struct Preferences *			GetPrefs();
short					GetRGB4();
long					GetScreenData();
short					GetSprite();
struct WBObject *			GetWBObject();
long					IncrCLMark();
short					Info();
void					InitArea();
void					InitBitMap();
long					InitCLPool();
void					InitCode();
void					InitGMasks();
void					InitGels();
void					InitMasks();
void					InitRastPort();
void					InitRequester();
void					InitResident();
void					InitSemaphore();
void					InitStruct();
void					InitTmpRas();
void					InitVPort();
void					InitView();
BPTR					Input();
void					Insert();
struct Region *				InstallClipRegion();
long					IntuiTextLength();
struct InputEvent *			Intuition();
long					IoErr();
short					IsInteractive();
struct MenuItem *			ItemAddress();
void					LoadRGB4();
struct Segment *			LoadSeg();
void					LoadView();
BPTR					Lock();
void					LockLayer();
void					LockLayerInfo();
void					LockLayerRom();
void					LockLayers();
struct DeviceNode *			MakeDosNode();
long					MakeFunctions();
struct Library *			MakeLibrary();
void					MakeScreen();
void					MakeVPort();
long					MarkCList();
long					MatchToolValue();
void					ModifyIDCMP();
void					ModifyProp();
void					Move();
long					MoveLayer();
void					MoveScreen();
void					MoveSprite();
void					MoveWindow();
void					MrgCop();
void					NewList();
void					NewModifyProp();
struct Region *				NewRegion();
void					ObtainConfigBinding();
void					ObtainSemaphore();
void					ObtainSemaphoreList();
void					OffGadget();
void					OffMenu();
void					OnGadget();
void					OnMenu();
BPTR					Open();
long					OpenDevice();
struct Font *				OpenDiskFont();
struct Font *				OpenFont();
void					OpenIntuition();
struct Library *			OpenLibrary();
struct MiscResource *			OpenResource();
struct Screen *				OpenScreen();
struct Window *				OpenWindow();
short					OpenWorkBench();
void					OrRectRegion();
long					OrRegionRegion();
BPTR					Output();
void					OwnBlitter();
BPTR					ParentDir();
short					PeekCLMark();
void					Permit();
void					PolyDraw();
void					PrintIText();
long					PutCLBuf();
long					PutCLChar();
long					PutCLWord();
short					PutDiskObject();
long					PutIcon();
void					PutMsg();
long					PutWBObject();
void					QBSBlit();
void					QBlit();
short					RawKeyConvert();
long					Read();
char					ReadExpansionByte();
long					ReadExpansionRom();
short					ReadPixel();
void					RectFill();
void					RefreshGadgets();
void					RefreshGList();
void					RefreshWindowFrame();
void					ReleaseConfigBinding();
void					ReleaseSemaphore();
void					ReleaseSemaphoreList();
void					RemConfigDev();
long					RemDevice();
void					RemFont();
struct Node *				RemHead();
void					RemIBob();
void					RemICRVector();
void					RemIntServer();
long					RemLibrary();
unsigned short				RemoveGList();
void					RemPort();
void					RemResource();
void					RemSemaphore();
struct Node *				RemTail();
void					RemTask();
void					RemVSprite();
void					RemakeDisplay();
void					Remove();
unsigned short				RemoveGadget();
short					Rename();
void					ReplyMsg();
void					ReportMouse();
short					Request();
void					RethinkDisplay();
void					ScreenToBack();
void					ScreenToFront();
void					ScrollLayer();
void					ScrollRaster();
void					ScrollVPort();
long					Seek();
void					SendIO();
void					SetAPen();
void					SetBPen();
void					SetCollision();
short					SetComment();
void					SetCurrentBinding();
short					SetDMRequest();
void					SetDRMd();
long					SetExcept();
long					SetFont();
long					SetFunction();
long					SetICR();
struct Interrupt *			SetIntVector();
short					SetMenuStrip();
void					SetPointer();
struct Preferences *			SetPrefs();
short					SetProtection();
void					SetRast();
void					SetRGB4();
void					SetRGB4CM();
long					SetSR();
long					SetSignal();
long					SetSoftStyle();
short					SetTaskPri();
void					SetWindowTitles();
void					ShowTitle();
void					Signal();
long					SizeCList();
short					SizeLayer();
void					SizeWindow();
void					SortGList();
cList					SplitCList();
cList					SubCList();
void					SubTime();
void					SubLibrary();
void					SumKickData();
long					SuperState();
void					SwapBitsRastPortClipRect();
void					SyncSBitMap();
long					Text();
long					TextLength();
long					Translate();
long					UnGetCLChar();
long					UnGetCLWord();
void					UnLoadSeg();
void					UnLock();
short					UnPutCLChar();
short					UnPutCLWord();
void					UnlockLayer();
void					UnlockLayerInfo();
void					UnlockLayerRom();
void					UnlockLayers();
short					UpfrontLayer();
void					UserState();
short					VBeamPos();
struct View *				ViewAddress();
struct ViewPort *			ViewPortAddress();
short					WBenchToBack();
short					WBenchToFront();
long					Wait();
void					WaitBOVP();
void					WaitBlit();
short					WaitForChar();
long					WaitIO();
struct Message *			WaitPort();
void					WaitTOF();
struct Layer *				WhichLayer();
short					WindowLimits();
void					WindowToBack();
void					WindowToFront();
long					Write();
long					WriteExpansionByte();
void					WritePixel();
void					WritePotgo();
void					XorRectRegion();
long					XorRegionRegion();
SHAR_EOF
#	End of shell archive
exit 0
-- 
Bob Page, U of Lowell CS Dept.  page@swan.ulowell.edu  ulowell!page
Have five nice days.