www.pudn.com > pccp047.zip > TERM.C


/*	Copyright (C) 1992 Peter Edward Cann, all rights reserved. 
 */ 
 
#include 
#include 
#include 
#include 
#include 
#include"emu.h" 
#include"color.h" 
#include"port.h" 
 
 
int locechop; 
 
dispkbd(code) 
	unsigned short code; 
	{ 
	int i; 
	long tstamp, tstamp1, dayofticksp; 
	unsigned char ccode, scode; 
	ccode=code&0xff; 
	scode=(code>>8)&0xff; 
	if(ccode) 
		{ 
		while(!(inp(basereg+STATREG)&0x20)); 
		if(locechop) 
			dispport(ccode); 
		outp(basereg, code); 
		} 
	else 
		if(!emu.keys[scode].len) 
			putch(0x07); 
		else 
			for(i=0;i22) 
							break; 
						} 
					} 
				else if(emu.keys[scode].nullpause_p&&(emu.keys[scode].chars[i]==0xff)) 
					{ 
					_bios_timeofday(_TIME_GETCLOCK, &tstamp); 
					outp(basereg+LCTLREG, lctl|0x40); 
					dayofticksp=0; 
					while(1) 
						{ 
						if(_bios_timeofday(_TIME_GETCLOCK, &tstamp1)) 
							dayofticksp+=20*60*60*24; 
						if(tstamp1+dayofticksp-tstamp>10) 
							break; 
						} 
					outp(basereg+LCTLREG, lctl); 
					} 
				else 
					{ 
					if(locechop) 
						dispport(emu.keys[scode].chars[i]); 
					outp(basereg, emu.keys[scode].chars[i]); 
					} 
				} 
	} 
 
#define LISTSIZ 16 
 
struct 
	{ 
	short index; 
	short row; 
	char rowset; 
	short column; 
	char colset; 
	short list[LISTSIZ]; 
	short listindex; 
	} 
	funcstor[NFUNCS]; 
 
clrfuncstor(seqn) 
	short seqn; 
	{ 
	int i; 
	if(funcstor[seqn].listindex==LISTSIZ) 
		funcstor[seqn].listindex--; 
	for(i=funcstor[seqn].listindex;i>=0;i--) 
		funcstor[seqn].list[i]=0; 
	funcstor[seqn].row=funcstor[seqn].column=funcstor[seqn].listindex=funcstor[seqn].index=funcstor[seqn].rowset=funcstor[seqn].colset=0; 
	} 
 
int bold, faint, blink, inverse, bkcolor, fgcolor; 
struct videoconfig far *vconf; 
 
atthndl() 
	{ 
	int adds, workingbk, workingfg; 
	adds=0; 
	if((vconf->adapter!=_MDPA)&&(vconf->adapter!=_HGC)) 
		{ 
		workingbk=bkcolor; 
		workingfg=fgcolor; 
		if(faint) 
			if(inverse) 
				if(bkcolor==WHITE) 
					workingbk=GRAY; 
				else if(bkcolor==BLACK) 
					; 
				else 
					adds+=FAINTADD; 
			else 
				if(fgcolor==WHITE) 
					workingfg=GRAY; 
				else if(fgcolor==BLACK) 
					; 
				else 
					adds+=FAINTADD; 
		else 
			if(bold) 
				{ 
				if(bkcolor==WHITE) 
					workingbk=BWHITE; 
				if(fgcolor==WHITE) 
					workingfg=BWHITE; 
				} 
		if(blink) 
			adds+=BLINKADD; 
		if(inverse) 
			{ 
			_settextcolor(workingbk+adds); 
			_setbkcolor((long)(workingfg&0x07)); 
			} 
		else 
			{ 
			_settextcolor(workingfg+adds); 
			_setbkcolor((long)(workingbk&0x07)); 
			} 
		} 
	else 
		{ 
		workingbk=BLACK; 
		if(bold&&!inverse) 
			workingfg=M_UNDER; 
		else 
			if(inverse) 
				workingfg=WHITE; 
			else 
				workingfg=M_NORMAL; 
		if(faint) 
			if(inverse) 
				if(bkcolor!=BLACK) 
					adds+=FAINTADD; 
				else; 
			else 
				if(fgcolor!=BLACK) 
					adds+=FAINTADD; 
		if(blink) 
			adds+=BLINKADD; 
		if(inverse) 
			{ 
			_settextcolor(workingbk+adds); 
			_setbkcolor((long)(workingfg&0x07)); 
			} 
		else 
			{ 
			_settextcolor(workingfg+adds); 
			_setbkcolor((long)(workingbk&0x07)); 
			} 
		} 
	} 
 
 
ansiatthndl(seqn) 
	short seqn; 
	{ 
	int i, adds, workingbk, workingfg; 
	if(emu.funcs[seqn].func==ANSIATTRIB) 
		for(i=0;i1) 
				_settextposition(posptr.row-1, posptr.col); 
			break; 
		case DOWN: 
			posptr=_gettextposition(); 
			if(posptr.row<24) 
				_settextposition(posptr.row+1, posptr.col); 
			else 
				{ 
				showchar('\n'); 
				_settextposition(posptr.row, posptr.col); 
				} 
			break; 
		case LEFT: 
			posptr=_gettextposition(); 
			if(posptr.col>1) 
				_settextposition(posptr.row, posptr.col-1); 
			break; 
		case RIGHT: 
			posptr=_gettextposition(); 
			if(posptr.col<80) 
				_settextposition(posptr.row, posptr.col+1); 
			break; 
		case GOTO: 
			funcstor[seqn].row-=(emu.firstrowaddr-1); 
			funcstor[seqn].column-=(emu.firstcoladdr-1); 
			if(funcstor[seqn].row<1) 
				funcstor[seqn].row=1; 
			if(funcstor[seqn].row>24) 
				funcstor[seqn].row=24; 
			if(funcstor[seqn].column<1) 
				funcstor[seqn].column=1; 
			if(funcstor[seqn].column>80) 
				funcstor[seqn].row=80; 
			_settextposition((emu.tophi_p?25-funcstor[seqn].row:funcstor[seqn].row), funcstor[seqn].column); 
			break; 
		case NORMAL: 
			fgcolor=WHITE; 
			bkcolor=BLACK; 
			blink=faint=bold=inverse=0; 
			atthndl(); 
			break; 
		case BLINK: 
			blink=1; 
			atthndl(); 
			break; 
		case NOBLINK: 
			blink=0; 
			atthndl(); 
			break; 
		case BOLD: 
			bold=1; 
			atthndl(); 
			break; 
		case NOBOLD: 
			bold=0; 
			atthndl(); 
			break; 
		case FAINT: 
			faint=1; 
			atthndl(); 
			break; 
		case NOFAINT: 
			faint=0; 
			atthndl(); 
			break; 
		case INVERSE: 
			inverse=1; 
			atthndl(); 
			break; 
		case NOINVERSE: 
			inverse=0; 
			atthndl(); 
			break; 
		case UPN: 
			posptr=_gettextposition(); 
			if(posptr.row-funcstor[seqn].row<1) 
				_settextposition(1, posptr.col); 
			else 
				_settextposition(posptr.row-funcstor[seqn].row, posptr.col); 
			break; 
		case DOWNN: 
			posptr=_gettextposition(); 
			if(posptr.row+funcstor[seqn].row>24) 
				{ 
				_settextposition(24,1); 
				for(i=25-(posptr.row+funcstor[seqn].row);i<0;++i) 
					showchar('\n'); 
				_settextposition(24, posptr.col); 
				} 
			else 
				_settextposition(posptr.row+funcstor[seqn].row, posptr.col); 
			break; 
		case LEFTN: 
			posptr=_gettextposition(); 
			if(posptr.col-funcstor[seqn].column<1) 
				_settextposition(posptr.row, 1); 
			else 
				_settextposition(posptr.row, posptr.col-funcstor[seqn].column); 
			break; 
		case RIGHTN: 
			posptr=_gettextposition(); 
			if(posptr.col+funcstor[seqn].column>80) 
				_settextposition(posptr.row, 80); 
			else 
				_settextposition(posptr.row, posptr.col+funcstor[seqn].column); 
			break; 
		case ANSIATTRIB: 
			ansiatthndl(seqn); 
			break; 
		case WRAP: 
			wrap_p=1; 
			wrapctl(); 
			break; 
		case NOWRAP: 
			wrap_p=0; 
			wrapctl(); 
			break; 
		case GOTOLINE: 
			funcstor[seqn].row-=(emu.firstrowaddr-1); 
			posptr=_gettextposition(); 
			if(funcstor[seqn].row<1) 
				funcstor[seqn].row=1; 
			if(funcstor[seqn].row>24) 
				funcstor[seqn].row=24; 
			_settextposition(emu.tophi_p?25-funcstor[seqn].row:funcstor[seqn].row, 1); 
			break; 
		case GOTOCOL: 
			funcstor[seqn].column-=(emu.firstcoladdr-1); 
			posptr=_gettextposition(); 
			if(funcstor[seqn].column<1) 
				funcstor[seqn].column=1; 
			if(funcstor[seqn].column>80) 
				funcstor[seqn].row=80; 
			_settextposition(posptr.row, funcstor[seqn].column); 
			break; 
		case BINATTR: 
			if((funcstor[seqn].row-emu.attroffset)&emu.blinkmask) 
				blink=1; 
			else 
				blink=0; 
			if((funcstor[seqn].row-emu.attroffset)&emu.inversemask) 
				inverse=1; 
			else 
				inverse=0; 
			if((funcstor[seqn].row-emu.attroffset)&emu.boldmask) 
				bold=1; 
			else 
				bold=0; 
			if((funcstor[seqn].row-emu.attroffset)&emu.faintmask) 
				faint=1; 
			else 
				faint=0; 
			atthndl(); 
			break; 
		case GRAPHCHAR: 
			showchar(emu.gchars[funcstor[seqn].row]); 
			break; 
		case BEGGRAPH: 
			graphics=1; 
			break; 
		case ENDGRAPH: 
			graphics=0; 
			break; 
		case TAB: 
			posptr=_gettextposition(); 
			_settextposition(posptr.row, posptr.col+(8-((posptr.col-1)%8))); 
			break; 
		case BELL: 
			putch(7); 
			break; 
		case DTAB: 
			posptr=_gettextposition(); 
			for(i=0;i<(8-((posptr.col-1)%8));++i) 
				_outtext(" "); 
 
		case CRLF: 
			showchar('\n'); 
			break; 
		case SAVEPOS: 
			posptr=_gettextposition(); 
			savedrow=posptr.row; 
			savedcol=posptr.col; 
			break; 
		case RESTOREPOS: 
			_settextposition(savedrow, savedcol); 
			break; 
		default: 
			break; 
		} 
	} 
 
dispport(c) 
	unsigned char c; 
	{ 
	int seqn, done, ok; 
	done=0; 
	ok=0; 
	for(seqn=0;seqn='0')&&(c<='9')) 
						{ 
						ok=1; 
						funcstor[seqn].column*=10; 
						funcstor[seqn].column+=(c-'0'); 
						funcstor[seqn].colset=1; 
						} 
					else 
						if(funcstor[seqn].colset&&(c==emu.funcs[seqn].codes[++funcstor[seqn].index])) 
							{ 
							ok=1; 
							if(emu.funcs[seqn].codes[++funcstor[seqn].index]==END) 
								{ 
								done=1; 
								perffunc(seqn); 
								} 
							} 
						else 
							clrfuncstor(seqn); 
					break; 
				case ASCDECROW: 
					if((c>='0')&&(c<='9')) 
						{ 
						ok=1; 
						funcstor[seqn].row*=10; 
						funcstor[seqn].row+=(c-'0'); 
						funcstor[seqn].rowset=1; 
						} 
					else 
						if(funcstor[seqn].rowset&&(c==emu.funcs[seqn].codes[++funcstor[seqn].index])) 
							{ 
							ok=1; 
							if(emu.funcs[seqn].codes[++funcstor[seqn].index]==END) 
								{ 
								done=1; 
								perffunc(seqn); 
								} 
							} 
						else 
							clrfuncstor(seqn); 
					break; 
				case ASCDECSEMILIST: 
					if((c>='0')&&(c<='9')&&(funcstor[seqn].listindex "); 
		if(getchar()!='y') /* Note getchar() and not getch()! */ 
			{ 
			printf("I didn't think so!\n"); 
			exit(99); 
			} 
		else 
			printf("OK, you're the boss!\n"); 
		} 
	_getvideoconfig(vconf); 
	_setvideomode(_DEFAULTMODE); 
	index=follow=0; 
	if((argc<4)||(argc>6)) 
		{ 
		printf("Copyright (C) 1992 Peter Edward Cann, all rights reserved.\n"); 
		printf("USAGE: term    [] []\n"); 
		printf(" is an emulation file base pathname.\n"); 
		printf(" is a dribble (text capture) file.\n"); 
		printf("The environment variable PCCPPATH is used for the emulation file if set.\n"); 
		exit(1); 
		} 
	fpname[0]='\0'; 
	dribpname[0]='\0'; 
	if((argc>=5)&&(argv[4][0]=='+')) 
		{ 
		locechop=1; 
		argv[4]++; 
		} 
	else 
		locechop=0; 
	if((argc>=5)&&(argv[4][0]!='-')) 
		{ 
		if((getenv("PCCPPATH")==NULL)||(argv[4][0]=='\\')||(argv[4][1]==':')) 
			sprintf(fpname, "%s.emu", argv[4]); 
		else 
			sprintf(fpname, "%s\\%s.emu", getenv("PCCPPATH"), argv[4]); 
		if((emufd=open(fpname, O_RDONLY|O_BINARY))==-1) 
			{ 
			printf("Error opening emulation file %s.\n", fpname); 
			exit(2); 
			} 
		else 
			if(read(emufd, &emu, sizeof(emu))!=sizeof(emu)) 
				{ 
				printf("Error reading emulation file %s.\n", fpname); 
				exit(3); 
				} 
			else; 
		} 
	else 
		{ 
		nullemu(); 
		emu.funcs[0].func=LEFT; 
		emu.funcs[0].codes[0]='\b'; 
		emu.funcs[0].codes[1]=END; 
		emu.funcs[1].func=DTAB; 
		emu.funcs[1].codes[0]='\t'; 
		emu.funcs[1].codes[1]=END; 
		emu.funcs[2].func=BELL; 
		emu.funcs[2].codes[0]='\007'; 
		emu.funcs[2].codes[1]=END; 
		} 
	if(argc==6) 
		{ 
		strcpy(dribpname, argv[5]); 
		if((dribble=fopen(argv[5], "a"))==NULL) 
			{ 
			printf("Couldn't open dribble file %s.\n"); 
			exit(10); 
			} 
		else 
			{ 
			setmode(fileno(dribble), O_BINARY); 
			fprintf(dribble, "\nBeginning of dribble segment.\n\n"); 
			} 
		} 
	else 
		dribble=NULL; 
	comnum=atoi(argv[1])-1; 
	speed=atoi(argv[2]); 
	parity=argv[3][1]; 
	databits=argv[3][0]; 
	stopbits=argv[3][2]; 
	setport(); 
	readset(); 
	setup(); 
	_clearscreen(_GCLEARSCREEN); 
	initdisp(); 
	updstatus(); 
	atthndl(); 
	_settextposition(1,1); 
	orun=0; 
	if(vconf->adapter==_VGA) 
		_remappalette(GRAY, (long)0x001a1a1a); /* Lighten up gray */ 
	while(1) 
		{ 
		if((_bios_keybrd(_KEYBRD_SHIFTSTATUS) & 3) == 3) 
			{ 
			cleanup(0); 
			_settextcolor(WHITE); 
			_setbkcolor((long)BLACK); 
			_settextposition(24,1); 
			if(dribble!=NULL) 
				{ 
				fprintf(dribble, "\nEnd of dribble segment.\n"); 
				fclose(dribble); 
				} 
			if(vconf->adapter==_VGA) 
				_remappalette(GRAY, _GRAY); /* Restore gray */ 
			_outtext("\nOrderly exit from TERM.\n"); 
			exit(0); 
			} 
		if(_bios_keybrd(_KEYBRD_READY)) 
			dispkbd(_bios_keybrd(_KEYBRD_READ)); 
		if(follow!=index) 
			{ 
			if(dribble!=NULL) 
				fputc(buf[follow], dribble); 
			/* We only display if we're not too far behind; */ 
			/* this makes dribble more reliable. */ 
			if(((index-follow)>4096)||(((index-follow)<0)&&((follow-index)<4096))) 
				if(!orun) 
					{ 
					orun=1; 
					initdisp(); 
					} 
				else; 
			else 
				{ 
				orun=0; 
				dispport(buf[follow]); 
				} 
			follow++; 
			follow=follow%TBUFSIZ; 
			} 
		} 
	}