DESTDIR, and general cleanup.
[unix-history] / usr / src / games / sail / dr_3.c
CommitLineData
b860dc81 1#ifndef lint
759267e0 2static char *sccsid = "@(#)dr_3.c 1.6 83/10/14";
b860dc81 3#endif
b860dc81 4
b3a57661 5#include "driver.h"
b860dc81
CL
6
7moveall() /* move all comp ships */
8{
b3a57661
EW
9 register struct ship *sp, *sq; /* r11, r10 */
10 register int n; /* r9 */
11 struct ship *closest;
12 register int k, l, m, ma; /* r8, r7, r6, */
6c17b19a
EW
13 int ta;
14 char af;
b3a57661
EW
15 int row[NSHIP], col[NSHIP], dir[NSHIP], r1, r2, c1, c2, d1, d2;
16 char clast[NSHIP][sizeof SHIP(0)->file->last];
b860dc81 17
b3a57661
EW
18 /*
19 * first try to create moves for OUR ships
20 */
21 foreachship(sp) {
6c17b19a 22 if (sp->file->captain[0] || sp->file->dir == 0)
b3a57661
EW
23 continue;
24 if (!sp->file->struck && windspeed && !snagged(sp)
25 && sp->specs->crew3) {
6c17b19a 26 ta = maxturns(sp, &af);
b3a57661
EW
27 ma = maxmove(sp, sp->file->dir, 0);
28 closest = closestenemy(sp, 0, 0);
29 if (closest == 0)
30 *sp->file->last = '\0';
b860dc81 31 else
b3a57661
EW
32 closeon(sp, closest, sp->file->last,
33 ta, ma, af);
34 } else
35 *sp->file->last = '\0';
759267e0
EW
36 /*
37 makesignal(sp, "move (%d): %s", 0, turn, sp->file->last);
38 */
b860dc81 39 }
b3a57661
EW
40 /*
41 * Then execute the moves for ALL ships (dead ones too),
42 * saving old positions in row[], col[], dir[],
43 * and the moves in clase[][].
44 * The new positions are written out.
45 */
46 n = 0;
47 foreachship(sp) {
48 if (snagged(sp))
b860dc81 49 clast[n][0] = '\0';
b3a57661
EW
50 else
51 (void) strcpy(clast[n], sp->file->last);
52 row[n] = sp->file->row;
53 col[n] = sp->file->col;
54 dir[n] = sp->file->dir;
55 moveship(sp, clast[n]);
56 n++;
b860dc81 57 }
b3a57661
EW
58 /*
59 * Now resolve collisions.
60 * This is the tough part.
61 */
62 for (k = 0; stillmoving(clast, k); k++) {
63 /*
64 * Step once.
65 * And propagate the nulls at the end of clast[].
66 */
67 n = 0;
68 foreachship(sp) {
b860dc81 69 if (dir[n])
b3a57661 70 step(clast[n][k], sp, row+n, col+n, dir+n);
b860dc81
CL
71 if (!clast[n][k])
72 clast[n][k+1] = '\0';
b3a57661 73 n++;
b860dc81 74 }
b3a57661
EW
75 /*
76 * The real stuff.
77 */
78 n = 0;
79 foreachship(sp) {
80 if ((d1 = sp->file->dir) == 0 || isolated(sp))
759267e0 81 goto cont1;
b3a57661
EW
82 r1 = sp->file->row;
83 c1 = sp->file->col;
84 sp->file->dir = dir[n];
85 sp->file->row = row[n];
86 sp->file->col = col[n];
87 l = 0;
88 foreachship(sq) {
759267e0
EW
89 if (sp == sq)
90 goto cont2;
91 if ((d2 = sq->file->dir) == 0)
92 goto cont2;
b3a57661
EW
93 r2 = sq->file->row;
94 c2 = sq->file->col;
95 sq->file->dir = dir[l];
96 sq->file->row = row[l];
97 sq->file->col = col[l];
759267e0 98 if (snagged2(sp, sq)
b3a57661
EW
99 && push(sp, sq) && range(sp, sq) > 1) {
100 Write(W_SHIPROW, sq, 0,
101 sp->file->row - 1, 0, 0, 0);
102 if (sp->file->dir == 1
103 || sp->file->dir == 5) /* XXX */
104 Write(W_SHIPCOL, sq, 0,
105 sp->file->col - 1,
106 0, 0, 0);
107 else
108 Write(W_SHIPCOL, sq, 0,
109 sp->file->col, 0, 0, 0);
110 Write(W_SHIPDIR, sq, 0,
111 sp->file->dir, 0, 0, 0);
112 }
113 if (!range(sp, sq) && !fouled2(sp, sq)
114 && push(sp, sq)) {
115 makesignal(sp,
116 "collision with %s (%c%c)", sq);
117 if (die() < 4) {
118 makesignal(sp,
119 "fouled with %s (%c%c)",
120 sq);
121 for (m = 0; m < NSHIP && sp->file->fouls[m].turnfoul; m++)
122 ;
123 if (m < NSHIP)
124 Write(W_FOUL, sp, 0,
125 m, turn, l, 0);
126 for (m = 0; m < NSHIP && sq->file->fouls[m].turnfoul; m++)
127 ;
128 if (m < NSHIP)
129 Write(W_FOUL, sq, 0,
130 m, turn, n, 0);
b860dc81 131 }
b3a57661
EW
132 clast[n][k+1] = '\0';
133 sp->file->row = r2;
134 sp->file->col = c2;
135 sp->file->dir = d2;
136 moveship(sp, clast[n]);
137 Write(W_SHIPROW, sq, 0,
138 sp->file->row-1, 0, 0, 0);
139 if (sp->file->dir == 1
140 || sp->file->dir == 5)
141 Write(W_SHIPCOL, sq, 0,
142 sp->file->col-1, 0, 0, 0);
143 else
144 Write(W_SHIPCOL, sq, 0,
145 sp->file->col, 0, 0, 0);
146 Write(W_SHIPDIR, sq, 0,
147 sp->file->dir, 0, 0, 0);
148 Write(W_DRIFT, sq, 0, 0, 0, 0, 0);
149 Write(W_DRIFT, sp, 0, 0, 0, 0, 0);
759267e0 150 goto cont2;
b860dc81 151 }
759267e0
EW
152 sq->file->row = r2;
153 sq->file->col = c2;
154 sq->file->dir = d2;
155 cont2:
b3a57661 156 l++;
b860dc81 157 }
b3a57661
EW
158 sp->file->row = r1;
159 sp->file->col = c1;
160 sp->file->dir = d1;
759267e0 161 cont1:
b3a57661 162 n++;
b860dc81
CL
163 }
164 }
b3a57661
EW
165 /*
166 * Clear old moves.
167 */
168 foreachship(sp)
169 sp->file->last[0] = 0;
b860dc81
CL
170}
171
172stillmoving(last, k)
b3a57661 173char last[][sizeof SHIP(0)->file->last]; /* how's that for portability */
b860dc81
CL
174register int k;
175{
b3a57661
EW
176 register struct ship *sp;
177 register char (*p)[sizeof *last]; /* and this? */
b860dc81 178
b3a57661
EW
179 p = last;
180 foreachship(sp) {
181 if ((*p)[k])
182 return 1;
183 p++;
184 }
185 return 0;
b860dc81
CL
186}
187
188isolated(ship)
b3a57661 189register struct ship *ship;
b860dc81 190{
b3a57661 191 register struct ship *sp;
b860dc81 192
b3a57661
EW
193 foreachship(sp) {
194 if (ship != sp && range(ship, sp) <= 10)
195 return 0;
196 }
197 return 1;
b860dc81
CL
198}
199
b3a57661 200/* XXX */
b860dc81 201push(from, to)
b3a57661 202register struct ship *from, *to;
b860dc81
CL
203{
204 int bow1r, bow1c, bow2r, bow2c, stern1r, stern1c, stern2r, stern2c;
205 register int bs, sb;
206
b3a57661
EW
207 stern1r = bow1r = from->file->row;
208 stern1c = bow1c = from->file->col;
209 stern2r = bow2r = to->file->row;
210 stern2c = bow2c = to->file->col;
211 stern2r += dr[to->file->dir];
212 stern2c += dc[to->file->dir];
b860dc81
CL
213 bs = bow1r - stern2r + bow1c - stern2c;
214 sb = stern1r - bow2r + stern1c - bow2c;
215 if (!bs)
b3a57661
EW
216 return 1;
217 stern1r += dr[from->file->dir];
218 stern1c += dc[from->file->dir];
b860dc81 219 if(!sb)
b3a57661
EW
220 return 0;
221 sb = to->specs->class;
222 bs = from->specs->class;
223 if (sb > bs)
224 return 1;
b860dc81 225 if (sb < bs)
b3a57661
EW
226 return 0;
227 return from < to;
b860dc81
CL
228}
229
b3a57661
EW
230step(com, ship, row, col, dir)
231register struct ship *ship;
232register int *row, *col, *dir;
b860dc81
CL
233char com;
234{
b860dc81
CL
235 register int dist;
236
b3a57661
EW
237 switch (com) {
238 case 'r':
239 if (++*dir == 9)
240 *dir = 1;
241 break;
242 case 'l':
243 if (--*dir == 0)
244 *dir = 8;
245 break;
246 case '0': case '1': case '2': case '3':
247 case '4': case '5': case '6': case '7':
248 if (*dir % 2 == 0)
249 dist = dtab[com - '0'];
250 else
251 dist = com - '0';
252 *row -= dr[*dir] * dist;
253 *col -= dc[*dir] * dist;
254 break;
255 case 'b':
256 break;
257 case 'd':
258 if (ship->specs->class >= 3 && !snagged(ship)
259 || turn % 2 == 0) {
260 *row -= dr[winddir];
261 *col -= dc[winddir];
262 }
263 break;
b860dc81
CL
264 }
265}
266
b3a57661
EW
267sendbp(from, to, sections, isdefense)
268register struct ship *from, *to;
269int sections;
270char isdefense;
b860dc81
CL
271{
272 int n;
b3a57661 273 register struct BP *bp;
b860dc81 274
b3a57661
EW
275 bp = isdefense ? from->file->DBP : from->file->OBP;
276 for (n = 0; n < 3 && bp[n].turnsent; n++)
277 ;
278 if (n < 3 && sections) {
279 Write(isdefense ? W_DBP : W_OBP, from, 0,
280 turn, to-SHIP(0), sections, 0);
281 if (isdefense)
282 makesignal(from, "repelling boarders",
283 (struct ship *)0);
b860dc81 284 else
b3a57661 285 makesignal(from, "boarding the %s (%c%c)", to);
b860dc81
CL
286 }
287}
288
b3a57661
EW
289toughmelee(ship, to, isdefense, count)
290register struct ship *ship, *to;
291int isdefense, count;
b860dc81 292{
b3a57661
EW
293 register struct BP *bp;
294 register obp = 0;
295 int n, OBP = 0, DBP = 0, dbp = 0;
b860dc81 296 int qual;
b860dc81 297
b3a57661
EW
298 qual = ship->specs->qual;
299 bp = isdefense ? ship->file->DBP : ship->file->OBP;
300 for (n = 0; n < NBP; n++, bp++) {
301 if (bp->turnsent && (to == bp->toship || isdefense)) {
302 obp += bp->mensent / 100
303 ? ship->specs->crew1 * qual : 0;
304 obp += (bp->mensent % 100)/10
305 ? ship->specs->crew2 * qual : 0;
306 obp += bp->mensent % 10
307 ? ship->specs->crew3 * qual : 0;
b860dc81
CL
308 }
309 }
b3a57661
EW
310 if (count || isdefense)
311 return obp;
312 OBP = toughmelee(to, ship, 0, count + 1);
313 dbp = toughmelee(ship, to, 1, count + 1);
314 DBP = toughmelee(to, ship, 1, count + 1);
b860dc81 315 if (OBP > obp + 10 || OBP + DBP >= obp + dbp + 10)
b3a57661 316 return 1;
b860dc81 317 else
b3a57661 318 return 0;
b860dc81
CL
319}
320
321reload()
322{
b3a57661 323 register struct ship *sp;
b860dc81 324
b3a57661
EW
325 foreachship(sp) {
326 sp->file->loadwith = 0;
327 }
b860dc81
CL
328}
329
330checksails()
331{
b3a57661
EW
332 register struct ship *sp;
333 register int rig, full;
334 struct ship *close;
b860dc81 335
b3a57661
EW
336 foreachship(sp) {
337 if (sp->file->captain[0] != 0)
338 continue;
339 rig = sp->specs->rig1;
340 if (windspeed == 6 || windspeed == 5 && sp->specs->class > 4)
b860dc81 341 rig = 0;
b3a57661
EW
342 if (rig && sp->specs->crew3) {
343 close = closestenemy(sp, 0, 0);
344 if (close != 0) {
345 if (range(sp, close) > 9)
346 full = 1;
347 else
b860dc81 348 full = 0;
b3a57661 349 } else
b860dc81 350 full = 0;
b3a57661
EW
351 } else
352 full = 0;
353 if ((sp->file->FS != 0) != full)
354 Write(W_FS, sp, 0, full, 0, 0, 0);
b860dc81
CL
355 }
356}