[net.sources] PCB part 1 of 10

agn@cmu-cs-unh.ARPA (Andreas Nowatzyk) (08/08/85)

#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting Makefile...
cat >Makefile <<'!E!O!F!'
main: pcb

pcb: pmain.c pparm.h pcdst.h part1.o part2.o pplace.o pwide.o pupdate.o cmu.o
	cc -O -o pcb pmain.c part1.o part2.o pplace.o pwide.o pupdate.o cmu.o -lm

part1.o: pparm.h pcdst.h paed.o psub.o pdiag.o pcif.o pmap.o patr.o pfio.o pstat.o
	ld -r -o part1.o paed.o psub.o pdiag.o pcif.o pmap.o patr.o pfio.o pstat.o

part2.o: pcdst.h pparm.h pwork.o pcmdl.o pmnrt.o pleer.o pleer1.o pleer2.o pplow.o
	ld -r -o part2.o pwork.o pcmdl.o pmnrt.o pleer.o pleer1.o pleer2.o pplow.o

pplace.o: pplace.c pparm.h pcdst.h
	cc -O -c pplace.c

pmap.o: pmap.c pparm.h pcdst.h
	cc -O -c pmap.c

pdiag.o: pdiag.c pparm.h pcdst.h
	cc -O -c pdiag.c

pleer.o: pleer.c pparm.h pcdst.h pleer.h
	cc -O -c pleer.c

pleer1.o: pleer1.c pparm.h pcdst.h pleer.h
	cc -O -c pleer1.c

pleer2.o: pleer2.c pparm.h pcdst.h pleer.h
	cc -O -c pleer2.c

pmnrt.o: pmnrt.c pparm.h pcdst.h
	cc -O -c pmnrt.c

patr.o: patr.c pparm.h pcdst.h pleer.h
	cc -O -c patr.c

psub.o: psub.c pparm.h pcdst.h
	cc -O -c psub.c

paed.o: paed.c pparm.h pcdst.h
	cc -O -c paed.c

pfio.o: pfio.c pparm.h pcdst.h
	cc -O -c pfio.c

pwork.o: pwork.c pparm.h pcdst.h
	cc -O -c pwork.c

pcif.o: pcif.c pparm.h pcdst.h
	cc -O -c pcif.c

pcmdl.o: pcmdl.c pparm.h pcdst.h
	cc -O -c pcmdl.c

pplow.o: pplow.c pparm.h pcdst.h
	cc -O -c pplow.c

pstat.o: pstat.c pparm.h pcdst.h
	cc -O -c pstat.c

pwide.o: pwide.c pparm.h pcdst.h
	cc -O -c pwide.c

pupdate.o: pupdate.c pparm.h pcdst.h
	cc -O -c pupdate.c

cmu.o: getbool.o getint.o getfloat.o wantread.o wantwrite.o fwantread.o fwantwrite.o openp.o getstr.o searchp.o
	ld -r -o cmu.o getbool.o getint.o getfloat.o wantread.o wantwrite.o fwantread.o fwantwrite.o openp.o getstr.o searchp.o

getbool.o: getbool.c
	cc -O -c getbool.c

getfloat.o: getfloat.c
	cc -O -c getfloat.c

getint.o: getint.c
	cc -O -c getint.c

wantread.o: wantread.c
	cc -O -c wantread.c

wantwrite.o: wantwrite.c
	cc -O -c wantwrite.c

fwantread.o: fwantread.c
	cc -O -c fwantread.c

fwantwrite.o: fwantwrite.c
	cc -O -c fwantwrite.c

searchp.o: searchp.c
	cc -O -c searchp.c

openp.o: openp.c
	cc -O -c openp.c

getstr.o: getstr.c
	cc -O -c getstr.c
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting READ.ME...
cat >READ.ME <<'!E!O!F!'
This directory contains the source files to PCB V1.24:

PCB is a PC board editor with integrated routers. It was writen
for a VAX running UNIX V4.1 BSD that has a AED-512 graphic terminal
and a Versatec V-80 electrostatic plotter attached.

The PCB source files are:

	paed.c	patr.c	pcdst.h	pcif.c	pcmdl.c	pdiag.c	pfio.c	pleer2.c
	pleer.c	pleer.h	pmain.c	pmap.c	pmnrt.c	pparm.h	pplow.c	pleer1.c
	pstat.c	psub.c	pwide.c	pwork.c	pplace.c pupdate.c

Other files:

	pcb.mss		A manual for PCB in SCRIBE-format
	pcb.1		Unix manual page
	pcbsdef.CIF	The standart CIF library for PCB
	Makefile	Compilation commands
	displays	Sample display location file
	mosis_pcb.txt	MOSIS documentation on their PC board service
	test.cp		Sample componet file
	test.nl		Sample netlist
	test.ty		Sample type file

The following source file are functions of the CMU library that are
used by PCB. These routines were included with permission from CMU.
<leagal mumble saying that you should be thankful that you may use
 this code and the CMU will get mad if you use it to make money>

	fwantread.c	fwantwrite.c	getbool.c	getfloat.c
	getint.c	getstr.c	openp.c		searchp.c
	wantread.c	wantwrite.c

Please send all bug reports, suggestions and improvements to:

		Andreas.Nowatzyk@cmu-cs-vlsi.arpa
	or	...!seismo!cmu-cs-vlsi!agn

However, I do not promise to do anything about it.

	Have fun  --  Andreas
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting change.log...
cat >change.log <<'!E!O!F!'
7/4/85	Redundant extern declarations of members of <stdio.h> removed.
	Redundant "string.h" is no longer referenced. This should
	avoid warnigs on BSD 4.2 systems.
7/8/85  CRMOD added to the AED terminal line initialization. This should
	help on other systems.
7/23/85 r0 in fillet hole routine reduced to 72 (from 82) because of
	potential interaction with nearby via-holes: if the via-hole
        is positioned 6/4 uints from the component hole AND a wire
        leaves the component hole diagonally towards the unrelated
	via hole, the seperation between fillet and wire becomes
        6.5 mil (instead of 8 mil) with the old fillet size.
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting displays...
cat >displays <<'!E!O!F!'
/dev/tty04 /dev/tty03 aed513
/dev/tty00 /dev/tty01 aed513
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting fwantread.c...
cat >fwantread.c <<'!E!O!F!'
/*  fwantread  --  attempt to open file for input
 *
 *  Usage:  f = fwantread (path,file,fullname,prompt);
 *	FILE *f;
 *	char *path,*file,*fullname,*prompt;
 *
 *  Fwantread will search through the specified path for the
 *  specified file, attempting to open it for input if it is
 *  found.  If no such file is found, the user is given
 *  an opportunity to enter a new file name (after the prompt is
 *  printed).  The new file will then be sought using the same
 *  path.
 *  If the path is the null string, the file will be searched for
 *  with no prefix.  If the file name is null, the user will be
 *  prompted for a file name immediately.  The user can always
 *  abort fwantread by typing just a carriage return to the prompt.
 *  Fwantread will put the name of the successfully opened file into
 *  the "fullname" string (which therefore must be long enough to hold a
 *  complete file name), and return its file pointer; if no file
 *  is successfully found, 0 is returned.
 *
 *  HISTORY
 * 21-Oct-81  Fil Alleva (faa) at Carnegie-Mellon University
 *	Fixed bug which caused an infinite loop when getstr() got
 *	an EOT error and returned NULL. The error return was ignored
 *	and the value of "answer" was not changed which caused the loop.
 *
 * 28-Aug-80  Mike Accetta (mja) at Carnegie-Mellon University
 *	Fixed bug which used the "file" string to hold name typed at terminal
 *	even though "file" may have been passed as a constant.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Created for VAX.  Nobody can anticipate if it's a win or a lose
 *	to use path-searching; we'll have to see.
 *
 */

#include <stdio.h>

int strcmp();
FILE *fopenp();
char *getstr();

FILE *fwantread (path,file,fullname,prompt)
char *path,*file,*fullname,*prompt;
{
	register FILE *value;
	char myfile[200], *retval;

	if (*file == '\0') {
		getstr (prompt,"no file",myfile);
		if (strcmp(myfile,"no file") == 0)  return (0);
	}
	else
	    strcpy(myfile, file);

	do {
		value = fopenp (path,myfile,fullname,"r");
		if (value == 0) {
			if (*path && (*myfile != '/')) {
				sprintf (fullname,"Want to read %s in path \"%s\"",myfile,path);
			}
			else {
				sprintf (fullname,"Want to read %s",myfile);
			}
			perror (fullname);
			retval = getstr (prompt,"no file",myfile);
			if ((strcmp(myfile,"no file") == 0) || retval == NULL)
			    return (0);
		}
	} 
	while (value == 0);

	return (value);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting fwantwrite.c...
cat >fwantwrite.c <<'!E!O!F!'
/*  fwantwrite  --  attempt to open file for output
 *
 *  Usage:  f = fwantwrite (path,file,fullname,prompt,warn);
 *    FILE *f;
 *    int warn;
 *    char *path,*file,*fullname,*prompt;
 *
 *  Fwantwrite will attempt to open "file" for output somewhere in
 *  the pathlist "path".  If no such file can be created, the user
 *  is given an oportuity to enter a new file name (after the
 *  prompt is printed).  The new file will then be sought using
 *  the same path.
 *  If the path is the null string, the file will be created with
 *  no prefix to the file name.  If the file name is null, the
 *  user will be prompted for a file name immediately.  The user
 *  can always abort fwantwrite by typing just a carriage return
 *  to the prompt.
 *  Fwantwrite will put the name of the successfully created file
 *  into the "fullname" string (which must therefore be long enough to
 *  hold a complete file name), and return its file pointer;
 *  if no file is created, 0 will be returned.
 *  Fwantwrite examines each entry in the path, to see if the
 *  desired file can be created there.  If "warn" is true, 
 *  fwantwrite will first check to ensure that no such file
 *  already exists (if it does, the user is allowed to keep it).
 *  If no such file exists (or the user wants to delete it), then
 *  fwantwrite attempts to create the file.  If it is unsuccessful,
 *  the next entry in the pathlist is examined in the same way.
 *
 *  HISTORY
 * 21-Oct-81  Fil Alleva (faa) at Carnegie-Mellon University
 *	Fixed bug which caused an infinite loop when getstr() got
 *	an EOT error and returned NULL. The error return was ignored
 *	and the value of "answer" was not changed which caused the loop.
 *
 * 28-Aug-80  Mike Accetta (mja) at Carnegie-Mellon University
 *	Fixed bug which used "file" instead of "myfile" in call to
 *	searchp.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Created for VAX.
 *
 */

#include <stdio.h>

int strcmp();
FILE *fopen();
int searchp();
char *getstr();

static int warnflag;
static FILE *filptr;

static int func (fnam)
char *fnam;
{		/* attempt to create fnam */
	register int goahead;
	register int fildes;

	goahead = 1;
	if (warnflag) {
		fildes = open (fnam,1);
		if (fildes >= 0) {
			close (fildes);
			printf ("%s already exists!  ",fnam);
			goahead = getbool ("Delete old file?",0);
		}
	}
	if (goahead) {
		filptr = fopen (fnam,"w");
		if (filptr == 0) {
			goahead = 0;
		}
	}
	return (!goahead);
}

FILE *fwantwrite (path,file,fullname,prompt,warn)
char *path,*file,*fullname,*prompt;
int warn;
{
	register int i;
	char myfile[200], *retval;

	if (*file == '\0') {
		getstr (prompt,"no file",myfile);
		if (strcmp(myfile,"no file") == 0)  return (0);
	}
	else strcpy (myfile,file);

	warnflag = warn;
	do {
		i = searchp (path,myfile,fullname,func);
		if (i < 0) {
			if (*path && (*myfile != '/')) {
				printf ("%s in path \"%s\":  Can't create.\n",myfile,path);
			} 
			else {
				perror (myfile);
			}
			retval = getstr (prompt,"no file",myfile);
			if ((strcmp(myfile,"no file") == 0) || retval == NULL)
			    return (0);
		}
	} 
	while (i < 0);

	return (filptr);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting getbool.c...
cat >getbool.c <<'!E!O!F!'
/*  getbool -- ask user a yes/no question
 *
 *  Usage:  i = getbool (prompt, defalt);
 *
 *  Example:  do {...} while (getbool ("More?",1));
 *
 *  Prints prompt string, asks user for response.  Defalt is
 *  0 (no) or 1 (yes), and is used if user types just carriage return,
 *  or on end-of-file or error in the standard input.
 *
 *  HISTORY
 * 23-Oct-82  Steven Shafer (sas) at Carnegie-Mellon University
 *	Added code to return default if gets returns NULL.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Rewritten for VAX.  Possible changes for the future:  accept "t" (true)
 *	and "f" (false), 0 and 1, etc.
 *
 */

#include <stdio.h>
#define TRUE 1
#define FALSE 0

int getbool (prompt, defalt)
char *prompt;
int defalt;
{
	register int valu;
	register char ch;
	char input [100];

	if (defalt != TRUE && defalt != FALSE)  defalt = TRUE;
	valu = 2;				/* meaningless value */
	do {
		printf ("%s  [%s]  ",prompt,(defalt ? "yes" : "no"));
		fflush (stdout);			/* in case it's buffered */
		if (gets (input) == NULL) {
			valu = defalt;
		}
		else {
			ch = *input;			/* first char */
			if (ch == 'y' || ch == 'Y')		valu = TRUE;
			else if (ch == 'n' || ch == 'N')	valu = FALSE;
			else if (ch == '\0')		valu = defalt;
			else printf ("Must begin with 'y' (yes) or 'n' (no).\n");
		}
	} 
	while (valu == 2);			/* until correct response */
	return (valu);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting getfloat.c...
cat >getfloat.c <<'!E!O!F!'
/*  getfloat --  prompt user for float
 *
 *  Usage:  f = getfloat (prompt,min,max,defalt)
 *	float f,min,max,defalt;
 *	char *prompt;
 *
 *  Getfloat prints the message:  prompt  (min to max)  [defalt]
 *  and accepts a line of input from the user.  If the input
 *  is not null or numeric, an error message is printed; otherwise,
 *  the value is converted to a float (or the value "defalt" is
 *  substituted if the input is null).  Then, the value is
 *  checked to ensure that is lies within the range "min" to "max".
 *  If it does not, an error message is printed.  As long as
 *  errors occur, the cycle is repeated; when a legal value is
 *  entered, this value is returned by getfloat.
 *  The default is returned on EOF or error in the standard input.
 *
 *  HISTORY
 *  5-Nov-84  Glenn Marcy (gm0w) at Carnegie-Mellon University
 *	Changed i to a double for extra precision in comparisons.
 *
 * 23-Oct-82  Steven Shafer (sas) at Carnegie-Mellon University
 *	Added code to return default on error or EOF on standard input.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Created for VAX.
 *
 */

#include <stdio.h>
#include <ctype.h>
#include <math.h>

float getfloat (prompt,min,max,defalt)
float min,max,defalt;
char *prompt;
{
	char input [200];
	register char *p;
	register int err;
	double i;
	do {

		printf ("%s  (%g to %g)  [%g]  ",prompt,min,max,defalt);
		fflush (stdout);

		err = 0;
		if (gets(input) == NULL) {
			i = defalt;
			err = (i < min || max < i);
		}
		else {
			for (p=input; *p &&
		 	(isdigit(*p) || *p=='-' || *p=='.' || *p=='+'
			  || *p=='e' || *p=='E');
			 p++);
			if (*p) {		/* non-numeric */
				err = 1;
			} 
			else {
				if (*input)	i = atof (input);
				else		i = defalt;
				err = (i < min || max < i);
			}
		}

		if (err) printf ("Must be a number between %g and %g\n",
		min,max);
	} 
	while (err);

	return (i);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting getint.c...
cat >getint.c <<'!E!O!F!'
/*  getint --  prompt user for int
 *
 *  Usage:  i = getint (prompt,min,max,defalt)
 *	int i,min,max,defalt;
 *	char *prompt;
 *
 *  Getint prints the message:  prompt  (min to max)  [defalt]
 *  and accepts a line of input from the user.  If the input
 *  is not null or numeric, an error message is printed; otherwise,
 *  the value is converted to an int (or the value "defalt" is
 *  substituted if the input is null).  Then, the value is
 *  checked to ensure that is lies within the range "min" to "max".
 *  If it does not, an error message is printed.  As long as
 *  errors occur, the cycle is repeated; when a legal value is
 *  entered, this value is returned by getint.
 *  On error or EOF in the standard input, the default is returned.
 *
 *  HISTORY
 * 23-Oct-82  Steven Shafer (sas) at Carnegie-Mellon University
 *	Added code to return default on EOF or error in standard input.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Rewritten for VAX.
 *
 */

#include <stdio.h>
#include <ctype.h>

int getint (prompt,min,max,defalt)
int min,max,defalt;
char *prompt;
{
	char input [200];
	register char *p;
	register int i,err;

	do {

		printf ("%s  (%d to %d)  [%d]  ",prompt,min,max,defalt);
		fflush (stdout);

		if (gets (input) == NULL) {
			i = defalt;
			err = (i < min || max < i);
		}
		else {
			err = 0;
			for (p=input; *p && (isdigit(*p) || *p == '-' || *p == '+'); p++) ;
	
			if (*p) {		/* non-numeric */
				err = 1;
			} 
			else {
				if (*input)	i = atol (input);
				else		i = defalt;
				err = (i < min || max < i);
			}
		}

		if (err) printf ("Must be a number between %d and %d\n",
		min,max);
	} 
	while (err);

	return (i);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting getstr.c...
cat >getstr.c <<'!E!O!F!'
/*  getstr --  prompt user for a string
 *
 *  Usage:  p = getstr (prompt,defalt,answer);
 *	char *p,*prompt,*defalt,*answer;
 *
 *  Getstr prints this message:  prompt  [defalt]
 *  and accepts a line of input from the user.  This line is
 *  entered into "answer", which must be a big char array;
 *  if the user types just carriage return, then the string
 *  "defalt" is copied into answer.
 *  Value returned by getstr is just the same as answer,
 *  i.e. pointer to result string.
 *  The default value is used on error or EOF in the standard input.
 *
 *  HISTORY
 * 23-Oct-82  Steven Shafer (sas) at Carnegie-Mellon University
 *	Added code to copy default to answer (in addition to Fil's code to
 *	return NULL) on error or EOF in the standard input.
 *
 * 21-Oct-80  Fil Alleva (faa) at Carnegie-Mellon University
 *	Getstr() now percuolates any errors from gets() up to the calling
 *	routine.
 *
 * 19-May-80  Steven Shafer (sas) at Carnegie-Mellon University
 *	Increased buffer size to 4000 characters.  Why not?
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Rewritten for VAX.  Mike thinks a 0 pointer for the default should
 *	print no default (i.e. not even braces); I'm not sure I like the idea
 *	of a routine that doesn't explicitly tell you what happens if you
 *	just hit Carriage Return.
 *
 */

#include <stdio.h>

char *getstr (prompt,defalt,answer)
char *prompt,*defalt,*answer;
{
	char defbuf[4000];
	register char *retval;

	printf ("%s  [%s]  ",prompt,defalt);
	fflush (stdout);
	strcpy (defbuf,defalt);
	retval = (char *) gets (answer);
	if (retval == NULL || *answer == '\0')  strcpy (answer,defbuf);
	if (retval == NULL)
	    return (retval);
	else
	    return (answer);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting mosis_pcb.txt...
cat >mosis_pcb.txt <<'!E!O!F!'
Messages from file DSKC:MAIL.MSG[C410AN90]@CMU-CS-A.ARPA
				on Monday, 10 June 1985 at 2344-EDT:

253?-+10 Jun 85 s r t MOSIS@ISIF@USC Topic: PCBFAB (5851)
254?-+10 Jun 85 s r t MOSIS@ISIF@USC Topic: PCBTEK (23201)

------------------------------------------------------------------------------

----Message 253 (5851 chrs) is----
Return-Path:<VLSI@USC-ISIF.ARPA>
Received: from USC-ISIF.ARPA by CMU-CS-A.ARPA; 10 Jun 85 23:23:15 EDT
Date: 10 Jun 1985 20:20 PDT
From: The MOSIS System <VLSI@USC-ISIF> (send requests to MOSIS@ISIF)
Subject: Topic: PCBFAB
To: Andreas.Nowatzyk@CMU-CS-A.ARPA
Your-message-sent: Mon, 10 Jun 85 23:06 EDT
Your-Message-ID: <10Jun85.230636.AN90@CMU-CS-A.ARPA>
MOSIS-Message-ID: 85061069502


		   STANDARD PCB FABRICATION INSTRUCTIONS
		   =====================================

Instructions for users
----------------------

Following is the standard PCB fabrication specifications template.
When submitting instructions for a project, users must edit the
following items:

***************************
* 1. Which layers present *
***************************

***************************
* 2. Project feature size *
***************************

***********************
* 3. Board dimensions *
***********************

*********************************
* 4. Number of boards requested *
*********************************

******************************************
* 5. Sizes and quantities of drill holes *
******************************************

to reflect the actual project specifications.  Users may then submit
the ENTIRE template as fabrication instructions via REQUEST:ATTENTION
message to MOSIS@USC-ISIF (naming project ID in subject field).

Should additional items need modification, please flag them in the
template AND send a separate ATTENTION message requesting clearance.

Fabrication instructions are read by MOSIS Project PCB staff.  Feel free to
include comments and questions in the template and/or additional ATTENTION
messages.





			SPECIFICATIONS TEMPLATE

Tolerances for positions are given by diameter-of-true-position to
be measured according to MIL-P-55110-C.  Tolerances for sizes are +/-.
Hole sizes are of the finished holes, e.g., after plating.

***********************************************************
* 1. Indicate which artwork layers are present (1:1)      *
*                                                         *
*    PC1  - Component side #1                             *
*    PN2  - Power plane #2                                *
*    PN3  - Ground plane #3                               *
*    PC4  - Solder side #4                                *
*    PSMC - Solder mask (component)                       *
*    PSMS - Solder mask (solder)    **optional**          *
*    PSSC - Silkscreen (component)  **optional**          *
*    PSSS - Silkscreen (solder)     **optional**          *
*    PD   - Drill layer (PTH, plated-thru-holes)          *
*    PDNP - Drill layer (non-PTH)   **optional**          *
*                                                         *
*    The above layers are for a typical 4-layer board.    *
*    For 2-layer boards please use PC1 and PC2 for the    *
*    component and the solder side, respectively.  For    *
*    other #-layer boards, use layer names of the form    *
*    PCn or PNn, where n is the serial number of the      *
*    layer, starting with the component side.             *
***********************************************************

********************************************************
* 2. Project feature size (line width/spacing): ?.???" *
********************************************************

***********************************************************************
* 3. Board dimensions:  ?? x ?? (typically up to 18.000"  x  16.000") *
***********************************************************************

************************************
* 4. Number of boards requested: ? *
************************************

*******************************************
* 5. Sizes and quantities of drill holes: * 
*        0.???, ?# holes                  *
*        0.???, ?# holes                  *
*        0.???, ?# holes                  *
*******************************************

 6. Layers: 4 layers, with internal layers for power and ground. 

 7. Etching tolerance:  +/-0.002

 8. PTH (after plating) size tolerance: +/-0.003"

 9. Holes position tolerance: 0.003" diameter true position.

10. All drill holes are on 0.025" grid

11. Hole plating copper thickness: 0.001" min

12. Copper on external layers:  1 oz. copper before plating.

13. Copper on internal layers:  1 oz. copper.

14. Layer-to-layer registration: 0.005"

15. Minimum annular ring width for all circular and square pads: 0.005"
    This does not apply to shaven pads.

16. Material: epoxy glass laminate.  Must meet UL 94V-0 and UL 94V-1
    flammability specifications.

17. Board thickness across connector finger area: 0.062" +/-0.007"

18. Edge connectors electroplating: min 0.000050" gold over 0.000050" nickel

19. Area to be gold plated:   Defined by engineering drawing.

20. Outside board dimensions tolerance: at edge connectors: +/-0.007"
                                                 elsewhere: +/-0.015"

21. Solder mask: dry film preferred (both sides)

22. Solder plate: 0.0003" min plus fuse all conductive surfaces

23. Solder mask-solder side:  If no artwork is provided for solder mask-solder
    side, the solder mask-component side will be used for the solder side.

24. Silk screen color: white

25. Engineering drawing

* Drawing Tolerances: .XX        +/- 0.010"
                      .XXX       +/- 0.005"
                       angles    +/- 1 degree

* Center of fingers to end of edge-connector: 0.086"

* Bevel: Connector finger outside corners: 0.03" x 45 degrees 2 places,
                    Board outside corners: 0.04" x 45 degrees 4 places.

* Board inside corners: 0.06" max Radius, 2 places.

* Chamfer: Connector finger edge: 0.015" x 30 degrees.
----Message 254 (23201 chrs) is----
Return-Path:<VLSI@USC-ISIF.ARPA>
Received: from USC-ISIF.ARPA by CMU-CS-A.ARPA; 10 Jun 85 23:34:38 EDT
Date: 10 Jun 1985 20:20 PDT
From: The MOSIS System <VLSI@USC-ISIF> (send requests to MOSIS@ISIF)
Subject: Topic: PCBTEK
To: Andreas.Nowatzyk@CMU-CS-A.ARPA
Your-message-sent: Mon, 10 Jun 85 23:06 EDT
Your-Message-ID: <10Jun85.230636.AN90@CMU-CS-A.ARPA>
MOSIS-Message-ID: 85061069502

                               THE MOSIS SYSTEM
                            PCB FABRICATION SERVICE



Table of Contents

1. Introduction                                                
2. General Information                                         
3. Submitting projects                                         
4. Fabrication instructions                                    
5. CIF layers                                                  
6. CIF to film design rules                                    
7. CIF to PCB design rules                                     
8. Miscellaneous recommendations                               
   8.(A) Plated-Through-Holes (PTHs) for 4-layer boards        
   8.(B) Components and vias for layers 1 and 4                
   8.(C) Component connection to power (PN2) and ground (PN3)  
   8.(D) Connection of signals to power (PN2) and to ground (PN3)


1. Introduction

PCBs,  like  integrated  circuits,  are fabricated by a process that produces a
series of two-dimensional images of possibly different properties,  constructed
on  top  of one another.  The conducting and insulating layers communicate with
each other  through  vias  with  patterns  for  that  purpose,  and  also  have
electrical  interaction where certain spatial relations hold, i.e., transistors
and inter-layer impedance.

Although PCBs and ICs are made of different  materials,  they  share  a  common
method  of  specification of the images required on each of their layers.  Both
are fabricated by a "photographic" process which transfers images to the  media
surface from a master tooling.

The  single  most important difference between these technologies is the scale,
or "feature size".  A typical IC device has a feature size of 3 microns  and  a
size  of 6mm; hence it is 1,000 line-pairs across.  A typical PCB has a feature
size of 0.004 inches and a size of 15 inches; hence 2,000  line-pairs.    These
numbers  show that the resolution of the tooling is not significantly different
between these two technologies.  The most significant  difference,  as  far  as
fabrication  preparation  (the  job  of MOSIS) is concerned, is the size.  Both
technologies use 1X tooling.

Realizing these similarities and differences, the MOSIS user community  decided
to  extend their VLSI design and fabrication tools to accommodate PCBs as well.
The simple first steps already taken treat PCBs as yet another technology, with
its  own  set  of conventions, standard cells and, obviously, its own geometric
and electric design rules.  As with IC designs, the PCB patterns are  expressed
in  CIF;  from the viewpoint of the user, MOSIS treats the geometric processing
required to convert CIF into tooling  for  PCBs  just  as  it  does  any  other
technology.

These technologies differ significantly in fabrication philosophy.  The unit of
production in the IC arena is a wafer which may have many different  die-types,
each  possibly with several independent projects.  PCBs, on the other hand, are
rarely combined in the fabrication process.  Therefore, MOSIS  does  not  apply
its  standard  Multi-Project-Chip  and Multi-Chip-Wafer procedures to PCBs, but
fabricates them one at a time.

Conventional tooling for ICs is a set of 1X masks, typically 5  inches  square.
The  conventional  tooling  for  PCBs is a set of 1X films, typically 20 inches
square.  The former  are  usually  made  by  E-beam  machines,  the  latter  by
photo-plotters (and soon also by lasers).

Neither  E-beam  machines  nor  photo-plotters can use the CIF format directly.
These families of equipment require data formats of totally different  natures:
E-beam  machines are most efficient while traversing a predefined scan, whereas
the electro-mechanical photo-plotters enjoy the ability to use  random  motion.
All the upcoming laser writers are expected to be similar to the E-beam pattern
generators rather than to the conventional electro-mechanical photo-plotters.

Due  to  the  limitation  of  the  old  photo-mechanical  equipment  used   for
photo-plotters,  all  of  the  data  formats  ("languages") suffer from various
archaic idiosyncracies, guaranteed to rule out any compatibility among  various
vendors.

Complying  with these idiosyncracies and passing them to the designers (in form
of design rules, for example) is diametrically opposed to the MOSIS philosophy.
It  was  therefore  decided  to  stay  with the same "combat proven" IC tooling
preparation method for PCBs.  Hence, MOSIS genertes the patterns  for  all  PCB
layers  by  using  E-beam  technology, which produces high-quality glass plates
instead of larger patterns on sheets of film.

Economy, the availability of software for E-beam machines,  and  the  ratio  of
feature size between IC and PCB technologies suggested that the glass plates be
made at 0.05X.  This scale allows  the  generation  of  16  patterns,  each  of
20"x20"  target  size,  on  a standard 5"x5" plate.  A simple (and inexpensive)
photographic process is used to transfer these images from the glass plates  to
film  sheets.    The  required magnification of 20X is an integral part of this
photographic process.  The  resolution  of  the  photographic  process  has  to
support only 2,000 line-pairs across the whole image, well under the limitation
of good lenses.

This approach of using a common tooling preparation methodology  for  both  ICs
and  PCBs  has many advantages: it allows designers to use common tools for the
design process (with details tailored  specifically  to  each  technology)  and
allows  MOSIS  to apply the same management procedures and the same geometrical
processing and tooling preparation methods to PCB technology.

An important and unexpected benefit of this approach is the  existence  of  the
master tooling on high-quality glass, which does not flex, stretch, scratch, or
deteriorate with time.  It is easy and common to  protect  glass  mask  masters
from environmental hazards.

Probably  the  most important feature of the expansion of MOSIS to include PCBs
is that the expansion has been done in a way which is expected to carry over to
other  packaging  technologies,  such as various hybrids, ceramic carriers, and
plastic tapes.

MOSIS has already published design rules, recommended procedures,  and  various
standard  cells  and  design  frames  for  PCBs, and the service is being used.
Typical turnaround time from receipt of CIF to delivery of boards is 3-4 weeks.

By adhering to the notion of  separation  of  design  from  fabrication,  MOSIS
refused  to  burden  its  users  with  many  of  the traditional idiosyncracies
involved  in  PCB  design,  especially  those  arising  from   aperture-related
constraints.    Although unconventional, the route to PCB tooling through 0.05X
E-beam masks has proven to be not only versatile, but economical.


                                Acknowledgement

The MOSIS Service wishes to thank Chuck Seitz of Caltech for helping to develop
the PCB service.


2. General Information


      MOSIS  assumes  that  users  submitting  PCB  projects  know  what is
    necessary for designing PCBs. MOSIS does not  verify  in  any  way  the
    validity of the designs and is not currently able to teach users how to
    design PCBs.  Users who are familiar with PCB design are encouraged  to
    share their knowledge with MOSIS.


In  order  to  support  fast  turnaround  fabrication of PCBs, MOSIS offers the
following services to its user community:

        *** CIF to films
        *** CIF to up to 8-layer PCBs

The CIF used for specifying films and/or PCBs  should  be  submitted  to  MOSIS
according to the CIF/PCB and MOSIS/PCB design rules and conventions included in
both this manual and the  MOSIS  information  service  via  REQUEST:INFORMATION
messages specifying the following topics:

PCBFAB.INF                    Fabrication specifications template to be
                              edited and submitted to MOSIS via ATTENTION
                              message for each PCB project.

DIPS.CIF                      Contains CIF symbols for various common DIPs
                              to use in a (4-layer) PC board layout.

PCSAM1.CIF                    Contains a sample 4-layer PC board CIF file 
                              with power as PN2 and ground as PN3.
                              Illustrates the design style of PCBTEK and 
                              the use of the various design layers.

The DRs are not lambda based.

Users who request CIF to film plotting have to comply with the CIF-to-film/DRs.
Users who request  CIF  to  PCB  fabrication  have  to  comply  with  both  the
CIF-to-film-DRs and with the CIF-to-PCB-DRs.

A  discussion  of  values  regarding  line  width,  spacing,  margins,  current
limitations, preferred grid, gold line specification, etc., is included in this
manual.


3. Submitting projects

Technology name: "PCB1".

Every project must start with a NEW-PROJECT request with the usual parameters.

The PCB FABRICATE request differs from the typical IC FABRICATE request only in
that an ATTENTION parameter containing  the  specification  "OUTPUT"  with  the
following values must be included:


OUTPUT: ART             for films
OUTPUT: PCBOARD         for (bare) PC-board fabrication
OUTPUT: ART/PCBOARD     for both


Sample FABRICATE request:


REQUEST: FABRICATE
    ID:          .....
    P-Password:  .....
    Technology:  PCB1
    Lambda:      10 mils (the minimum width/spacing in mils!!)
    Size:        18000 x 16000 mils
    Attention:   (a) OUTPUT required (ART and/or PCBOARD)
                 (b) fabrication-instructions and spec's ...
                     .......................................
                 (c) Other requests/information, as needed
    CIF:
                 ............................
                 ............................
                 END
REQUEST: END


The SIZE parameter should be in mils and should refer to the dimensions of
the finished board, not including the differential plating bars, engineering
drawing, etc.  Hence, the SIZE is not the MBB of the CIF file (as it is for
MOS).

Some  (or  all)  of  the  above  parameters  may be pre-submitted either in the
NEW-PROJECT or by  using  the  SUBMIT  request  before  requesting  the  actual
fabrication.

CIF-fragments, CIF-checksum and CIF-FTP may be used for submitting long files.


4. Fabrication instructions

Fabrication  instructions must be transmitted to MOSIS via ATTENTION as soon as
possible.  Please examine instructions and suggested specs in  TOPIC:PCBFAB.INF
(Appendix "Fabrication specifications template").

When  submitting these text instructions via ATTENTION to MOSIS please mark all
items that vary from our recommendation by inserting a row  of  asterisks  both
before  and  after  differences.    PCB  staff  will  then  clear  your special
requirement(s) with the board fabricator.

The engineering drawing (Layer PF) should show the board outline "crop  marks",
the  gold  line (end line of the gold plating), and the coordinates origin. The
board outline should be specified by using a (closed) wire of 1 mil width  (NOT
A POLYGON).


5. CIF layers

The following layers are supported:

        PCn or PNn for n=1,2,3....8
        PSSC       silk screen, component side
        PSSS       silk screen, solder side
        PSMC       solder mask cuts, component side
        PSMS       solder mask cuts, solder side

        PD         drill (plated-through-holes, PTH)
        PDNP       drill (non-plated-through-holes, NPTH)

        PF         engineering drawing of the finished board

The  R  commands  on the PD and the PDNP layers are used for defining the drill
position.  All other commands on these layers will  be  included  in  a  "drill
plot",  if any, but do not affect the drilling operations.  

The maximum film size is  approximately  20"  by  25".  For  larger  sizes  use
ATTENTION.

The  standard  film  plotting is black features/geometry (as defined by CIF) on
clear background/field.  For reverse plotting of any layer use ATTENTION.

Note that both PCn and PNn are plotted with the same polarity even though  they
have  opposite  electrical  meaning.    It  is  a standard practice to have the
internal layers (e.g., PN2 and PN3) reversed in the fabrication process.

DD, as usual, is not supported by MOSIS CIF reader(s).


6. CIF to film design rules

MOSIS rounds off all coordinates and sizes to be multiples of:

                [1 mil = 0.001" = 25.4 micron = 2540 CIF-units]

Geometrical conventions:

  -  The layers of an n-layer  PCB  are  assigned  consecutive  numbers,
     according to their order such that the component side is layer #1 and
     the solder side is #n.

  -  If the CIF features on the nth layer define  conductors  then  this
     layer  is  called PCn.  If they define non-conducting areas then this
     layer is called PNn.  Obviously it is illegal to have  both  PCn  and
     PNn for the same value of n.

  -  All  layers  are  drawn as seen from the component side.  Note that
     text to be read from the solder side is specified in CIF in  X-mirror
     image.


7. CIF to PCB design rules

The  CIF  for PCB fabrication must comply with the design rules for CIF-to-film
design rules.  The following rules are required in addition.

For a MOSIS n-layer board (2 <= n <= 8), the following layers are available:

  <M>   PC1          signal layer, component side
  <M>   PCi/PNi      internal power, ground or signal layers (1 < i < n)
  <M>   PCn          signal layer, solder side

  [O]   PSSC         silk screen, component side
  [O]   PSSS         silk screen, solder side

  <M>   PSMC         solder mask cuts, component side
  [O]   PSMS         solder mask cuts, solder side

  <M>   PD           drill (plated-through-holes, PTH)
  [O]   PDNP         drill (non-plated-through-holes, NPTH)

  <M>   PF           engineering drawing of the finished board 


<M> indicates the mandatory layers.  [O] indicates the optional layers.

For boards requiring more than 8 layers notify MOSIS via ATTENTION.

*If no PSMS is supplied then PSMC is used for both sides.

*If no PDNP is supplied then all holes are plated through.

Edge  connectors  have  to  be  extended  on  the  outside layers to the end of
differential plating bars (300 to 500 mil) and be  bussed  together  along  the
edge by a wire of 20 mil width.

All  layers except the internal ones (e.g., PN2 and PN3), including the drills,
should include "crop marks" which are 0.050" wide and  0.250"  to  0.500"  long
along  corners  (from the outside of both inside and outside corners, at 0.010"
to 0.015" off the board edge).  This can be done with the Wire command of  CIF,
with width of 0.050" and with center line 0.035" outside.

Example  of  "crop-marks"  and of differential plating bars may be found in the
PCSAM1.CIF file in the MOSIS library.

No copper should be on the internal layers within 0.100" of the edge of the
board.  (Suggestion: for each non-conducting layer, PNi, trace the outline
of the board with a line of width of 0.200").

No external (i.e., off-board) alignment marks are required, and none should  be
supplied.

All  holes,  both  PTH and NPTH, should be covered with a solder mask (SM).  In
the case of PTH the SM should be a symbol with diameter larger than the  copper
pad  (circle  or box) by 0.004".  In the case of NPTH the SM should be a circle
with diameter larger than the NPTH itself by 0.004".

For most designs the same Solder Mask may be used for both sides.  In this case
please  define  only  the PSMC and use the fabrication instructions text to ask
that the PSMC be used also for the solder side (i.e., as a PSMS).    Aggressive
designs using "shaven pads" may need PSMS different than the PSMC.


8. Miscellaneous recommendations

MOSIS recommends including the outline of all devices on PSSC.

MOSIS  also recommends marking pin#1 of DIPs if PSSS is not defined (or defined
without outline). For example by using non-standard PTH symbol --  to  make  it
easy to recognize pin#1, especially from the solder side.

MOSIS recommends that all component connections to power (e.g., PN2) and ground
(e.g., PN3) should use thermal reliefs on  these  layers.    Other  connections
(e.g., of the edge connectors) to the power and ground layers do not need them.

The  following recommendations for PTHs are for 4-layer boards using a minimum
34 mil hole (after plating) inside 60 mil copper areas with 64 mil solder area.
These  values  are used here as an example.  Check their applicability with any
set of specific design rules.

Note that the use of 10 mil wires with 10 mil spacing permits only one to  wire
pass between adjacent pads of 60 mil diameters on a 100 mil grid.  On the other
hand the use of 8/8 permits 2 wires to pass between such pads.  The use of  5/5
would yield 3 wires.  10/10 is standard conservative practice.  8/8 is becoming
standard.  5/5 is upcoming.

All of the following dimensions are in mils.  Each DS has A/B  =  2540/1,  thus
allowing geometry specification in mils.

8.(A) Plated Through Holes (PTHs) for 4-layer boards

The following symbol is used in the definition of several types of PTHs.


DS 1 2540 1 ; (basic PTH: PC1,PC4,PD,PSMC,PSMS) ;
        L PC1  ;  R 60 0 0 ;
        L PC4  ;  R 60 0 0 ;
        L PD   ;  R 34 0 0 ;
        L PSMC ;  R 64 0 0 ;
(use the following line if and only if PSMS is needed: ) ;
        L PSMS ;  R 64 0 0 ;
DF ;



8.(B) Components and vias for layers 1 and 4

MOSIS  recommends  using  symbol#2 for vias between layers 1 and 4 for signals,
for hand-inserted components, and for sockets.


DS 2 2540 1 ; (PTH for vias, components and sockets) ;
        C    1 ;
        L  PN2 ;  R  75 0 0 ; (avoid power) ;
        L  PN3 ;  R  75 0 0 ; (avoid ground) ;
DF ;


The choice of 80 for the PN2 and PN3 layers is recommended in order to  improve
the  yield at a slight risk of strip line impedance mismatching.  The choice of
60 does improve the strip line impedance matching, at a slight risk of yield.

For machine-inserted components, and for Holtite, MOSIS  recommends  adding  10
mils to all of the above diameters.

8.(C) Component connection to power (PN2) and ground (PN3)

For  hand-inserted  components  and for sockets MOSIS recommends using symbol#3
for power connection and symbol#4 for ground connection.  Symbols  #9  and  #10
are thermal reliefs for the power and ground planes.


DS 3 2540 1 ; (PTH for connecting components to power on PN2) ;
  C   1 ;
  L PN2 ; C  9 ; (#9 is a TR for power) ;
  L PN3 ; R 75 0 0 ;
DF ;

DS 4 2540 1 ; (PTH for connecting components to ground on PN3) ;
  C   1 ;
  L PN2 ; R 75 0 0 ;
  L PN3 ; C  10 ; (#10 is a TR for ground) ;
DF ;


For  machine  insertions and for Holtite MOSIS recommends adding 10 mils to the
above diameters.

8.(D) Connection of signals to power (PN2) and to ground (PN3)

For connection of  non-components  from  PC1  and  PC4  to  power  (PN2)  MOSIS
recommends using symbol#5:


DS 5 2540 1 ; (connect signals to power) ;
        C   1 ;
        L PN2 ; R 10 0 0 ; (this is a guide hole) ;
        L PN3 ; R 75 0 0 ;
DF ;


For  connection  of  non-components  from  PC1  and  PC4  to ground (PN3) MOSIS
recommends using symbol#6:


DS 6 2540 1 ; (Connect signal to ground) ;
        C   1 ;
        L PN2 ; R 75 0 0 ;
        L PN3 ; R 10 0 0 ; (this is a guide hole) ;
DF ;


MOSIS recommends using the following symbol#7 for pin#1 of DIPs:


DS 7 2540 1 ; (square pin#1) ;
        L PC1  ;  B 60 60 0 0 ;
        L PN2  ;  R 75  0 0   ;
        L PN3  ;  R 75  0 0   ;
        L PC4  ;  B 60 60 0 0 ;
        L PD   ;  R 34  0 0   ;
        L PSMC ;  B 64 64 0 0 ;
(use the following line if and only if PSMS is needed: ) ;
        L PSMS ;  B 64 64 0 0 ;
DF ;


MOSIS recommends using the following symbol#8 for alignment marks  on  4  layer
PCBs:


DS 8 2540 1 ; (alignment marks for 4 layers) ;
        L PC1  ; B 40 40  20,20 ; B 40 40 -20,-20 ;
        L PN2  ; B 40 40  20,20 ; B 40 40 -20,-20 ;
        L PN3  ; B 40 40  20,20 ; B 40 40 -20,-20 ;
        L PC4  ; B 40 40  20,20 ; B 40 40 -20,-20 ;
        L PSSC ; B 40 40  20,20 ; B 40 40 -20,-20 ;
        L PSMC ; B 40 40  20,20 ; B 40 40 -20,-20 ;
(use the following line if and only if PSMS is needed: ) ;
        L PSMS ; B 40 40  20,20 ; B 40 40 -20,-20 ;
DF ;


Following  are  examples  of  a  Thermal  Relief (symbol#9 for power on PN2 and
symbol#10 for ground on PN3).  In  this  example  the  TR  is  square,  with  4
"bridges",  ID  of  0.080"  and OD of 0.100".  TRs may be square or round, with
different number of "bridges" and with different IDs and ODs.


DS 9 2540 1 ; L PN2 ; (TR for the power plane) ;
  (square, 4 bridges, outside dimension 0.100", inside 0.080") ;
  B 40 10 -30 -45 ; B 40 10 30 -45 ; B 40 10 -30 45 ; B 40 10 30 45 ;
  B 10 40 -45 -30 ; B 10 40 45 -30 ; B 10 40 -45 30 ; B 10 40 45 30 ;
DF ;

DS 10 2540 1 ; L PN3 ; (TR for the ground plane) ;
  (square, 4 bridges, outside dimension 0.100", inside 0.080") ;
  B 40 10 -30 -45 ; B 40 10 30 -45 ; B 40 10 -30 45 ; B 40 10 30 45 ;
  B 10 40 -45 -30 ; B 10 40 45 -30 ; B 10 40 -45 30 ; B 10 40 45 30 ;
DF ;


MOSIS recommends using symbols like the following symbol#14  for  DIPs.    Note
that  this symbol has already a built-in power connection with a thermal relief
on pin#14 and a ground connection with thermal relief  on  pin#7.    It  has  a
square mark for its pin#1 on both sides.


DS 14 2540 1 ; (DIP-14);
  C 7  T 0,    0 ; (#1) ;        C 3  T 300,    0 ; (#14,power) ;
  C 2  T 0, -100 ; (#2) ;        C 2  T 300, -100 ; (#13) ;
  C 2  T 0, -200 ; (#3) ;        C 2  T 300, -200 ; (#12) ;
  C 2  T 0, -300 ; (#4) ;        C 2  T 300, -300 ; (#11) ;
  C 2  T 0, -400 ; (#5) ;        C 2  T 300, -400 ; (#10) ;
  C 2  T 0, -500 ; (#6) ;        C 2  T 300, -500 ; (# 9) ;
  C 4  T 0, -600 ; (#7,ground) ; C 2  T 300, -600 ; (# 8) ;
  L PSSC ; (outline in silk-screen);
  W 20 50,50 50,-650 250,-650 250,50 170,50 170,10 130,10 130,50 50,50;
DF ;


The  file  DIPS.CIF  in the MOSIS library contains all of the above symbols and
symbols for some popular DIPS (14, 16, 18, 20, 22, 24, 24-wide, 28, 40, 48  and
64).

[]
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting openp.c...
cat >openp.c <<'!E!O!F!'
/*  openp, fopenp  --  search pathlist and open file
 *
 *  Usage:
 *	i = openp (path,file,complete,mode)
 *	f = fopenp (path,file,complete,fmode)
 *	int i,mode;
 *	FILE *f;
 *	char *path,*file,*complete,*fmode;
 *
 *  Openp searches for "file" in the pathlist "path";
 *  when the file is found and can be opened by open()
 *  with the specified "mode", then the full filename
 *  is copied into "complete" and openp returns the file
 *  descriptor.  If no such file is found, openp returns -1.
 *  Fopenp performs the same function, using fopen() instead
 *  of open() and fmode instead of mode; it returns 0 if no
 *  file is found.
 *
 *  HISTORY
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Created for VAX.
 *
 */

#include <stdio.h>

int open();
int searchp();

static int mod,value;
static char *fmod;
static FILE *fvalue;

static int func (fnam)
char *fnam;
{
	value = open (fnam,mod);
	return (value < 0);
}

static int ffunc (fnam)
char *fnam;
{
	fvalue = fopen (fnam,fmod);
	return (fvalue == 0);
}

int openp (path,file,complete,mode)
char *path, *file, *complete;
int mode;
{
	register char *p;
	mod = mode;
	if (searchp(path,file,complete,func) < 0)  return (-1);
	return (value);
}

FILE *fopenp (path,file,complete,fmode)
char *path, *file, *complete, *fmode;
{
	register char *p;
	fmod = fmode;
	if (searchp(path,file,complete,ffunc) < 0)  return (0);
	return (fvalue);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting pcb.1...
cat >pcb.1 <<'!E!O!F!'
.TH PCB 1 6/16/85
.CM 4
.SH "NAME"
pcb \- PC Board router and editor
.SH "SYNOPSIS"
pcb [-sb]
.SH "DESCRIPTION"
.B PCB
is a tool to design a printed circuit board (pcb) for a given circuit.
The circuit must be described by 3 files: a type definition file that
has the layout of the used devices, a component definition file that
lists the devices in the circuit and associates them with an instatiation
name and optional placement information.
The third file is a netlist that
describes the electrical connections that should be realized.
For special
devices such as logos, connectors and annotations - a library of geometry
descriptions must be supplied (in CIF, Caltech Intermediate Format).

Based on these files describing the board, a database of the desired board
is constructed.
.B PCB
has facilities to route the board (either automatic or interactive), plot
it (either directly on a Versatec plotter or as a CIF file that may be submitted
to MOSIS for fabrication) and to make changes to it.
.SH "FILES"
[v/u]/usr/vlsi/bin/pcb			executable object
[v/u]/usr/agn/pcb/pcbsdef.CIF		standart CIF library
[v/u]/usr/vlsi/lib/caesar/displays	graphic terminal list
[v/u]/usr/agn/pcb/pcb.press       	documentation
.li
./pcb.SAV				saved database
.SH "ENVIRONMENT"
needs an AED-512 graphic terminal on a direct line to work with.
.SH "BUGS"
quite likely.
.B PCB
has a fair amount of internal consistency checking build in that tries to
locate trouble early (and prevent core-dumps).
If a problem is detected, a
copy of the current data base is written to 'pcb.ERR' along with some
diagnostic information to aid debugging.
Usually, it is possible to restart
on this data base (move it to pcb.SAV) without loosing work.
.SH HISTORY
.TP
16-Jun-85  Andreas Nowatzyk (agn) at Carnegie-Mellon University
Created.
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting pcdst.h...
cat >pcdst.h <<'!E!O!F!'
/***************************************************************\
*								*
*	PCB program						*
*								*
*	Common data structures					*
*								*
*	(c) 1985		A. Nowatzyk			*
*								*
\***************************************************************/

#ifdef mainpgm				/* main program ?	*/
#define cdext				/* define data struct.	*/
#else
#define cdext extern			/* declare data struct. */
#endif

cdext char pcb[ymax][xmax];		/* pcb bit map		*/

cdext struct comp {			/* component desc.	*/
	char name[nmmax];		/* incarnation name	*/
	struct type *ty;		/* type			*/
	int  x, y;			/* board position	*/
	unsigned r:2;			/* rotation 0-3 (*90 dg)*/
	unsigned unplaced:1;		/* =1 if not placed	*/
} CP[cpmax];

cdext struct type {			/* type decriptor	*/
	char name[nmmax];		/* type name		*/
	int x, y;			/* component box	*/
	short np;			/* number of pins	*/
	short cif;			/* 0 or (index to cif)+1*/
	struct pin *p;			/* start of pin list	*/
} TY[tymax];

cdext struct pin {			/* pin descr.		*/
	unsigned p:3;			/* pin type:		*/
					/*    0 : normal	*/
					/*    1 : ground	*/
					/*    2 : Vcc		*/
					/*    3 : Vee		*/
					/*    4 : Vbb		*/
	int x, y;			/* location		*/
} PN[pnmax];

cdext struct hole {			/* pcb hole		*/
	unsigned short x, y;		/* hole position	*/
	unsigned short pn;		/* pin number	[0..n]	*/
	unsigned short cpi;		/* component index	*/
	struct nlst *n;			/* net pointer		*/
} CH[chmax];

cdext struct nlhd {			/* net list heads	*/
	char name[nmmax];		/* net name		*/
	int l;				/* length of list	*/
	struct nlst *lp;		/* list pointer		*/
	int x1, y1, x2, y2;		/* list confinment	*/
	unsigned f:1;			/* flag: 1:done 0:not d.*/
	unsigned ref:1;			/* referenced (update)	*/
} NH[nhmax];

cdext struct nlst {			/* net list		*/
	struct hole *c;			/* component hole	*/
	struct nlst *n;			/* next list element	*/
	struct nlhd *nlp;		/* net list back pointer*/
	int mk;				/* mark for con. check	*/
} NL[nlmax];

cdext struct cif {			/* external cif descrip.*/
	int symn;			/* cif-symbol number	*/
	int xl, yl, xh, yh;		/* off-limit area	*/
	unsigned flg:1;			/* =1 for extenension	*/
	unsigned blk:1;			/* =1 if block present	*/
} CIF[cifmax];

cdext struct vtin {			/* vital information	*/
	int ncp;			/* number of components */
	int nty;			/* number of types	*/
	int npn;			/* number of pins	*/
	int nch;			/* number of com. holes */
	int nnh;			/* number of nets	*/
	int nnl;			/* total net list length*/
	int pver;			/* program version	*/
	int x, y;			/* size of used bit-map */
	struct comp *cp;		/* CP start pointer	*/
	struct type *ty;		/* TY start pointer	*/
	struct pin  *pn;		/* PN start pointer	*/
	struct hole *ch;		/* CH start pointer	*/
	struct nlhd *nh;		/* NH start pointer	*/
	struct nlst *nl;		/* NL start pointer	*/
	struct nlhd *cnet;		/* current net		*/
	struct nlhd *enhl;		/* empty NH list	*/
	struct nlst *enll;		/* empty NL list	*/
        int BSX, BSY;			/* board size		*/
	int reserved[8];		/* reserved for future use */
	char errtxt[82];		/* famous last words	*/
	int err_info[4];		/* some explanation	*/
	struct nlhd GND, VCC, VTT, VEE;	/* power nets		*/
	int resrv1;			/* reserved for future use */
	int resrv2;			/* reserved for future use */
	int ncif;			/* #of cif records	*/
	struct vtin *own;		/* own address          */
} V 
#ifdef mainpgm
	= {0, 0, 0, 0, 0, 0, pversion, xmax, ymax,
	   CP, TY, PN, CH, NH, NL, 0, 0, 0,
	   0, 0,			/* BSX, BSY		*/
	   0, 0, 0, 0, 0, 0, 0, 0,
	   "", 0, 0, 0, 0,		/* error info		*/
	   {"Gnd", 0, 0, xmax, ymax, 0, 0, 1},
	   {"Vcc", 0, 0, xmax, ymax, 0, 0, 1},
	   {"Vee", 0, 0, xmax, ymax, 0, 0, 1},
	   {"Vtt", 0, 0, xmax, ymax, 0, 0, 1},
	   0, 0, 0, &V
	}
#endif
;

/* The next variables are not realy common, but usefull		*/
cdext int	cx, cy,			/* current x/y position */
		wx, wy,			/* current window pos.  */
		fx, fy,			/* current frame pos.	*/
		cz,			/* current zoom factor  */
		ccc,			/* current color code	*/
		ccm;			/* complement color mask*/

cdext int	wtsb;			/* wire trace side bit	*/
cdext int (*wthf)(), (*wtvf)();	        /* wire trace function pointer	*/
cdext int nettgo;			/* nets to go (status info)	*/
cdext int no_beep			/* beep on/off switch		*/
#ifdef mainpgm
	= 0
#endif
		;
cdext int no_adjw			/* adjw on/off switch		*/
#ifdef mainpgm
	= 1
#endif
		;
cdext int st_reroute			/* straight by reroute		*/
#ifdef mainpgm
	= 0
#endif
		;
cdext int no_hrout			/* home route on/off switch	*/
#ifdef mainpgm
	= 0
#endif
		;
cdext int rt_str			/* routing strategy		*/
#ifdef mainpgm
	= 0
#endif
		;
cdext int batch				/* batch mode indicator		*/
#ifdef mainpgm
	= 0
#endif
		;
	
cdext int dr[8][2] 			/* wire directions		*/
#ifdef mainpgm
		=	{ { 1,  0},
			  { 1,  1},
			  { 0,  1},
			  {-1,  1},
			  {-1,  0},
			  {-1, -1},
			  { 0, -1},
	 		  { 1, -1}  }
#endif
;

#define ncolors 13 		/* number of color layers		 */
cdext struct color_tab {	/* guess what: this is the color table	 */
     int Z, O;			/* off/on bit mask			 */
     int r, g, b;		/* red, green, blue color intensity	 */
     char *name;		/* layer name				 */
} Color_tab[ncolors]
#ifdef mainpgm
	    = {	{0x00, 0x20, 255, 255, 255, "Text"},
		{0x00, 0x10,   0, 255, 255, "Frame & ext. cif symbols"},
		{0x80, 0x04,   0,   0, 200, "Componet pins"},
		{0x80, 0x08, 190, 190,   0, "Via holes"},
		{0x80, 0x01,   0, 190,   0, "Component side"},
		{0x80, 0x02, 190,   0,   0, "Solder side"},
		{0x00, 0x04, 190,   0, 190, "*Componet pins"},
		{0x00, 0x08, 255, 255,   0, "*Via holes"},
		{0x00, 0x01,   0, 255,   0, "*Component side"},
		{0x00, 0x02, 255,   0,   0, "*Solder side"},
		{0x00, 0x40,   0, 190, 200, "Cursor"},
		{0x80, 0x00, 100, 120, 130, "Background"},
		{0x00, 0x00, 100, 120, 200, "Trouble"}
	      }
#endif
;
#define CT_s1_n 4 		/* index to side 1 (normal)	 */
#define CT_s1_s 8		/* index to side 1 (selected)	 */
#define CT_s2_n 5		/* index to side 2 (normal)	 */
#define CT_s2_s 9		/* index to side 2 (selected)	 */

cdext int top_side;		/* visable top side (to select stuff)	*/

cdext char placed		/* =1: components are placed	 */
#ifdef mainpgm
			= 0
#endif
;

#undef cdext
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting pleer.h...
cat >pleer.h <<'!E!O!F!'
/*******************************************************\
* 						        *
* 	PCB program				        *
* 						        *
* 	Lee Router section  (common data structures)    *
* 						        *
* 	(c) 1985		A. Nowatzyk	        *
* 						        *
\*******************************************************/

#define maxrtl 10000		/* initial max ray table length	 */
#define sftmrg 2		/* safty margin (lazy check)	 */
#define maxvht 3000		/* length of via hole table	 */

#define MSK1  0x0f		/* nibble mask (LOB, side 1)	 */
#define MSK2  0xf0		/* nibble mask (HOB, side 2)	 */
#define VALID 0			/* valid square			 */
#define NOGOD 1			/* forbidden bit		 */
#define TERM  2			/* terminal square		 */
#define VTERM 3			/* terminal square on other side */
#define HOLE  4			/* hole bit (may go with 0,2,3)	 */
#define MSTART 5		/* start of maze		 */
#define HDT   8			/* home direction token		 */

/**** warning:  bit-defines are hardwired into several tables ****/

#define slahb 1			/* selected (any-) hole bit	 */
#define ivs1b 8			/* invalid side 1 bit		 */
#define ivs2b 64		/* invalid side 2 bit		 */
#define sls1b 512		/* selected side 1 bit		 */
#define sls2b 4096		/* selected side 2 bit		 */

#define maxvhpt 10		/* max. number of via holes/segm */

#ifdef mainleer			/* main router section ?	 */
#define cdext			/* yes: define structures	 */
#define initvl(x) = x;
#else
#define cdext extern		/* no : reference external	 */
#define initvl(x) ;
#endif

cdext int RT_sel initvl(1)	/* router-select: 0=full 1=confined	 */

cdext int C1 initvl(25)		/* boarder for S_route			 */
cdext int C2 initvl(10)		/* fence distance (must be even)	 */
cdext int C3 initvl(2)		/* max number of via holes		 */
cdext int C4 initvl(5)		/* penalty for HV via holes		 */
cdext int C5 initvl(10)		/* penalty for D via holes		 */
cdext int C6 initvl(8)		/* via hole alignment (must be even)	 */
cdext int C7 initvl(3)		/* via hole penalty progression		 */

cdext int K1 initvl(10)		/* small delta limit for single side run */
cdext int K2 initvl(8)		/* boarder size for single side runs	 */
cdext int K3 initvl(8)		/* boarder size for L - runs	 	 */
#define K3max 15
cdext int K4 initvl(50)		/* min length for Z - runs		 */
cdext int K5 initvl(16)		/* > K3 min progress for each segment	 */
cdext int K6 initvl(4)		/* max number of via holes in L* routes	 */
cdext int K7 initvl(0)		/* max level for L*_route retries	 */
#define maxvhct 260		/* >=(K3 +1)**2 via-hole cost table	 */
cdext int K8 initvl(-7)		/* rectangular via hole bonus	 */

/* #define debug	0 	*/	/* debuging option		 */
#ifdef debug
    cdext struct nlhd *testbp;	/* debuging stuff		 */
    cdext int tx1, ty1, tx2, ty2;
    cdext int ttt;
#endif

cdext int sx, sy;		/* size of temporary bit map	 */
cdext int ox, oy;		/* offset to temp. origin	 */
cdext char *abm initvl(0)	/* pointer to aux. Bit map	 */

/***********************************************************************\
* 								        *
*  Position <x,y> in the auxiliary bit map is position <x+ox,y+oy> in   *
*  the main bitmap (= pcb[y+oy][x+ox]). This referes to *(abm+x+y*sx).  *
* 								        *
\***********************************************************************/

cdext int     dir[16];		/* direction table (*2) 	 */

/**********************************************************************\
* 								       *
*  The ray tables keep track of the expanding wave the sweeps trough   *
*  the maze. Each entry represents a particular direction. If it hits  *
*  any obstacle, the ray terminates. as it propergates, it tries to    *
*  spawn new rays in directions +/- 1 of its own direction.	       *
*  A ray table entry has the following format:			       *
*  (it was compressed into a word because the number of rays can be    *
*  quite large)							       *
* 								       *
*         MSB                            LSB			       *
*          ========--------========--------			       *
*          ************************........ : offset in abm	       *
*          ............................*... : side bit: 0=s1b 1=s2b    *
*          .............................*** : direction (0-7)	       *
*          ........................****.... : Via hole count (0-15)    *
* 								       *
\**********************************************************************/
cdext unsigned *drt, *hvrt;	/* ray tables			 */
#define rtsb 0x08		/* side bit			 */
#define rtdr 0x07		/* direction bits		 */
#define rtvc 0xf0		/* via counter bits		 */
cdext int
	drtc, drtcd, drtmax,	/* ray tab cnt (diagonal)	 */
	hvrtc, hvrtcd, hvrtmax;	/* ray tab cnt (horizontal)	 */
struct vhtab {			/* via hole table		 */
	char *t;		/* koordinate			 */
	char s;			/* from side (= s1b or s2b)	 */
	char n;			/* wait counter			 */
	char c;			/* hole counter			 */
}   vht[maxvht];
cdext int vhtc;		/* counter for vht		 */

cdext char *vhpt[maxvhpt];	/* via hole pointer table	 */
cdext int vhptc;		/* number of via holes in segm	 */

#undef cdext
#undef initvl
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting pparm.h...
cat >pparm.h <<'!E!O!F!'
/***************************************************************\
*								*
*	PCB program						*
*								*
*	Program parameter definitions				*
*								*
*	(c) 1985		A. Nowatzyk			*
*								*
\***************************************************************/

#define pversion 124			/* program version 1.24 */
#define mgnm 3341			/* magic number		*/
#define xmax 1280			/* max. X size +2	*/
#define ymax 1024			/* max. Y size +2	*/
#define ovs  50				/* overshot for windows */
#define rsun 8				/* raster unit		*/
#define savcnt 25			/* auto save period	*/
#define pvws 200			/* preview window size	*/
#define delrmax 20			/* max. delete recursion*/

#define nmmax 15			/* name length		*/
#define cpmax 500	/* < 64K */	/* component limit	*/
#define tymax 500			/* type limit		*/
#define pnmax 2000			/* pin definition limit */
#define chmax 10000			/* component hole limit */
#define nhmax 4000			/* net limit		*/
#define nlmax 8000			/* net length limit	*/
#define wbmax 100			/* current chain buffer	*/
#define lrn_max 200			/* learn buffer size	*/
#define cifmax 500			/* ex CIF symtab size	*/

#define ex_cifL 500			/* range for External	*/
#define ex_cifH 999			/*   cif descriptions	*/

#define inp_lnl 1024			/* input line length	*/

#define cp_align(x) ((x+2) & 0xfffffffc)/* align a component co */
#define cp_alchk(x) (x & 3)		/* CP align check: 1=err*/

#define nil 0				/* used for pointers	*/
#define DELETED "deleted"		/* used to invalidate TY, CP */

#define s1b  1				/* side 1 bit		*/
#define s2b  2				/* side 2 bit		*/
#define chb  4				/* component hole bit   */
#define ishb 8				/* inter side hole bit  */
#define fb   16				/* frame bit		*/
#define resb 32				/* spare: may need 2 mrk*/
#define mrkb 64				/* mark for wire trace	*/
#define selb 128			/* select bit		*/
/****************************************************************************\
* 									     *
*  Usage of bits:							     *
* 		    -- in pcb --       		-- on the AED --	     *
*     s1b:            side1 trace bit		same			     *
*     s2b:	    side2 trace bit		same			     *
*     chb:	    component hole outline	same			     *
*     ishb:	    via-hole outline		same			     *
*     fb:		    restricted areas (frame..)	same		     *
*     resb:	    side disambiguation		text & graphic overlay	     *
*     mrkb:	    temp marker for traces	cursor plane		     *
*     selb:	    select marker		highlight objects	     *
* 									     *
*  Conventions:								     *
*     'selb' is used to select nets: V.cnet will have a pointer to	     *
* 	   the selected net or is '0'. Only one net can be selected at	     *
* 	   a time and all points that are selected should eventually be	     *
* 	   connected electrically. Selected object may not be adjacents	     *
* 	   to unselected ones (design rule). If V.cnet is '0' no select	     *
* 	   bits should be present.					     *
*     'mrkb' is used as temporary marker within certain functions (wtrace,   *
* 	   adj_sort). It must be cleared when those functions are done.	     *
*     'resb' is set only along with 'selb' if 's2b' is present as part of    *
* 	   the selection process to disambiguate between a selected	     *
* 	   's1b' and a selected 's2b' when they are both set.		     *
* 									     *
*  Note: this particular use of the bit-planes is a serious design mistake,  *
*        but it is too late to fix that. A better bit assignment would pack  *
*        'fb', 'ishb' and 'chb' into 2 bit (along with background there are  *
*        4 mutual exclusive possibilities) and would use 3 bits for each     *
*        signal plane: a presence bit ('s1b','s2b'), a select bit ('sel1b',  *
*        'sel2b') and a mark bit ('mrk1b', 'mrk2b'). This would get rid of   *
*        many constaints and special cases: a vastly cleaner solution.	     *
* 									     *
\****************************************************************************/
#define all  255			/* all bit planes	*/
#define vec  3	 /* = s1b|s2b		   vectored bit planes  */
#define ahb  12  /* = chb|ishb		   any hole bit plane	*/
#define rec  28	 /* = chb|ishb|fb	   rectangular b planes */

#define START 0				/* Start context	*/
#define ROUTE 1				/* Route context	*/
#define EDIT 2				/* Edit context		*/
#define LEARN 3				/* Learn context	*/
#define ADELE 4				/* Area delete context	*/
#define AROUTE 5			/* Area route		*/
#define CMOVE 6				/* component move	*/
#define PLOW 7				/* plow context		*/
#define PLACE 8				/* component place cntx */
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting searchp.c...
cat >searchp.c <<'!E!O!F!'
/*  searchp  --  search through pathlist for file
 *
 *  Usage:  p = searchp (path,file,fullname,func);
 *	char *p, *path, *file, *fullname;
 *	int (*func)();
 *
 *  Searchp will parse "path", a list of pathnames separated
 *  by colons, prepending each pathname to "file".  The resulting
 *  filename will be passed to "func", a function provided by the
 *  user.  This function must return zero if the search is
 *  successful (i.e. ended), and non-zero if the search must
 *  continue.  If the function returns zero (success), then
 *  searching stops, the full filename is placed into "fullname",
 *  and searchp returns 0.  If the pathnames are all unsuccessfully
 *  examined, then searchp returns -1.
 *  If "file" begins with a slash, it is assumed to be an
 *  absolute pathname and the "path" list is not used.  Note
 *  that this rule is used by Bell's cc also; whereas Bell's
 *  sh uses the rule that any filename which CONTAINS a slash
 *  is assumed to be absolute.  The execlp and execvp procedures
 *  also use this latter rule.  In my opinion, this is bogosity.
 *
 *  HISTORY
 * 23-Oct-82  Steven Shafer (sas) at Carnegie-Mellon University
 *	Fixed two bugs: (1) calling function as "func" instead of
 *	"(*func)", (2) omitting trailing null name implied by trailing
 *	colon in path.  Latter bug fixed by introducing "lastchar" and
 *	changing final loop test to look for "*lastchar" instead of
 *	"*nextpath".
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Created for VAX.  If you're thinking of using this, you probably
 *	should look at openp() and fopenp() (or the "want..." routines)
 *	instead.
 *
 */

int searchp (path,file,fullname,func)
char *path,*file,*fullname;
int (*func)();
{
	register char *nextpath,*nextchar,*fname,*lastchar;
	int failure;

	nextpath = ((*file == '/') ? "" : path);
	do {
		fname = fullname;
		nextchar = nextpath;
		while (*nextchar && (*nextchar != ':'))
			*fname++ = *nextchar++;
		if (nextchar != nextpath)  *fname++ = '/';
		lastchar = nextchar;
		nextpath = ((*nextchar) ? nextchar + 1 : nextchar);
		nextchar = file;	/* append file */
		while (*nextchar)  *fname++ = *nextchar++;
		*fname = '\0';
		failure = (*func) (fullname);
	} 
	while (failure && (*lastchar));
	return (failure ? -1 : 0);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting test.cp...
cat >test.cp <<'!E!O!F!'
*components:
nand1,7400 10 10 0
n2	7400 10 15 0
n3	7400 10,20 0
n4	7400 20,10 1
c1 con 10 30 0
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting test.nl...
cat >test.nl <<'!E!O!F!'
Cnetlist:
1 n4-1 n2-5 n3-4 ;alles fusch
2 n4-3 n2-7 nand1-7
3 nand1-5 c1-7
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting test.ty...
cat >test.ty <<'!E!O!F!'
*types:
7400:
0,0,a-1
1,0,b-1
2,0,q-1
3,0,a-2
4,0,b-2
5,0,q-2
6,0,gnd
6,3,q-3
5,3,b-3
4,3,a-3
3,3,q-4
2,3,b-4
1,3,a-4
0,3,vcc

con:
0,0,a-1
1,0,a-2
2,0,a-3
3,0,a-4
4,0,a-5
5,0,a-6
6,0,a-7
7,0,a-8
8,0,a-9
9,0,a-10
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting wantread.c...
cat >wantread.c <<'!E!O!F!'
/*  wantread  --  attempt to open file for input
 *
 *  Usage:  i = wantread (path,file,fullname,prompt);
 *	int i;
 *	char *path,*file,*fullname,*prompt;
 *
 *  Wantread will search through the specified path for the
 *  specified file, attempting to open it for input if it is
 *  found.  If no such file is found, the user is given
 *  an opportunity to enter a new file name (after the prompt is
 *  printed).  The new file will then be sought using the same
 *  path.
 *  If the path is the null string, the file will be searched for
 *  with no prefix.  If the file name is null, the user will be
 *  prompted for a file name immediately.  The user can always
 *  abort wantread by typing just a carriage return to the prompt.
 *  Wantread will put the name of the successfully opened file into
 *  the "fullname" string (which therefore must be long enough to hold a
 *  complete file name), and return its file descriptor; if no file
 *  is successfully found, -1 is returned.
 *
 *  HISTORY
 * 21-Oct-81  Fil Alleva (faa) at Carnegie-Mellon University
 *	Fixed bug which caused an infinite loop when getstr() got
 *	an EOT error and returned NULL. The error return was ignored
 *	and the value of "answer" was not changed which caused the loop.
 *
 * 28-Aug-80  Mike Accetta (mja) at Carnegie-Mellon University
 *	Fixed bug which used the "file" string to hold name typed at terminal
 *	even though "file" may have been passed as a constant.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Rewritten for VAX.
 *
 */

#include <stdio.h>

int strcmp(),openp();
char *getstr();

int wantread (path,file,fullname,prompt)
char *path,*file,*fullname,*prompt;
{
	register int value;
	char myfile[200], *retval;

	if (*file == '\0') {
		getstr (prompt,"no file",myfile);
		if (strcmp(myfile,"no file") == 0)  return (-1);
	}
	else
	    strcpy(myfile, file);

	do {
		value = openp (path,myfile,fullname,0);
		if (value < 0) {
			if (*path && (*myfile != '/')) {
				sprintf (fullname,"Want to read %s in path \"%s\"",myfile,path);
			}
			else {
				sprintf (fullname,"Want to read %s",myfile);
			}
			perror (fullname);
			retval = getstr (prompt,"no file",myfile);
			if ((strcmp(myfile,"no file") == 0) || retval == NULL)
			    return (-1);
		}
	} 
	while (value < 0);

	return (value);
}
!E!O!F!
#
# type    sh /usru0/agn/pcb/distr/../usenet/part1   to unpack this archive.
#
echo extracting wantwrite.c...
cat >wantwrite.c <<'!E!O!F!'
/*  wantwrite  --  attempt to open file for output
 *
 *  Usage:  i = wantwrite (path,file,fullname,prompt,warn);
 *    int i,warn;
 *    char *path,*file,*fullname,*prompt;
 *
 *  Wantwrite will attempt to open "file" for output somewhere in
 *  the pathlist "path".  If no such file can be created, the user
 *  is given an oportuity to enter a new file name (after the
 *  prompt is printed).  The new file will then be sought using
 *  the same path.
 *  If the path is the null string, the file will be created with
 *  no prefix to the file name.  If the file name is null, the
 *  user will be prompted for a file name immediately.  The user
 *  can always abort wantwrite by typing just a carriage return
 *  to the prompt.
 *  Wantwrite will put the name of the successfully created file
 *  into the "fullname" string (which must therefore be long enough to
 *  hold a complete file name), and return its file descriptor;
 *  if no file is created, -1 will be returned.
 *  Wantwrite examines each entry in the path, to see if the
 *  desired file can be created there.  If "warn" is true, 
 *  wantwrite will first check to ensure that no such file
 *  already exists (if it does, the user is allowed to keep it).
 *  If no such file exists (or the user wants to delete it), then
 *  wantwrite attempts to create the file.  If it is unsuccessful,
 *  the next entry in the pathlist is examined in the same way.
 *
 *  HISTORY
 * 21-Oct-81  Fil Alleva (faa) at Carnegie-Mellon University
 *	Fixed bug which caused an infinite loop when getstr() got
 *	an EOT error and returned NULL. The error return was ignored
 *	and the value of "answer" was not changed which caused the loop.
 *
 * 20-Nov-79  Steven Shafer (sas) at Carnegie-Mellon University
 *	Rewritten for VAX.
 *
 */

#include <stdio.h>

int strcmp();
int creat();
int searchp();
char *getstr();

static int warnflag;
static int fildes;

static int func (fnam)
char *fnam;
{		/* attempt to create fnam */
	register int goahead;
	goahead = 1;
	if (warnflag) {
		fildes = open (fnam,1);
		if (fildes >= 0) {
			close (fildes);
			printf ("%s already exists!  ",fnam);
			goahead = getbool ("Delete old file?",0);
		}
	}
	if (goahead) {
		fildes = creat (fnam,0644);
		if (fildes < 0) {
			goahead = 0;
		}
	}
	return (!goahead);
}

int wantwrite (path,file,fullname,prompt,warn)
char *path,*file,*fullname,*prompt;
int warn;
{
	register int i;
	char myfile [200], *retval;

	if (*file == '\0') {
		getstr (prompt,"no file",myfile);
		if (strcmp(myfile,"no file") == 0)  return (-1);
	}
	else strcpy (myfile,file);

	warnflag = warn;
	do {
		i = searchp (path,myfile,fullname,func);
		if (i < 0) {
			if (*path && (*myfile != '/')) {
				printf ("%s in path \"%s\":  Can't create.\n",myfile,path);
			} 
			else {
				perror (myfile);
			}
			retval = getstr (prompt,"no file",myfile);
			if ((strcmp(myfile,"no file") == 0) || retval == NULL)
			    return (-1);
		}
	} 
	while (i < 0);

	return (fildes);
}
!E!O!F!