tsf@druxn.UUCP (FisherTS) (12/02/85)
# This is a shell archive. Remove anything before this line, # then unpack it by saving it in a file and typing "sh file". # # Wrapped by tsf on Sun Dec 1 15:00:54 MST 1985 # Contents: ./MAN/ ./_unix.O/ ./hdrs/ ./EHELP/ ./EHELP/_unix.O/ ./README # ./Buglist ./Makefile ./MAN/ehelp.1 ./MAN/eupd.1 ./_unix.O/genlib.a # ./hdrs/emp.h ./hdrs/ship.h ./EHELP/ehelp.c ./EHELP/Makefile # ./EHELP/_unix.O/ehelp.o echo x - ./README sed 's/^@//' > "./README" <<'@//E*O*F ./README//' ==[ Instructions for installing Old Empire playing aids ]== 1) If you are on a 4.2BSD system, change emp.h to uncomment the #define BSD. For SysV, nothing has to be changed. Also, for 4.2BSD systems, you might want to use the 4.2mkfile in GENLIB, TERMLIB, and UPDLIB instead of the Makefiles provided. 2) When any modifications have been made, do: make clobber make all There are five main programs that are made: ecre - program to create your local sector database (newsect) also can be used to relocate in case you have to move your capital. eupd - program to extract info from Old Empire game output and update your local sector database (empsect) and ship database (empship). ehelp - Old Empire "visual empire". Screen oriented display of your local databases (empsect & empship), and Old Empire command script generator. Script gets written into file called .yout. I have no idea why it was named .yout. pworld - program to print out the world from your empsect file. rdship - program to list the ships in your empship file. In addition, there are several shell/awk programs in MISC that I have found useful. They also demonstrate alternate ways to change or look at your local database. 3) This version is meant to be played with Version 1.1 and any more recent versions of Old Empire. 4) The file, Buglist contains all known bugs fixed and remaining in this version. 5) This package was incrementally thrown together as adversaries put pressure on the author's country. There are lots of opportunities for improving the function and human factors of ehelp, and eupd contains one of the most bizarre uses of lex and yacc I've ever seen - but it works. The whole idea behind this set of tools was to make the emp'ing more efficient than using grid paper and colored pencils, and using up your BTU and time allocation doing census, map, ship, and mov commands. Generally, only the "unpredictable" commands are executed without a script (attack, assault, fly, board, spy). 6) Send all bug reports and wish list items to ihnp4!druxn!tsf. @//E*O*F ./README// chmod u=rw,g=r,o=r ./README echo x - ./Buglist sed 's/^@//' > "./Buglist" <<'@//E*O*F ./Buglist//' ==[ All the bugs that fit, we print ]== Version 1.0 Visual Empire for Old Empire December 1985 Things that generate incorrect scripts, core dumps, hung terminals, cpu loops, inaccurate displays, are bugs. Things that are inconvenient, un-pretty, incomplete, are items for the wish list. Please send all bug reports and wish list items to ihnp4!druxn!tsf. @//E*O*F ./Buglist// chmod u=rw,g=r,o=r ./Buglist echo x - ./Makefile sed 's/^@//' > "./Makefile" <<'@//E*O*F ./Makefile//' MAKE=make LIBDIR=./_unix.O GENLIB=$(LIBDIR)/genlib.a TERMLIB=$(LIBDIR)/termlib.a UPDLIB=$(LIBDIR)/updlib.a all: $(GENLIB) $(TERMLIB) $(UPDLIB) eupd ehelp ecre pworld rdship @echo All done! $(GENLIB): FRC @echo GENLIB: @cd GENLIB; $(MAKE) genlib.a: $(GENLIB) $(TERMLIB): FRC @echo TERMLIB: @cd TERMLIB; $(MAKE) termlib.a: $(TERMLIB) $(UPDLIB): FRC @echo UPDLIB: @cd UPDLIB; $(MAKE) updlib.a: $(UPDLIB) eupd: FRC @echo EUPD: @cd EUPD; $(MAKE) ehelp: FRC @echo EHELP: @cd EHELP; $(MAKE) ecre: FRC @echo ECRE: @cd ECRE; $(MAKE) pworld: FRC @echo "MISC (pworld):" @cd MISC; $(MAKE) pworld rdship: FRC @echo "MISC (rdship):" @cd MISC; $(MAKE) rdship clean: @cd GENLIB; $(MAKE) clean @cd TERMLIB; $(MAKE) clean @cd UPDLIB; $(MAKE) clean @cd EUPD; $(MAKE) clean @cd EHELP; $(MAKE) clean @cd ECRE; $(MAKE) clean @cd MISC; $(MAKE) clean clobber: @cd GENLIB; $(MAKE) clobber @cd TERMLIB; $(MAKE) clobber @cd UPDLIB; $(MAKE) clobber @cd EUPD; $(MAKE) clobber @cd EHELP; $(MAKE) clobber @cd ECRE; $(MAKE) clobber @cd MISC; $(MAKE) clobber @.PRECIOUS: $(GENLIB) $(TERMLIB) $(UPDLIB) FRC: @//E*O*F ./Makefile// chmod u=rw,g=r,o=r ./Makefile echo mkdir - ./MAN mkdir ./MAN chmod u=rwx,g=rx,o=rx ./MAN echo x - ./MAN/ehelp.1 sed 's/^@//' > "./MAN/ehelp.1" <<'@//E*O*F ./MAN/ehelp.1//' ehelp - an Old Empire playing aid Version 1.0 12/85 There are three programs designed (hacked together) to reduce the empire playing time, while maximizing the enjoyment of interacting with the other players. The program captures data from Old Empire output (e.g. census, ship, radar, ...), and uses a screen oriented user interface to display the accumulated knowledge of the world. The user uses the display to create a empire command script which can be executed with the "ex" command. In this way, delivery routes can be established, goods can be moved, ships can be navigated, etc. The four programs are: ecre, ehelp, and eupd. They are used in the following sequence: COMMAND WHAT TO DO WITH IT 1. ecre [-x new_capx] [-y new_capy] Invoked without arguments, it creates an empty world in a file called, "newsect". Create a file "newsect". Rename it "empsect" after optionally saving the old world. Also create an empty file called "empship" ( >empship). Invoked with arguments, this command can be used to change the location of your capital. In fact, if you don't use this program to reflect a new capital location, your view of the world will get all hosed up. If you designate 1,3 as a new capital, use ecre -x 1 -y 3 to create a "newsect" having the appropriate adjustments. 2. play empire, saving the output in a file (e.g. empire Cname rep | tee outfile) Optionally use scripts generated in step 4. 3. eupd < outfile Update your view of the world. This updates empsect and empship. I don't think eupd handles "route" command output very gracefully, so don't use "route". Use "census" and ehelp instead. eupd -p Suppose your neighbor has taken over most of your western border while you were on a trip to New Jersey. The updater isn't smart enough to read through the telegrams and find out what you no longer own. This can be handled by issuing: eupd -p This purges the world of all sectors owned by you. To get the sectors assigned to you again, simply do a cen # (the whole world) and run the output through the eupd command. The sectors you no longer own will be missing in the census output, and therefore they will remain unowned on your map. Of course, the best strategy of all is never take a trip to New Jersey. 4. ehelp Enter the screen oriented display, and create the desired command scripts. These scripts are written in a file called .yout . Now erase outfile, and go back to step 2. Use ehelp like this: While in ehelp, the cursor is either on the map or down in the lower left corner waiting for command input. Furthermore, ehelp is either set up for a specified empire command or it's waiting for you to specify a command (or possibly map coordinates). When your prompt is ">" in the lower left corner, you haven't specified a command yet. In this mode, the following is legal: Enter: x,y change center coordinates map display map cen set up for census commands mov set up for move commands del set up for delivery commands des set up for designate commands shi set up for ship commands nav set up for navigate commands >command append the string following the ">" to .yout crtl-d exit ehelp When you set up any of the command modes (cen, des, etc.) your prompt will change, and the information block in the upper right will change. For commands like mov, del, des, you change the quantity, designation, resource, threshold, etc. by entering the number or letter while the cursor is in the lower left corner, next to the prompt. For example, after entering des, the cursor will still be in the lower left corner. Note that the default designation in the information block in the upper right is 'g'. Type d to change the designation to a defense plant, for example. To leave the specified command mode, type '.' or ctrl-d when the cursor is in the corner. After entering the number or letter, the cursor will go up to the map. To bring the cursor back to the corner, hit the return key. When the cursor is in the corner, put it on the map by hitting the return key. Once on the map, move around by using the w e r k \ | / | s - - d or h - - l / | \ | z x c j keys. When positioned over a sector, hit the tab (ctrl-i) to see what's in that sector. If you're in ship or nav mode, hit 'I' and 'i' to see other useful info. Nothing gets written to the script file (.yout) unless you're on the map and you hit the space bar, or you use the ">command" feature shown above. Specific commands: When the prompt is ">", type "map" to get a map drawn on the screen. The display is centered around the coordinates chosen (default is 0,0). It might look like this: . - . m f h m ^? . * f f d ? m i m u ? ? Question marks indicate sectors you don't own. Sometimes the designation is shown just to the left of the '?'. In the display above, the mountain was detected by a map or spy command, and the fact that it's owned by someone else was probably obtained from a spy command. The other '?'s were probably the result of a map command. To get a census command appended to .yout, enter cen mode and postition the cursor on the sector you want a census of. Then hit the space bar. To designate sectors, enter des mode and select a designation. Position the cursor on the victim sector, and hit the space bar. A "des" command will be appended to .yout. To establish a delivery route, enter del mode. Select resource and threshold. Note that the screen will be redrawn showing the existing routes for the selected resource. When in del mode, position the cursor on the supplying sector, then type a '+'. Next, position the cursor on the adjacent receiving sector, and hit the space bar. A "del" command will be appended to .yout, and the receiving sector is automatically marked as the next supplying sector. Move the cursor to the next receiving sector, and hit the space bar again. To indicate a new supplying sector at any time, position the cursor, then type '+'. Your route is shown as you construct it on the map, but remember that no changes are made to the empire world until you run the script. In fact, your local database isn't changed either. It will change when you run the output of the empire session (with appropriate census output) through eupd. To move things around, enter mov mode. Select resource and quantity. Position cursor on the supplying sector, then type a '+'. Move the cursor to the next sector in the route to the destination and type another '+'. Continue in this way until the cursor is positioned on the destination sector. Instead of typing '+', hit the space bar. A "mov" command will be appended to .yout. The route will be indicated with '@' characters. To tear down the route completely or partially, type a '-'. Ships are navigated the same way, except you enter nav mode, and select a ship number, group of ships (124/35/245), or all ships in the starting sector (type a ',' instead of ship number). Hit the space bar to append a "nav" command to .yout . To find out where all the ships are, enter ship mode. You can limit the operation to ships of only certain types by entering a string next to the prompt. For example, to limit operations to carriers and battleships, type "cb". To reinstate the full list again, type "*". To get a display of all the ships known to you, type "?". Your ships will be to the right of the sector, and other country ships will be positioned to the left. Ships are shown as capital letters. For example your harbor with a pt boat in it and someone else's battleship just to the north would look like this: . . . . m B. . f f hP * m ^ f m u All the ships in a particular sector "stack" up, and only the ship with the highest number is shown. If there were 30 ships in your harbor above, and several other countries had parked ships just to the north, the display would look the same so long as the battleship and pt boat had the highest ship number in that sector. Watch out for capital letters to the left of your harbors... There is a way to limit the other country display to just a particular country, perhaps an enemy of particular interest. Before invoking ehelp, set the shell variable FOES to the country number of interest. e.g. FOES=4 export FOES Then invoke ehelp. The numbers next to the sectors are the ones-digits of the owning country number (11 and 1 will look alike), and ship displays will be limited to just your ships and ships owned by the country number FOES was set to. Note that you can change your database (empsect and empship) just by faking empire output and running it through eupd. For example, suppose your ship hits a mine. You could have a shell script named "mine" that takes the x,y coordinate of the mined sector and produces a fake census command output having zero values for everything except the shells. One effect of this is to change the '.' on the map to a ':' when that sector is displayed. Hopefully you can avoid that sector when doing a "nav". To get rid of the ':', fake a census command that has shells=0. Another example is when ships sink (gasp!). You can fake a ship command output and set the efficiency to zero. This way, the ship won't be displayed. You can also hose up your database pretty badly if you don't know what you're doing with all these fake commands. One last trick. Suppose you want to set up delivery routes for ore, shells and guns all in one shot without having to wait for the screen to redraw at 1200 baud. The trick is to change the resource with the mov command instead of with the del command. Enter del, and select o as the resource. The screen redraws showing the ore delivery routes. Get on the map and set up your new ore routes. Then hit a return. That puts you back at the prompt. Instead of selecting another resource (which would cause the map to be redrawn), leave the del mode by entering a '.' or ctrl-d. Now enter mov mode. Change the resource to s (shells). Leave mov mode, and re-enter del mode. Without entering a resource, hit the return key to get on the map. Now set up your shell delivery routes. Go on to do the gun routes the same way. Not pretty, but it works. While you're still getting familiar with ehelp, be sure to check your scripts. Make sure they're what you intended. Otherwise you could end up doing something you didn't want to do. Also, if you suspect that the map isn't being drawn in the right place on the screen (bad termcap, flaky terminal, noisy line, program bugs(gasp!)), redraw the screen before creating another line of script. Otherwise, the coordinates of the script commands will be wrong. @//E*O*F ./MAN/ehelp.1// chmod u=rw,g=r,o=r ./MAN/ehelp.1 echo x - ./MAN/eupd.1 sed 's/^@//' > "./MAN/eupd.1" <<'@//E*O*F ./MAN/eupd.1//' eupd - an Old Empire playing aid Version 1.0 12/85 Eupd is used to extract information from Old Empire output and update your local sector and ship databases (empsect and empship). Version 1.0 eupd extracts information from the following command outputs: census map ship navigate look radar deliver spy fly For the navigate command, only the "ship #nn stopped at x,y" message is extracted, and the coordinates of your ships is updated. The mobility is left unchanged. For the look command, in addition to the land and ship information extracted, a message is printed when a sub is detected. The sub's presence is not written into the empship file. It is assumed that you'll want to go take a closer "look" to get the sub's number and country info. The output of delivery commands of the following form: del o #1 - is parsed for the threshold information. The delivery direction is gotten from the cesus command. For the spy command, all the normal info is parsed, but when the spy is shot, no info is extracted. When the spy is deported, the sector that deported the spy is checked to see if you own it. That is, your local database is checked to see if you think you still own that sector. If your database indicates (falsely) that you still own that sector, the owner of the sector is changed to 98 (unknown). There is a way to gather reconnaissance data from planes. Fly over a sector of unknown designation. Then do a 'v' to view the sector. This has to be done in a particular manner. For example, suppose you suspect your neighbor's capital is somewhere around 3 to 4 sectors to the east of one of your airfields. You could find out like this: fly 24,-10 1 0 <24.2:1:0:24,-10> rrr <21.2:1:0:27,-10> v Now over completely constructed technical center. <20.2:1:0:27,-10> d <19.2:1:0:27,-9> v Now over completely constructed capital. <18.2:1:0:27,-9> \llle 1 plane landed. Always put the 'v' on a separate line by itself. Otherwise eupd will update the wrong sectors. @//E*O*F ./MAN/eupd.1// chmod u=rw,g=r,o=r ./MAN/eupd.1 echo mkdir - ./_unix.O mkdir ./_unix.O chmod u=rwx,g=rx,o=rx ./_unix.O echo x - ./_unix.O/genlib.a sed 's/^@//' > "./_unix.O/genlib.a" <<'@//E*O*F ./_unix.O/genlib.a//' @//E*O*F ./_unix.O/genlib.a// chmod u=rw,g=r,o=r ./_unix.O/genlib.a echo mkdir - ./hdrs mkdir ./hdrs chmod u=rwx,g=rx,o=rx ./hdrs echo x - ./hdrs/emp.h sed 's/^@//' > "./hdrs/emp.h" <<'@//E*O*F ./hdrs/emp.h//' /* Copyright (c) 1985 by Thomas S. Fisher - Westminster, CO 80030 */ /* Define BSD if you're building this on a 4.2 BSD system */ /* Otherwise (for SysV), leave it undefined */ /* #define BSD */ #define MAXSCN 20 #define XYMAX 64 #define ERROR -1 #define OK 1 /* * Sector Record */ #define CIV 0 #define MIL 1 #define SHL 2 #define GUN 3 #define PLN 4 #define ORE 5 #define BAR 6 struct sector { int s_secno; char s_des; char s_flag; int s_coun; int s_date; char s_ckpt; char s_def; int s_eff; int s_min; int s_gold; int s_mob; int s_rsrc[7]; int s_prod; char s_del[7]; char s_rsrvd[9]; } ; /* * */ @//E*O*F ./hdrs/emp.h// chmod u=rw,g=r,o=r ./hdrs/emp.h echo x - ./hdrs/ship.h sed 's/^@//' > "./hdrs/ship.h" <<'@//E*O*F ./hdrs/ship.h//' /* ship types */ #define S_PT 0 #define S_MIN 1 #define S_DES 2 #define S_SUB 3 #define S_FRE 4 #define S_TEN 5 #define S_BAT 6 #define S_CAR 7 #define TMAXNO 7 struct shpstr { char shp_own; /* country # of owner */ char shp_type; /* ship type */ char shp_effc; /* 0 - 100 */ short shp_xp, shp_yp; /* location in abs coords */ char shp_fleet; /* group membership */ char shp_crew; /* military | civvies on board */ char shp_shels; /* shells on board */ char shp_gun; /* etc */ char shp_plns; char shp_or; char shp_gld; char shp_spric; /* ship price, if for sale */ char shp_mbl; /* mobility */ int shp_lstp; /* time of last update */ }; @//E*O*F ./hdrs/ship.h// chmod u=rw,g=r,o=r ./hdrs/ship.h echo mkdir - ./EHELP mkdir ./EHELP chmod u=rwx,g=rx,o=rx ./EHELP echo x - ./EHELP/ehelp.c sed 's/^@//' > "./EHELP/ehelp.c" <<'@//E*O*F ./EHELP/ehelp.c//' /* Copyright (c) 1985 by Thomas S. Fisher - Westminster, CO 80030 */ /* There are a variety of fflush and sleep calls in here to fix(?) some of the problems with terminals running at 9600 baud on an Amdahl UTS system. */ #include <stdio.h> #include <ctype.h> #include "emp.h" #include "ship.h" /* There are two ways of handling raw mode in here: one for 4.2 BSD and one for SysV. The BSD symbol in emp.h must be defined if this is being built on a 4.2 system. */ #ifdef BSD #include <sgtty.h> #else #include <termio.h> #endif BSD #define MAXLINE 132 /* Max command line (at bottom of screen) length */ #define MAXPATH 64 /* Max path for nav and mov */ /* Miscellaneous constants */ #define OK 1 #define RESET 0 #define TRUE 1 #define FALSE 0 /* Special characters while cursor is on the map */ #define DELETE 077 #define CR 015 #define LF 012 #define SPACE ' ' #define PLUS '+' #define MINUS '-' #define TAB 011 /* Screen motion characters */ #define UP 'e' #define UPRIGHT 'r' #define RIGHT 'd' #define DNRIGHT 'c' #define DOWN 'x' #define DNLEFT 'z' #define LEFT 's' #define UPLEFT 'w' #define VILEFT 'h' #define VIDN 'j' #define VIUP 'k' #define VIRIGHT 'l' #define CENSW 15 /* Width of census display area */ /* Valid command codes */ #define CEN 1 #define DES 2 #define MOV 3 #define DEL 4 #define MAP 5 #define SHP 6 #define NAV 7 #define NCMDS 7 FILE *fopen(), *fdsec, *fdscrpt, *fdship; struct sector s; struct shpstr Ship; int Func = CEN; char Stype[] = { 'p', 'm', 'd', 's', 'f', 't', 'b', 'c' }; char *Sorder = "cbdtspmf"; char Shiplist[128]; int Shpnum = 0; char *Fchar[] = { " ", "cen", "des", "mov", "del", "map", "shi", "nav" }; char *Deldir[] = { ".", "$", "", "", "", "", "", "", "n", "ne", "e", "se", "s", "sw", "w", "nw" }; char *Movdir[] = { "\\l", "l", "/l", "u", "e", "d", "/r", "r", "\\r" }; int Rtxlat[] = { 15, 14, 13, 8, 0, 12, 9, 10, 11 }; char Rtdirl[] = { ' ', '$', ' ', ' ', ' ', ' ', ' ', ' ', '^', ' ', ' ', ' ', 'v', '/', '<', '\\' }; char Rtdirr[] = { ' ', '$', ' ', ' ', ' ', ' ', ' ', ' ', '^', '/', '>', '\\', 'v', ' ', ' ', ' ' }; char Desig = 'g'; int Thresh = 0; int Rsrc = ORE; int Quant = 0; char Rchar[] = { 'c', 'm', 's', 'g', 'p', 'o', 'b' }; int Pathl = 0; int Pathx[MAXPATH], Pathy[MAXPATH]; int Xcen = 0, Ycen = 0; int Xcur = 0, Ycur = 0; int Xl, Yl, Xh, Yh, Xlast, Ylast; char linebuf[MAXLINE]; #ifdef BSD struct sgttyb tty0, ttyb; #else struct termio st, st0; #endif BSD char tbuf[BUFSIZ], tcapbuf[50]; char *CL, *CM; int Termh, Termw, Censtrt; int Foe; #undef putchar int putchar(); main() { char *prompt(); char funcstr[4], *getenv(), *foestr; int i; if( (fdsec = fopen("empsect", "r")) == NULL ) { fprintf(stderr, "Can't open empsect\n"); exit(1); } if( (fdscrpt = fopen(".yout", "a+")) == NULL ) { fprintf(stderr, "Can't open output file\n"); exit(2); } fdship = fopen("empship", "r"); if( (foestr = getenv("FOES")) == NULL ) { Foe = 0; } else { Foe = atoi(foestr); } #ifdef BSD ioctl(0, TIOCGETP, &tty0); /* save terminal state 4.2BSD */ #else ioctl(0, TCGETA, &st0); /* save terminal state */ #endif BSD getcap(); clrscrn(); rawmode(); ckdmode(); prfunc(); prcoord(); strcpy(Shiplist,","); while( prompt(">") != NULL ) { if( linebuf[0] == '>' ) { fputs(&linebuf[1], fdscrpt); continue; } if( sscanf(linebuf, "%d,%d%*[^\n]\n", &Xcen, &Ycen) == 2 ) { prcoord(); Xcur = Xcen; Ycur = Ycen; continue; } if( sscanf(linebuf, "%3s%*[^\n]\n", funcstr) != 1 ) continue; for( i = 1; i <= NCMDS; i++ ) { if( strncmp(funcstr, Fchar[i], 3) != 0 ) continue; Func = i; prfunc(); fflush(stdout); switch( Func ) { case CEN: docen(); break; case DES: dodes(); break; case MOV: domov(); break; case DEL: dodel(); break; case MAP: prmap(); break; case SHP: doship(); break; case NAV: donav(); break; } break; } } mvcrsr(Termh, 1); #ifdef BSD ioctl(0, TIOCSETN, &ttyb); /* restore terminal state and exit 4.2BSD */ #else ioctl(0, TCSETAF, &st0); /* restore terminal state and exit */ #endif BSD } getcap() { extern short ospeed; char *ap; char *getenv(), *tgetstr(); char *term; term = getenv("TERM"); if(term == NULL) { fprintf(stderr, "No TERM in environment\n"); exit(1); } switch(tgetent(tbuf, term)) { case -1: fprintf(stderr, "Cannot open termcap file\n"); exit(2); case 0: fprintf(stderr, "%s: unknown terminal", term); exit(3); } ap = tcapbuf; Termh = tgetnum("li"); Termw = tgetnum("co"); Censtrt = Termw - CENSW; CL = tgetstr("cl", &ap); CM = tgetstr("cm", &ap); if (Termh <= 0 || Termw <= 0) { fprintf(stderr, "Must know the screen size\n"); exit(5); } #ifdef BSD ospeed = ttyb.sg_ospeed & 017; #else ospeed = st0.c_cflag & CBAUD; #endif BSD } char * prompt(s) char *s; { static int plength, ilength; int i, blanks; char *ret; blanks = plength + ilength; for( i = 0; i < blanks; i++ ) { linebuf[i] = ' '; } linebuf[blanks] = '\0'; mvcrsr(Termh-1, 1); printf("%s", linebuf); mvcrsr(Termh-1, 1); printf("%s", s); plength = strlen(s); ret = fgets(linebuf, MAXLINE, stdin); ilength = strlen(linebuf); return(ret); } rawmode() { #ifdef BSD ioctl(0, TIOCGETP, &ttyb); ttyb.sg_flags &= ~ECHO; ttyb.sg_flags |= RAW; ioctl(0, TIOCSETN, &ttyb); #else ioctl(0, TCGETA, &st); st.c_iflag &= ~(INLCR | ICRNL | BRKINT); st.c_oflag |= OPOST; st.c_oflag &= ~(OLCUC | ONLCR | OCRNL | ONOCR | ONLRET); st.c_lflag &= ~(ICANON | ECHO | ISIG | ECHOK | ECHONL); st.c_cc[VMIN] = '\01'; st.c_cc[VTIME] = '\00'; ioctl(0, TCSETA, &st); #endif BSD /* Now in raw mode */ } ckdmode() { #ifdef BSD ioctl(0, TIOCGETP, &ttyb); ttyb.sg_flags |= ECHO; ttyb.sg_flags &= ~RAW; ioctl(0, TIOCSETN, &ttyb); #else ioctl(0, TCGETA, &st); st.c_iflag |= ICRNL; st.c_lflag |= (ICANON | ECHO); st.c_cc[VMIN] = st0.c_cc[VMIN]; st.c_cc[VTIME] = st0.c_cc[VTIME]; ioctl(0, TCSETA, &st); #endif BSD /* Now in cooked mode */ } mvcrsr(row, col) short row, col; { fflush(stdout); printf("%s", tgoto(CM, col-1, row-1)); } clrscrn() { mvcrsr(1, 1); tputs(CL, Termh, putchar); fflush(stdout); } docen() { char c, onmap(); while( prompt("cen>") != NULL ) { if( linebuf[0] == '.' ) break; if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { if( c == SPACE ) { fprintf(fdscrpt, "cen %d,%d\n", Xcur, Ycur); } if( c == TAB ) prfcen(); } } } dodes() { char c, desstr[4], onmap(); prdes(); while( prompt("des>") != NULL ) { if( linebuf[0] == '.' ) break; if( sscanf(linebuf, "%1[abcdfghimrtuwx#*!)+-]%*[^\n]\n", desstr) == 1 ) { if( desstr[0] != '\0' ) { Desig = desstr[0]; prdes(); linebuf[0] = '\n'; } } if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { if( c == SPACE ) { fprintf(fdscrpt, "des %d,%d %c\n", Xcur, Ycur, Desig); putchar( Desig ); } if( c == TAB ) prfcen(); } } } domov() { int ret; char c, onmap(); Pathl = 0; prrsrc(); prquant(); while( prompt("mov>") != NULL ) { if( linebuf[0] == '.' ) break; if( sscanf(linebuf, "%d%*[^\n]\n", &Quant) == 1 ) { prquant(); linebuf[0] = '\n'; } if( (ret = getrsrc()) != ERROR ) { Rsrc = ret; prrsrc(); linebuf[0] = '\n'; } if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { switch( c ) { case TAB: prfcen(); break; case PLUS: addsec(); break; case MINUS: delsec(); getsec(&s, secno(Xcur, Ycur)); break; case SPACE: if( Pathl == 0 && Quant > 0 ) break; if( addsec() != OK ) break; fprintf(fdscrpt, "mov %c %d,%d %d ", Rchar[Rsrc], Pathx[0], Pathy[0], Quant); mvcrsr((Pathy[0]-Yl+1), (Pathx[0]-Xl)*3+2); if( Quant == 0 ) { fprintf(fdscrpt, "\n"); delsec(); break; } moveit(); fprintf(fdscrpt, "v\ne\n"); break; } } } } dodel() { int ret, index, ix, iy; char c, onmap(); prrsrc(); prthresh(); while( prompt("del>") != NULL ) { if( linebuf[0] == '.' ) break; if( sscanf(linebuf, "%d%*[^\n]\n", &Thresh) == 1 ) { prthresh(); linebuf[0] = '\n'; } if( (ret = getrsrc()) != ERROR ) { Rsrc = ret; prmap(); prrsrc(); prthresh(); linebuf[0] = '\n'; } if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { switch( c ) { case TAB: prfcen(); break; case PLUS: addsec(); break; case SPACE: if( adjacent(Xcur, Ycur, Xlast, Ylast) != OK ) break; fprintf(fdscrpt, "del %c %d,%d\n%d,%d (%d)\n", Rchar[Rsrc], Xlast, Ylast, Xcur, Ycur, Thresh); ix = Xcur - Xlast; if( ix < -1 ) ix += XYMAX; if( ix > 1 ) ix -= XYMAX; iy = Ycur - Ylast; if( iy < -1 ) iy += XYMAX; if( iy > 1 ) iy -= XYMAX; index = (ix + 1)*3 + (iy + 1); mvcrsr(Ylast - Yl + 1, (Xlast - Xl)*3 + 1); putchar(Rtdirl[Rtxlat[index]]); mvcrsr(Ylast - Yl + 1, (Xlast - Xl)*3 + 3); putchar(Rtdirr[Rtxlat[index]]); addsec(); break; } } } } getrsrc() { int i; char rstr[4]; if( sscanf(linebuf, "%1[cmsgpob]%*[^\n]\n", rstr) != 1 ) { return(ERROR); } if( rstr[0] == '\0' ) return(ERROR); for( i = 0; i <= BAR; i++ ) { if( rstr[0] == Rchar[i] ) return(i); } return(ERROR); } doship() { int x, y, row, col, i; int shipok; char c, sorder[TMAXNO+1]; if( fdship == NULL ) return; prorder(); prshpnum(); while( prompt("ship>") != NULL ) { shipok = ERROR; for( i = 0; i <= TMAXNO; i++ ) { sorder[i] = ' '; } if( linebuf[0] == '.' ) break; if( sscanf(linebuf, "%d%*[^\n]\n", &Shpnum) == 1 ) { prshpnum(); shipok = OK; } sscanf(linebuf, "%8[pmdsftbcPMDSFTBC]%*[^\n]\n", sorder); for( i = 0; i <= TMAXNO; i++ ) { if( sorder[i] == '\0' || sorder[i] == ' ' ) break; Sorder[i] = tolower(sorder[i]); } if( sorder[0] != '\0' && sorder[0] != ' ' ) { Sorder[i] = '\0'; prorder(); shipok = OK; } if( linebuf[0] == '*' && linebuf[1] == '\n' ) { strcpy(Sorder, "cbdtspmf"); prorder(); shipok = OK; } if( linebuf[0] == '?' && linebuf[1] == '\n' ) { rewind(fdship); while( fread(&Ship, sizeof(struct shpstr), 1, fdship) == 1 ) { if( Ship.shp_effc == 0 ) continue; if( Foe != 0 && Ship.shp_own != 0 && Ship.shp_own != Foe ) continue; for( i = 0; i <= TMAXNO && Sorder[i]!='\0'; i++ ) { if( Sorder[i] == Stype[Ship.shp_type]) break; } if( Sorder[i] != Stype[Ship.shp_type]) continue; x = Ship.shp_xp; if( (Xcen - x) >= XYMAX/2 ) x += XYMAX; if( (x - Xcen) >= XYMAX/2 ) x -= XYMAX; if( x < Xl || x > Xh ) continue; y = Ship.shp_yp; if( (Ycen - y) >= XYMAX/2 ) y += XYMAX; if( (y - Ycen) >= XYMAX/2 ) y -= XYMAX; if( y < Yl || y > Yh ) continue; row = y - Yl + 1; col = (x - Xl)*3 + 1; if( Ship.shp_own == 0 ) col += 2; mvcrsr(row, col); putchar(toupper(Stype[Ship.shp_type])); } shipok = OK; } if( shipok == OK ) linebuf[0] = '\n'; if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { switch( c ) { case '\t': prship(); break; case 'i': prshplst(); break; case 'I': prshpsum(); break; } } } } donav() { int shipok; char c, onmap(); Pathl = 0; prorder(); prshpnum(); while( prompt("nav>") != NULL ) { shipok = ERROR; if( linebuf[0] == '.' ) break; if( linebuf[0] == '\n' ) ; else if( linebuf[0] == ',' ) { strcpy(Shiplist,","); shipok = OK; } else if( isalpha(linebuf[0]) ) { Shiplist[0] = linebuf[0]; Shiplist[1] = '\0'; shipok = OK; } else if( sscanf(linebuf,"%120[0123456789/]",Shiplist) == 1 ) { if( Shiplist[0] != '\0' && sscanf(Shiplist,"%d",&Shpnum) == 1 ) shipok=OK; } if( shipok == OK ) { linebuf[0] = '\n'; prnav(); } if( linebuf[0] != '\n' ) continue; while( (c = onmap()) != '\n' ) { switch(c) { case TAB: prship(); break; case 'i': prshplst(); break; case 'I': prshpsum(); break; case PLUS: addsec(); break; case MINUS: delsec(); break; case SPACE: if( Pathl == 0 ) break; if( addsec() != OK ) break; if( strchr(Shiplist, ',') != NULL ) { sprintf(Shiplist, "%d,%d", Pathx[0], Pathy[0]); } fprintf(fdscrpt,"nav %s ", Shiplist); moveit(); fprintf(fdscrpt, "\ne\n"); break; } } } } moveit() { int i, ix, iy, row, col; row = Pathy[0] - Yl + 1; col = (Pathx[0] - Xl)*3 + 2; mvcrsr(row, col); putchar('@'); mvcrsr(row, col); for( i = 1; i < Pathl; i++ ) { ix = Pathx[i] - Pathx[i-1]; if( ix < -1 ) ix += XYMAX; if( ix > 1 ) ix -= XYMAX; iy = Pathy[i] - Pathy[i-1]; if( iy < -1 ) iy += XYMAX; if( iy > 1 ) iy -= XYMAX; fprintf(fdscrpt, "%s", Movdir[(ix+1)*3 + (iy+1)]); row = Pathy[i] - Yl + 1; col = (Pathx[i] - Xl)*3 + 2; mvcrsr(row, col); putchar('@'); mvcrsr(row, col); } } prfunc() { mvcrsr(1, Censtrt); printf("Func: %-3s", Fchar[Func]); } prcoord() { mvcrsr(2, Censtrt); printf("Center: %3d,%-3d", Xcen, Ycen); } prdes() { mvcrsr(3, Censtrt); printf("Desig: %c ", Desig); } prrsrc() { mvcrsr(3, Censtrt); printf("Resource: %c ", Rchar[Rsrc]); } prthresh() { mvcrsr(4, Censtrt); printf("Thresh: %-3d", Thresh); } prquant() { mvcrsr(4, Censtrt); printf("Quant: %-4d", Quant); } prorder() { mvcrsr(3, Censtrt); printf("Order %-8s", Sorder); } prshpnum() { mvcrsr(4, Censtrt); printf("Ship: %-5d", Shpnum); } prnav() { char *p, out[8]; int i; mvcrsr(4, Censtrt); p = Shiplist; for( i = 0; i < 7; i++ ) { if( *p == '\0' || *p == '/' ) break; out[i] = *p++; } out[i] = '\0'; printf("Ship: %-5s", out); } prship() { short mbl; if( getship(&Ship, Shpnum) == ERROR ) return; mvcrsr(5, Censtrt); printf(" "); mvcrsr(6, Censtrt); printf("%c%5d,%-3d %3d ", toupper(Stype[ Ship.shp_type ]), Ship.shp_xp, Ship.shp_yp, Ship.shp_own); mvcrsr(7, Censtrt); /* kluge to handle unsigned characters (so ship.h doesn't have to change) */ if( (mbl = Ship.shp_mbl) > 127 ) mbl -= 256; printf("%3d%% %c %3d ", Ship.shp_effc, Ship.shp_fleet, mbl); mvcrsr(8, Censtrt); if( Ship.shp_type == S_CAR ) { printf("%3d %3d %2d %3d ", Ship.shp_crew, Ship.shp_shels, Ship.shp_gun, Ship.shp_plns); } else { printf("%3d %3d %2d ", Ship.shp_crew, Ship.shp_shels, Ship.shp_gun); } } prshpsum() { int num, frlist[TMAXNO+1], foelist[TMAXNO+1]; int i; rewind( fdship ); num = 0; for( i = 0; i <= TMAXNO; i++ ) { frlist[i] = foelist[i] = 0; } while( getship(&Ship, num++) != ERROR ) { if( Ship.shp_effc == 0 ) continue; if( (Ship.shp_xp - Xcur)%XYMAX != 0 ) continue; if( (Ship.shp_yp - Ycur)%XYMAX != 0 ) continue; if( Foe != 0 && Ship.shp_own != 0 && Foe != Ship.shp_own ) continue; if( Ship.shp_own == 0 ) { frlist[Ship.shp_type]++; } else { foelist[Ship.shp_type]++; } } mvcrsr(5, Censtrt); printf("%2.0dc %2.0db %2.0dd %2.0dt", frlist[S_CAR], frlist[S_BAT], frlist[S_DES], frlist[S_TEN]); mvcrsr(6, Censtrt); printf("%2.0ds %2.0dp %2.0dm %2.0df", frlist[S_SUB], frlist[S_PT ], frlist[S_MIN], frlist[S_FRE]); mvcrsr(7, Censtrt); printf("%2.0dc %2.0db %2.0dd %2.0dt", foelist[S_CAR], foelist[S_BAT], foelist[S_DES], foelist[S_TEN]); mvcrsr(8, Censtrt); printf("%2.0ds %2.0dp %2.0dm %2.0df", foelist[S_SUB], foelist[S_PT ], foelist[S_MIN], foelist[S_FRE]); } prshplst() { int num, field, frfld, foefld; int i; rewind(fdship); num = 0; frfld = 0; foefld = 21; while( getship(&Ship, num++) != ERROR ) { if( Ship.shp_effc == 0 ) continue; if( (Ship.shp_xp - Xcur)%XYMAX != 0 ) continue; if( (Ship.shp_yp - Ycur)%XYMAX != 0 ) continue; if( Foe != 0 && Ship.shp_own != 0 && Foe != Ship.shp_own ) continue; for( i=0; i<=TMAXNO && Sorder[i]!='\0'; i++ ) { if( Sorder[i] == Stype[Ship.shp_type]) break; } if( Sorder[i] != Stype[Ship.shp_type]) continue; if( Ship.shp_own == 0 ) { field = (frfld > 20) ? 20 : frfld++; } else { field = (foefld > 41) ? 41 : foefld++; } mvcrsr(10 + field/3, Censtrt + (field%3)*5); printf("%c%-4d",Stype[Ship.shp_type], num-1); } for( ; frfld <= 20; frfld++ ) { mvcrsr(10 + frfld/3, Censtrt + (frfld%3)*5); printf(" "); } for( ; foefld <= 41; foefld++ ) { mvcrsr(10 + foefld/3, Censtrt + (foefld%3)*5); printf(" "); } } addsec() { int i; if( Func == MOV || Func == NAV ) { i = (Pathl == 0) ? 0 : Pathl - 1; if( Pathl != 0 && adjacent(Xcur,Ycur,Pathx[i],Pathy[i]) != OK ) { return(ERROR); } if( Pathl == 0 || Xcur != Pathx[i] || Ycur != Pathy[i] ) { Pathx[Pathl] = Xcur; Pathy[Pathl] = Ycur; Pathl++; putchar('@'); } } Xlast = Xcur; Ylast = Ycur; return(OK); } delsec() { if( Func == MOV || Func == NAV ) { getsec(&s, secno(Xcur, Ycur)); putchar(s.s_des); if( Pathl <= 0 ) return; Pathl--; if( Pathl <= 0 ) return; Xcur = Pathx[Pathl-1]; Ycur = Pathy[Pathl-1]; } } adjacent(x, y, xl, yl) int x, y, xl, yl; { int xdiff, ydiff; xdiff = x - xl; if( xdiff < 0 ) xdiff = -xdiff; if( xdiff == (XYMAX-1) ) xdiff = 1; ydiff = y - yl; if( ydiff < 0 ) ydiff = -ydiff; if( ydiff == (XYMAX-1) ) ydiff = 1; if( (xdiff == 0 || xdiff == 1) && (ydiff == 0 || ydiff == 1) ) return(OK); return(ERROR); } prmap() { int height, width, xm, ym, row, col, nosect; clrscrn(); prfunc(); prcoord(); fflush(stdout); sleep(1); /* to make some terminals work at 9600 baud */ height = Termh - 3; width = Termw - CENSW - 4; row = 1; Yl = Ycen - height/2; Yh = Ycen + height/2; Xl = Xcen - width/6; Xh = Xcen + width/6; for( ym = Yl; ym <= Yh; ym++ ) { col = 1; nosect = TRUE; for( xm = Xl; xm <= Xh; xm++ ) { getsec(&s, secno(xm, ym)); if( s.s_des != '\0' && s.s_des != ' ' ) { if( nosect == TRUE ) { mvcrsr(row, col); nosect = FALSE; } if( s.s_coun != 0 && s.s_coun != 99 ) { if( s.s_des != '?' ) { if(Foe==0 || s.s_coun==98) { putchar('?'); } else { printf("%1d", s.s_coun%10); } } else { putchar(' '); } putchar(s.s_des); putchar(' '); } else if( s.s_coun == 99 ) { putchar('~'); putchar(s.s_des); putchar(' '); } else if( s.s_coun == 0 ) { if( Func == DEL ) { putchar(Rtdirl[(int)(s.s_del[Rsrc]&017)]); } else { putchar(' '); } if( s.s_des == '.' && s.s_rsrc[SHL] != 0 ) { putchar(':'); } else { putchar(s.s_des); } if( Func == DEL ) { putchar(Rtdirr[(int)(s.s_del[Rsrc]&017)]); } else { putchar(' '); } } } else { nosect = TRUE; } col += 3; } row++; } mvcrsr((Ycen - Yl), (Xcen - Xl)*3); } prcen() { char amntstr[8], thstr[8]; int i, xcur, ycur; xcur = Xcur; ycur = Ycur; if( Xcur < -XYMAX/2 ) xcur = Xcur + XYMAX; if( Xcur > XYMAX/2 ) xcur = Xcur - XYMAX; if( Ycur < -XYMAX/2 ) ycur = Ycur + XYMAX; if( Ycur > XYMAX/2 ) ycur = Ycur - XYMAX; mvcrsr(9, Censtrt); if( s.s_des == '\0' ) s.s_des = ' '; printf("%c%5d,%-3d %3d", s.s_des, xcur, ycur, s.s_coun); } prfcen() { int i, thrsh; char amntstr[8], thstr[8]; mvcrsr(10, Censtrt); printf(" "); mvcrsr(11, Censtrt); printf("%3d%%%10d", s.s_eff, s.s_mob); mvcrsr(12, Censtrt); printf("m%4d gm%4d", s.s_min, s.s_gold); mvcrsr(13, Censtrt); printf(" "); for( i = 0; i <= BAR; i++ ) { mvcrsr(14+i, Censtrt); sprintf(amntstr, "%d", s.s_rsrc[i]); if( *amntstr == '0' ) *amntstr = '.'; thrsh = (s.s_del[i] >> 4) & 017; thrsh *= 8; if( s.s_des == 'u' && i == CIV ) thrsh *= 10; if( s.s_des == 'b' && i == BAR ) thrsh *= 4; if( s.s_des == 'w' && (i==SHL || i==GUN || i==ORE) ) thrsh *= 10; sprintf(thstr, "%d ", thrsh); if( *thstr == '0' ) *thstr = '.'; printf("%c%5s%3s%5s ", Rchar[i], amntstr, Deldir[(int)(s.s_del[i]&017)], thstr); } mvcrsr(22, Censtrt); printf("prod%4d %c%c", s.s_prod, s.s_ckpt, s.s_def); } char onmap() { int row, col; char c; rawmode(); if( Func != SHP ) { getsec(&s, secno(Xcur, Ycur)); prcen(); } row = Ycur - Yl + 1; col = (Xcur - Xl)*3 + 2; mvcrsr(row, col); while( c = getchar() ) { switch( c ) { case LF: case CR: ckdmode(); return('\n'); case TAB: case 'i': case 'I': case PLUS: case MINUS: case SPACE: return(c); } switch( c ) { case UPLEFT: case LEFT : case DNLEFT: case VILEFT: if( Xcur <= Xl ) break; Xcur--; col -= 3; break; case UPRIGHT: case RIGHT : case DNRIGHT: case VIRIGHT: if( Xcur >= Xh ) break; Xcur++; col += 3; break; case DOWN: case UP: case VIDN: case VIUP: break; default: continue; } switch( c ) { case UPLEFT: case UP : case UPRIGHT: case VIUP: if( Ycur <= Yl ) break; Ycur--; row--; break; case DNLEFT: case DOWN : case DNRIGHT: case VIDN: if( Ycur >= Yh ) break; Ycur++; row++; break; } getsec(&s, secno(Xcur, Ycur)); prcen(); mvcrsr(row, col); } } @//E*O*F ./EHELP/ehelp.c// chmod u=rw,g=r,o=r ./EHELP/ehelp.c echo x - ./EHELP/Makefile sed 's/^@//' > "./EHELP/Makefile" <<'@//E*O*F ./EHELP/Makefile//' INSDIR=.. LIBDIR=../_unix.O GENLIB=$(LIBDIR)/genlib.a TERMLIB=$(LIBDIR)/termlib.a HDRDIR=../hdrs HEADERS= \ $(HDRDIR)/emp.h \ $(HDRDIR)/ship.h CFLAGS= -c -O ehelp: $(INSDIR)/ehelp $(INSDIR)/ehelp: _unix.O/ehelp.o $(GENLIB) $(TERMLIB) $(CC) -o $(INSDIR)/ehelp _unix.O/ehelp.o $(GENLIB) $(TERMLIB) _unix.O/ehelp.o: ehelp.c $(HEADERS) $(CC) $(CFLAGS) -I$(HDRDIR) ehelp.c @mv ehelp.o _unix.O/ehelp.o clean: rm -f _unix.O/*.o clobber: clean rm -f $(INSDIR)/ehelp FRC: @//E*O*F ./EHELP/Makefile// chmod u=rw,g=r,o=r ./EHELP/Makefile echo mkdir - ./EHELP/_unix.O mkdir ./EHELP/_unix.O chmod u=rwx,g=rx,o=rx ./EHELP/_unix.O echo x - ./EHELP/_unix.O/ehelp.o sed 's/^@//' > "./EHELP/_unix.O/ehelp.o" <<'@//E*O*F ./EHELP/_unix.O/ehelp.o//' @//E*O*F ./EHELP/_unix.O/ehelp.o// chmod u=rw,g=r,o=r ./EHELP/_unix.O/ehelp.o exit 0