[comp.os.minix] Official Clam1.3 Patch#1

wtoomey@gara.une.oz (Warren Toomey) (08/24/89)

Well, after a barrage of plaintive cries & diffs, we present the first set
of patches to Clam 1.3. Please apply these patches to Clam, as further
patches will be relative to these!

Now a few words on the patches, & the mail we've been getting on Clam:

1) Jwahar Bammi was hot off the mark with the diffs to get Clam working
   under GnuC on the Atari ST. If anybody else is using GnuC, look at
   his included libraries, & the code in #ifdef __STDC__  & #ifdef __GNUC__
   to see what things are needed for GnuC.

   Also, `idoprintf.c' & `iscanf.c' are NOT NEEDED any more, so remove
   them! Atari people still need to alter their login.c to use Clam as a
   login shell. Could Jwahar please post this - I've misplaced it.

2) Thanks to the people who have sent in bug reports. The major bug found
   so far is that directories after `.' were not searched. We didn't notice
   it as we have `.' on the end of our paths [ thus the bug could be
   construed as a feature :-) ]. This has been fixed. Another bug showed
   up with "" and * or ? in the same pipeline; I think this has been fixed
   too.

3) The makefile and header.h are going to be a major headache, because each
   system has got its include files in a different place, and everybody
   is going to customise header.h. The problem is now greater as Clam can
   now be used on any Unix or Minix machine. I've included patches to
   these files for the Atari, but unless we get an overwhelming response to
   change these files, they are going to stay `as is'.

4) Most of you noticed that I accidently send clamshar4 as clamshar3, but
   sent clamshar3 properly later. Some people didn't notice, and were
   asking where `builtin1.c' had got too. It's there, in the 2nd posting
   of clamshar3. { The best laid plans of mice & men .... }

That's about it. Keep any bug reports/ideas/questions rolling in!

	Callum Gibson & Warren Toomey.

wtoomey@gara.une.oz (Warren Toomey) (08/24/89)

# This is a shell archive.  Remove anything before this line, then
# unpack it by saving it in a file and typing "sh file".  (Files
# unpacked will be owned by you and have default permissions.)
#
# This archive contains:
# Makefile.dif clex.cdif exec.cdif hash.cdif main.cdif meta.cdif var.cdif

echo x - Makefile.dif
cat > "Makefile.dif" << '//E*O*F Makefile.dif//'
*** Makefile	Thu Aug 24 11:29:53 1989
--- ../New/Makefile	Thu Aug 24 11:39:22 1989
***************
*** 53,60 ****
  # compiler, try the previous section. I don't guarantee this will work
  # with Gnu C either, as I don't have Gnu to test it with.
  #DEFINES=-DMINIX -DATARI_ST
! #CLIB=-ltermcap -ldir
! 
  
  clam : alias.$(O) builtin1.$(O) builtin2.$(O) clex.$(O) comlined.$(O) cx.$(O) exec.$(O) file.$(O) global.$(O) hash.$(O) hist.$(O) job.$(O) main.$(O) meta.$(O) parse.$(O) var.$(O)
  	$(CC) $(CFLAGS) alias.$(O) builtin1.$(O) builtin2.$(O) clex.$(O) comlined.$(O) cx.$(O) exec.$(O) file.$(O) global.$(O) hash.$(O) hist.$(O) job.$(O) main.$(O) meta.$(O) parse.$(O) var.$(O) -o clam $(CLIB)
--- 53,59 ----
  # compiler, try the previous section. I don't guarantee this will work
  # with Gnu C either, as I don't have Gnu to test it with.
  #DEFINES=-DMINIX -DATARI_ST
! #CLIB= -ldir32 -liio32 -s -z
  
  clam : alias.$(O) builtin1.$(O) builtin2.$(O) clex.$(O) comlined.$(O) cx.$(O) exec.$(O) file.$(O) global.$(O) hash.$(O) hist.$(O) job.$(O) main.$(O) meta.$(O) parse.$(O) var.$(O)
  	$(CC) $(CFLAGS) alias.$(O) builtin1.$(O) builtin2.$(O) clex.$(O) comlined.$(O) cx.$(O) exec.$(O) file.$(O) global.$(O) hash.$(O) hist.$(O) job.$(O) main.$(O) meta.$(O) parse.$(O) var.$(O) -o clam $(CLIB)
//E*O*F Makefile.dif//

echo x - clex.cdif
cat > "clex.cdif" << '//E*O*F clex.cdif//'
*** clex.c	Thu Aug 24 11:30:10 1989
--- ../New/clex.c	Thu Aug 24 11:26:48 1989
***************
*** 660,666 ****
--- 660,671 ----
    }
    if (index)			/* have we found any ?? */
    {
+ #ifdef __GNUC__
+     qsort((char *)carray,(unsigned long)index,
+     	  (unsigned long)(sizeof(struct candidates_2)),compare);
+ #else
      qsort((char *)carray,index,(int)(sizeof(struct candidates_2)),compare);
+ #endif
      colprint(carray,index,maxlength);
  /* free up the space */
      for (index--;index>=0;index--)
//E*O*F clex.cdif//

echo x - exec.cdif
cat > "exec.cdif" << '//E*O*F exec.cdif//'
*** exec.c	Thu Aug 24 11:30:18 1989
--- ../New/exec.c	Thu Aug 24 11:27:02 1989
***************
*** 380,400 ****
  fprintf(stderr,"call executable\n");
  #endif
  	  errno=0;
! 	  if (executable(name,NULL,1)==FALSE)
  	  {
- 	    if (errno!=ENOENT)
- 	      exist=TRUE;
- 	    hashval++;
- 	    hashval%=HSHSIZ;
- 	    continue;
- 	  }
- 	  else
- 	  {
  	    if (times==0) hits++;		/* found it first go */
  	    else misses++;			/* had a collision */
  	    strcpy(fullpathname,hasharray[hashval].name);
  	    return(FOUND);
  	  }
  	}
  #ifdef DEBUG
  fprintf(stderr,"Not rejected by . checking for alias or builtin.\n");
--- 380,393 ----
  fprintf(stderr,"call executable\n");
  #endif
  	  errno=0;
! 	  if (executable(name,NULL,1)==TRUE)
  	  {
  	    if (times==0) hits++;		/* found it first go */
  	    else misses++;			/* had a collision */
  	    strcpy(fullpathname,hasharray[hashval].name);
  	    return(FOUND);
  	  }
+ 	  /* otherwise we just fall through and do the other testing */
  	}
  #ifdef DEBUG
  fprintf(stderr,"Not rejected by . checking for alias or builtin.\n");
***************
*** 401,406 ****
--- 394,402 ----
  #endif
  	if (pos=(hasharray[hashval].flag&EXTYPE))
  	{
+ #ifdef DEBUG
+ fprintf(stderr,"pos is %d\n",pos);
+ #endif
  	  if (pos==ALIASEX)
  	  {
  	    for (i=0;i<MAXAL && current_alias[i]!=NULL;i++)
***************
*** 434,441 ****
--- 430,443 ----
  	strcpy(fullpathname,hasharray[hashval].exec_ptr.dir);
  	strcat(fullpathname,"/");
  	strcat(fullpathname,hasharray[hashval].name);
+ #ifdef DEBUG
+ fprintf(stderr,"doing executable with %s<\n",fullpathname);
+ #endif
  	if (executable(fullpathname,"",1)==FALSE)
  	{
+ #ifdef DEBUG
+ fprintf(stderr,"executable failed\n");
+ #endif
  	  exist=TRUE;
  	  hashval++;
  	  hashval%=HSHSIZ;
***************
*** 778,783 ****
--- 780,788 ----
  	       }
  /* All caught signals should be reset by execve so we shouldn't have to do it in
     resetsigdefaults. It doesn't work for ignored ones, though. */
+ #ifdef DEBUG
+ fprintf(stderr,"path %s argv[0] %s argv[1] %s argv[2] %s\n",path,argv[0],argv[1],argv[2]);
+ #endif
  	       execve(path,argv,environ);
  
  /* Try to use shell to interpret, now. First move args along, insert the
//E*O*F exec.cdif//

echo x - hash.cdif
cat > "hash.cdif" << '//E*O*F hash.cdif//'
*** hash.c	Thu Aug 24 11:30:15 1989
--- ../New/hash.c	Thu Aug 24 11:26:49 1989
***************
*** 53,66 ****
    char fpn[MAXWL];
  
    if (nojoin)
!     stat(dir,&buf);
    else
    {
      sprintf(fpn,"%s/%s",dir,entname);
!     stat(fpn,&buf);
    }
    if (((buf.st_mode & S_IFMT)==S_IFREG) && (buf.st_mode & 0111))
      return(TRUE);
    return(FALSE);
  }
  
--- 53,82 ----
    char fpn[MAXWL];
  
    if (nojoin)
!   {
! #ifdef DEBUG
! fprintf(stderr,"ex f1\n");
! #endif
!     if (stat(dir,&buf)) return(FALSE);
!   }
    else
    {
+ #ifdef DEBUG
+ fprintf(stderr,"ex f2\n");
+ #endif
      sprintf(fpn,"%s/%s",dir,entname);
!     if (stat(fpn,&buf)) return(FALSE);
    }
    if (((buf.st_mode & S_IFMT)==S_IFREG) && (buf.st_mode & 0111))
+   {
+ #ifdef DEBUG
+ fprintf(stderr,"ex s\n");
+ #endif
      return(TRUE);
+   }
+ #ifdef DEBUG
+ fprintf(stderr,"ex f3\n");
+ #endif
    return(FALSE);
  }
  
//E*O*F hash.cdif//

echo x - main.cdif
cat > "main.cdif" << '//E*O*F main.cdif//'
*** main.c	Thu Aug 24 11:30:33 1989
--- ../New/main.c	Thu Aug 24 11:27:02 1989
***************
*** 730,736 ****
  {
    extern SYM_T intercom();
    extern bool getline(),getpipeline();
!   extern void insert(),(*charfn)(),(*ptif)();
    extern int loadline,O_echoexp,O_exiterror,meta_1(),meta_2(),
  	     waitfor();
    extern char saveline[];
--- 730,736 ----
  {
    extern SYM_T intercom();
    extern bool getline(),getpipeline();
!   extern void reportjobs(),insert(),(*charfn)(),(*ptif)();
    extern int loadline,O_echoexp,O_exiterror,meta_1(),meta_2(),
  	     waitfor();
    extern char saveline[];
//E*O*F main.cdif//

echo x - meta.cdif
cat > "meta.cdif" << '//E*O*F meta.cdif//'
*** meta.c	Thu Aug 24 11:30:41 1989
--- ../New/meta.c	Thu Aug 24 11:26:45 1989
***************
*** 549,554 ****
--- 549,557 ----
  	}
  	break;
        case ' ':
+ #ifdef DEBUG
+ fprintf(stderr,"inword %d insym %d\n",inword,insym);
+ #endif
  	if (inword || insym)
  	{
  	  l=0;
***************
*** 561,568 ****
  fprintf(stderr,"copying to next \"\n");
  #endif
  	inword=1;
! 	word[i++]=line[(*pos)++];
! 	while(line[*pos]!=EOS && line[*pos]!='"') word[i++]=line[(*pos)++];
  	break;
        case '\'':
  #ifdef DEBUG
--- 564,579 ----
  fprintf(stderr,"copying to next \"\n");
  #endif
  	inword=1;
! 	while(line[*pos]!=EOS)
! 	{
! 	  word[i++]=line[*pos];
! 	  if (line[*pos]=='"')
! 	  {
! 	    (*pos)++;
! 	    break;
! 	  }
! 	  (*pos)++;
! 	}
  	break;
        case '\'':
  #ifdef DEBUG
***************
*** 569,576 ****
  fprintf(stderr,"copying to next '\n");
  #endif
  	inword=1;
! 	word[i++]=line[(*pos)++];
! 	while(line[*pos]!=EOS && line[*pos]!='\'') word[i++]=line[(*pos)++];
  	break;
        case '\\':
  	inword=1;
--- 580,595 ----
  fprintf(stderr,"copying to next '\n");
  #endif
  	inword=1;
! 	while(line[*pos]!=EOS)
! 	{
! 	  word[i++]=line[*pos];
! 	  if (line[*pos]=='\'')
! 	  {
! 	    (*pos)++;
! 	    break;
! 	  }
! 	  (*pos)++;
! 	}
  	break;
        case '\\':
  	inword=1;
***************
*** 607,612 ****
--- 626,634 ----
    *pattern=FALSE;
    if (loadword(line,pos,word,1)==FALSE)
      return(EOLN);			/* end of line encountered */
+ #ifdef DEBUG
+ fprintf(stderr,"word from loadword is %s<\n",word);
+ #endif
  /* this loop will detect if there's any * ? [] to match */
    while(c=word[i++])
      switch(quote)
***************
*** 847,852 ****
--- 869,876 ----
  #endif
  /* if an absolute path name is given, then chop it off the front of word and
     put it in dir. Now word contains the patterned stuff onwards. */
+   
+     dir[0] = EOS;	/* finddir seems to assume this */
      finddir(word,dir);
  
  /* Ok, here goes with the first call to the recursive functions. The parameters
***************
*** 857,863 ****
      mindex=0;nopat=0;
      if (!(err=matchdir(dir,word))) m_err=OK;
      else lasterr=err;		/* keep record of last error */
!     qsort((char *)matchers,mindex,(int)sizeof(char *),cmp);
      for (k=0;k<mindex;k++)
      {
        strcat(newline," ");
--- 881,892 ----
      mindex=0;nopat=0;
      if (!(err=matchdir(dir,word))) m_err=OK;
      else lasterr=err;		/* keep record of last error */
! #ifdef __GNUC__
! 	qsort((char *)matchers,(unsigned long)mindex,
! 	  (unsigned long)sizeof(char *),cmp); 
! #else
!         qsort((char *)matchers,mindex,(int)sizeof(char *),cmp);
! #endif
      for (k=0;k<mindex;k++)
      {
        strcat(newline," ");
***************
*** 1031,1037 ****
  					   return(DL_ERR);
  				  case -1: strcpy(&newline[j],vget(vname));
  					   break;
! 				  default: strcpy(&newline[j],vwget(vname,num));
  				}
  			      else
  				if (getenv(vname))
--- 1060,1071 ----
  					   return(DL_ERR);
  				  case -1: strcpy(&newline[j],vget(vname));
  					   break;
! 				  default:
! 				     { char *tmp, *vwget();
! 				       strcpy(&newline[j],
! 					      (tmp = vwget(vname,num))); 
! 				       free(tmp);
! 				     }
  				}
  			      else
  				if (getenv(vname))
//E*O*F meta.cdif//

echo x - var.cdif
cat > "var.cdif" << '//E*O*F var.cdif//'
*** var.c	Thu Aug 24 11:30:45 1989
--- ../New/var.c	Thu Aug 24 11:26:58 1989
***************
*** 52,59 ****
  {
    extern bool getword();
    int i,pos;
!   char word[MAXWL],*vval;
  
    pos=0;
    vval=vget(vname);
    for (i=0;i<=wnum;i++)
--- 52,64 ----
  {
    extern bool getword();
    int i,pos;
!   char *word,*vval;
  
+   if((word = (char *)malloc((unsigned)MAXWL)) == (char *)NULL)
+   {
+       perror("vwget: malloc");
+       return(NULL);
+   }
    pos=0;
    vval=vget(vname);
    for (i=0;i<=wnum;i++)
***************
*** 60,66 ****
      if (getword(vval,&pos,word,TRUE)==TRUE)
        continue;
      else break;
!   return(word);
  }
  
  bool export(vname,opt)
--- 65,72 ----
      if (getword(vval,&pos,word,TRUE)==TRUE)
        continue;
      else break;
!   return(word);	/* caller frees mem alloc'ed for word */
!   		/* found only one instance in meta.c  */
  }
  
  bool export(vname,opt)
***************
*** 120,130 ****
--- 126,146 ----
        if (!strncmp(environ[i],"PATH=",5))
        {
  	environ[i]=(char *) realloc (environ[i],(unsigned)(strlen(env)+1));
+ 	if (environ[i]==NULL)
+ 	{
+ 	  perror("realloc");
+ 	  exit(1);
+ 	}
  	break;
        }
      if (!environ[i])			/* if we didn't find an existing one */
      {
        environ[i]=(char *) malloc ((unsigned)(strlen(env)+1));
+       if (environ[i]==NULL)
+       {
+ 	perror("malloc1");
+ 	exit(1);
+       }
        environ[i+1]=0;
      }
      strcpy(environ[i],env);
***************
*** 168,173 ****
--- 184,195 ----
      if (!environ[i])			/* if we didn't find an existing one */
      {
        environ[i]=(char *) malloc ((unsigned)(strlen(env)+1));
+       if (environ[i]==NULL)
+       {
+ 	perror("malloc2");
+ 	environ[i]="NULL";
+ 	return;
+       }
        environ[i+1]=0;
      }
      strcpy(environ[i],env);
***************
*** 232,242 ****
--- 254,279 ----
      if (i)		/* normal insertion between old and ptr */
      {
        new=(struct vlist *) malloc ((unsigned)(sizeof(struct vlist)));
+       if (new==NULL)
+       {
+ 	perror("vset: malloc1");
+ 	return;
+       }
        old->next=new;
        new->next=ptr;
        new->var=(char *) malloc ((unsigned)(strlen(vname)+1));
+       if (new->var==NULL)
+       {
+ 	perror("vset: malloc2");
+ 	return;
+       }
        strcpy(new->var,vname);
        new->val=(char *) malloc ((unsigned)(strlen(vval)+1));
+       if (new->val==NULL)
+       {
+ 	perror("vset: malloc3");
+ 	return;
+       }
        strcpy(new->val,vval);
        new->exported=FALSE;
      }
***************
*** 243,252 ****
--- 280,304 ----
      else		/* insertion before top, old=ptr=top still. */
      {
        old=(struct vlist *) malloc ((unsigned)(sizeof(struct vlist)));
+       if (old==NULL)
+       {
+ 	perror("vset: malloc4");
+ 	return;
+       }
        old->next=top;
        old->var=(char *) malloc ((unsigned)(strlen(vname)+1));
+       if (old->var==NULL)
+       {
+ 	perror("vset: malloc5");
+ 	return;
+       }
        strcpy(old->var,vname);
        old->val=(char *) malloc ((unsigned)(strlen(vval)+1));
+       if (old->val==NULL)
+       {
+ 	perror("vset: malloc6");
+ 	return;
+       }
        strcpy(old->val,vval);
        old->exported=FALSE;
        top=old;		/* and finally assign new top */
***************
*** 258,273 ****
--- 310,345 ----
  fprintf(stderr,"old val %s new val %s.\n",ptr->val,vval);
  #endif
        ptr->val=(char *) realloc (ptr->val,(unsigned)(strlen(vval)+1));
+       if (ptr->val==NULL)
+       {
+ 	perror("vset: malloc7");
+ 	return;
+       }
        strcpy(ptr->val,vval);
      }
      else		/* value doesn't exist, make new variable and append */
      {
        new=(struct vlist *) malloc ((unsigned)(sizeof(struct vlist)));
+       if (new==NULL)
+       {
+ 	perror("vset: malloc8");
+ 	return;
+       }
        new->next=0;
        old->next=new;
        new->var=(char *) malloc ((unsigned)(strlen(vname)+1));
+       if (new->var==NULL)
+       {
+ 	perror("vset: malloc9");
+ 	return;
+       }
        strcpy(new->var,vname);
        new->val=(char *) malloc ((unsigned)(strlen(vval)+1));
+       if (new->val==NULL)
+       {
+ 	perror("vset: malloc10");
+ 	return;
+       }
        strcpy(new->val,vval);
      }
  
***************
*** 358,363 ****
--- 430,440 ----
    {
      l=strlen(vget(vname));
      newval=(char *) malloc ((unsigned)(l+strlen(vval)+1));
+     if (newval==NULL)
+     {
+       perror("vadd: malloc");
+       return;
+     }
      sprintf(newval,"%s%s",vget(vname),vval);
      vset(vname,newval);
      free(newval);
***************
*** 445,450 ****
--- 522,532 ----
    for (i=0;envp[i];i++)
    {
      newenv[i]=(char *) malloc ((unsigned)(strlen(envp[i])+1));
+     if (newenv[i]==NULL)
+     {
+       perror("copyenv: malloc");
+       return;
+     }
      (void) strcpy(newenv[i],envp[i]);
    }
    newenv[i]=0;
//E*O*F var.cdif//

exit 0

wtoomey@gara.une.oz (Warren Toomey) (08/24/89)

# This is a shell archive.  Remove anything before this line, then
# unpack it by saving it in a file and typing "sh file".  (Files
# unpacked will be owned by you and have default permissions.)
#
# This archive contains:
# header.h

echo x - header.h
cat > "header.h" << '//E*O*F header.h//'
/*****************************************************************************
**                                                                          **
**          The Clam Shell is Copyright (C) 1988 by Callum Gibson.          **
**       This file is part of Clam Shell. You may freely use, copy and      **
**     distribute it, but if you alter any source code do not distribute    **
**   the altered copy. i.e. you may alter this file for your own use only.  **
**                                                                          **
*****************************************************************************/
#include <stdio.h>
#include <ctype.h>
#include <signal.h>
#include <sys/types.h>
#include <errno.h>

#ifdef ATT
# include <dirent.h>
# include <termio.h>
# include <sys/file.h>
#endif

#ifdef MINIX
# include <sgtty.h>
# include <dirent.h>
# include <fcntl.h>
#  ifndef ATARI_ST
#   include <sys/dir.h>
#   include <sys/time.h>
#  else
#   include <time.h>
#  endif
#endif

#ifdef UCB
# include <sgtty.h>
# include <sys/dir.h>
# include <sys/time.h>
# include <sys/file.h>
# include <sys/resource.h>
#  ifdef SUN
#   include <sys/wait.h>
#  else
#   include <wait.h>
#  endif
#endif

/* Here is the Minix section i.e all the things that had to be set up
   to get Minix to go */

#ifdef MINIX
# define TIOCSETN TIOCSETP
# define lstat stat
# define O_echoexpbefore O_ebefore
# define builtin_name b_name
# define builtin_func b_func
# define current_alias c_alias
# define getline getlin
# define alias_depth als_dpt
#endif

/* for some reason the read set the error flag before the eof flag so I
   wrote my own ffinish macro which does both feof and ferror simultaneously */

#ifdef MINIX
# define ffinish(p)	(((p)->_flags&(_EOF|_ERR))!=0)
#else
# define ffinish(p)	(((p)->_flag&(_IOEOF|_IOERR))!=0)
#endif

/***************************************************************************
	Anything that needs to be changed is under this line.
***************************************************************************/

/* name of file with user passwords and directory entries e.g. /etc/passwd */
#define PASSWD "/etc/passwd"

/* name of help program (full path, please) */
#define HELP "/usr/local/bin/man"

/* name of default interpreter shell. Normally it will be Bourne Shell */
#define DFLTSH "/bin/sh"

/* name of default editor to use for alias creation. */
#define DFLTED "/usr/local/bin/vi"

/* Clam needs to know where it is for customised popen */
#define CLAMSH "/usr/local/bin/clam"

/* Sizes of some data structures */
#ifdef MINIX
# define MAXARG  512			/* no. of arguments */
# define MAXWL 	 512			/* word length */
# define MAXFNL  128			/* file name length */
# define MAXLL  1024			/* line length */
# define MAXPL   128			/* path length */
# define MAXCAN 1000			/* maximum number of candidates */
# define VARNL    32			/* variable name length */
# define VARVL   256			/* variable value length */
# define USERNL   32			/* max length of user names */
# define MAXAL    16			/* max depth of aliases */
#else
# define MAXARG  512			/* no. of arguments */
# define MAXWL  1024			/* word length */
# define MAXFNL  256			/* file name length */
# define MAXLL  2048			/* line length */
# define MAXPL  2048			/* path length */
# define HSHSIZ 1021			/* size of hash array */
# define MAXCAN 2000			/* maximum number of candidates */
# define VARNL   256			/* variable name length */
# define VARVL  1024			/* variable value length */
# define USERNL   32			/* max length of user names */
# define MAXAL    32			/* max depth of aliases */
#endif

/* number of signals. For ucb usually 27, for att 19. */

#ifdef ATT
# define NUMSIG 19
#endif
#ifdef MINIX
# ifdef ATARI_ST
#  define NUMSIG NSIG		/* defined in <signal.h> */
# else
#  define NUMSIG 19
# endif
#endif
#ifdef UCB
# define NUMSIG 27
#endif

/****************************************************************************
	Don't change anything past this line unless you're hacking.
****************************************************************************/

/* Some general defines */
#define EOS '\0'
#define UNDEF -1
#define NFILES 20
#define ALIASEX   01		/* executable is alias */
#define BUILTEX   02		/* executable is builtin */
#define EXTYPE    03		/* mask for the type of executable */
#define BEFOREDOT  0		/* priority flag bit if before . on path */
#define AFTERDOT  04		/* priority flag bit if after . on path */
#define PRIORITY  04		/* mask for priority of executable (as above) */

/* Identification for error codes for metacharacter expansion function */
#ifdef OK	/* defined somewhere on minixST */
#undef OK
#endif
#define OK 0
#define SH_ERR -1
#define ST_ERR -2
#define BR_ERR -3
#define BQ_ERR -4
#define QM_ERR -5
#define TL_ERR -6
#define CY_ERR -7
#define CT_ERR -8
#define NX_ERR -9
#define DL_ERR -10

typedef enum TS {RDRIN,RDROUT,RDRERR,APPND,PIPE,WORD,ENDLN,SEMI,EQ,ADD,BCKGND,DBLPIPE,DBLAMP,ERRER} SYM_T;

/* some brain damaged people put these in stdio */
#ifdef FALSE
#undef FALSE
#endif

#ifdef TRUE
#undef TRUE
#endif

typedef enum bb {FALSE,TRUE} bool;

/* These structures are used to store the alias definitions. */
struct adefn
{
  char *a_line;
  struct adefn *nextln;
};

struct alias
{
  char *a_name;
  struct adefn *defin;
  struct alias *next;
};

/* ex_ptr is the hasharray structure's union which points to an executable's whereabouts */
union ex_ptr
{
  char *dir;
  void (*builtin_fn)();
  struct adefn *alias_defn;
};
  
/* har is the hasharray structure */
struct har
{
  char *name;
  char flag;
  union ex_ptr exec_ptr;
};

struct job
{
  int jobnumber;
  int pid;
  char *name;
  bool rdrout;
  char *dir;
#ifdef ATT
  int status;
#endif
#ifdef MINIX
  int status;
#endif
#ifdef UCB
  union wait status;
#endif
  long lastmod;
  struct job *next;
};

#ifdef __STDC__
#ifndef __NO_PROTO__

/* alias.c */
struct adefn *checkalias (char *aname);
void aliaslist (char *aname);
void savealias (char *aname, FILE *fp);
void addalias (char *aname, struct adefn *stdefn);
void makelinealias (char *aname, char *aline);
void makealias (char *aname, FILE *fp);
void delalias (char *aname);

/* builtin1.c */
void alias (int argc, char **argv, int infd, int outfd, int errfd,
	    char *ifil, char *ofil, char *efil, bool appnd, bool bckgnd);
void logout (int argc, char **argv, int infd, int outfd, int errfd,
	     char *ifil, char *ofil, char *efil, bool appnd, bool bckgnd);
void Kill (int argc, char *argv[], int infd, int outfd, int errfd,
	   char *ifil, char *ofil, char *efil, bool appnd, bool
	   bckgnd, bool piped);
void limit (int argc, char *argv[], int infd, int outfd, int errfd,
	    char *ifil, char *ofil, char *efil, bool appnd, bool
	    bckgnd, bool piped);
void unlimit (int argc, char *argv[], int infd, int outfd, int errfd,
	      char *ifil, char *ofil, char *efil, bool appnd, bool
	      bckgnd, bool piped);
void (*checkbuiltins())(char *);

/* builtin2.c */
void printlimit (char *limname);
void setlimit (char *limname, char *limval);
int getnextword (char *line, int *pos, char *word);
int convert (char *string);
void editalias (char *aname);

/* clex.c */
bool firstword (char *line, int pos);
void complete (char *line, int *pos, int curs[]);
void nameopt (char *line, int pos, int curs[]);

/* comlined.c */
void mputc (int c, FILE *f, int curs[]);
int oputc (int c);
void go (int curs[], int  hor, int vert);
void backward (int curs[]);
void forward (int curs[]);
void clrscrn (void);
void insert (char *line, int pos, int letter, int curs[]);
void overwr (char *line, int pos, int letter, int curs[]);
void show (char *line, int curs[], bool clearing);
void goend (char *line, int *pos, int curs[]);
void copyback (char *line, int pos, int curs[], int count);
void delnextword (char *line, int pos, int curs[]);
void delprevword (char *line, int *pos, int curs[]);
void backword (char *line, int *pos, int curs[]);
void forword (char *line, int *pos, int curs[]);
void yanknext (char *line, int pos, char *yankbuf);
void yankprev (char *line, int pos, char *yankbuf);
void clrline (char *line, int pos, int curs[]);
void transpose (char *line, int pos, int curs[]);
int strip (char *line);
void tardis (char *line, int *pos, int curs[]);
bool getline (char *line, int *nosave, int feature_off);

/* cx.c */
bool expand_tilde (char *user_path, int *builtin);
void help (char *line, int pos, int curs[]);

/* exec.c */
void setbgexec (void);
void resetsigdefaults (void);
bool findslash (char *string);
void runalias (struct adefn *start, int argc, char *argv[], int infd,
		int outfd, int errfd, char *ifil, char *ofil, char *efil,
		bool appnd, bool bckgnd, bool piped);
int getpath (char *fullpathname, char *name, int flag);
void panic (char *mess);
int atoo (char *str);
void setmask (char *str);
void redirect (int infd, int outfd, int errfd, char *ifil, char *ofil,
		char *efil, bool appnd, bool bckgnd);
int execute (int argc, char *argv[], int infd, int outfd, int errfd,
	     char *ifil, char *ofil, char *efil, bool appnd,
	     bool bckgnd, bool piped, int fromfile);

/* file.c */
bool getfileline (char *line, FILE *fp, int nostrip);
void file (FILE *finp, int nosave);


/* hash.c */
bool executable (char *dir, char *entname, int nojoin);
int hash (char *name);
int hashaliases (void);
int hashbuiltins (void);
int tildehashisin (char *path);
void hashpath (void);

/* hist.c */
int savehist (char *line, int histnum, int max);
void loadhist (char *line, int *pos, int histnum, int curs[]);
void mprint (char *line, int nocr);
void history (char *argv[]);
bool gethist (char *event);
char *getnumhist (int histnum);
int matchhist (int histnum);

/* job.c */
#ifdef JOB
void joblist (void);
bool stoppedjobs (void);
struct job *findjob (int pid);
int pidfromjob (int jobno);
void addreport (struct job *newone);
int addjob (int pid, char *name, int outfd, bool bckgnd);
void newcurr (void);
void rmjob (int pid);
int update (int pid, union wait status);
void checkjobs (void);
int waitfor (int pid);
void reportjobs (void);
#endif

/* main.c */
int lengthint (int num);
void printime (void);
void prprompt (int prtype);
bool tflagexist (char *id, char *tc);
void printctrl (char *name, char *str);
void terminal (void);
void graceful (int sig);
void setup (void);
void resetsh (void);
void setdown (void);
void leave_shell (void);
int process (int argc, char *argv[], char *comfile);
void shinit (void);
void interact (void);
void execstring (int argc, char *argv[], int argp);
int main (int argc, char *argv[], char *envp[]);

/* meta.c */
void getdir (FILE *fp, char *line);
int isanum (char *string);
int meta_1 (char *line, int nosave);
int meta_2 (char *line);

/* parse.c */
bool getword (char *line, int *pos, char *word, bool allow_slash_or_bracket);
SYM_T retsym (char *line, char *word, int *pos, bool allow_colon);
bool getpipeline (char *line, int *pos, char *pipeline, bool sts);
SYM_T intercom (char *line, int *pos, int *wpid, int *outpfd,
		bool pipedin, int fromfile);

/* var.c */
char *vget (char *vname);
char *vwget (char *vname, int wnum);
bool export (char *vname, char *opt);
void makenvpath (void);
void makenventry (char *vname);
void makenv (void);
void vset (char *vname, char *vval);
void vadd (char *vname, char *vval);
void vdel (char *vname);
void venvdel (char *vname);
void vprint (void);
void venvprint (void);
void copyenv (char *newenv[], char *envp[]);
void loadenv (void);

#endif /* __NO_PROTO__ */
#endif /* __STDC__ */
//E*O*F header.h//

exit 0

wtoomey@gara.une.oz (Warren Toomey) (08/24/89)

Just checking that you're awake & got all the files - full marks to
those who are reading this! Actually, there are only two (2) shar
files, but I can't count. Callum says `Don't try to unshar this!'.
There are a few (!) lint messages with Clam1.3, so the next patches
may include fixes to pacify lint.

	Cheers all,

		Warren.