2 * Empire - A multi-player, client/server Internet based war game.
3 * Copyright (C) 1986-2006, Dave Pare, Jeff Bailey, Thomas Ruschak,
4 * Ken Stevens, Steve McClure
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 * See the "LEGAL", "LICENSE", "CREDITS" and "README" files for all the
23 * related information and legal notices. It is expected that any future
24 * projects/authors will amend these files as needed.
28 * multifire.c: Fire at other sectors/ships
30 * Known contributors to this file:
56 targ_land, targ_ship, targ_sub, targ_unit, targ_bogus
60 struct emp_qelem queue; /* list of fired things */
61 int type; /* ship? otherwise sector */
62 int uid; /* ship uid */
63 coord x, y; /* sector coords */
64 int defdam; /* damage defenders did */
65 int victim; /* who I was shooting at */
74 static void add_to_fired_queue(struct emp_qelem *, struct emp_qelem *);
75 static int defend(struct emp_qelem *al,
77 enum targ_type target,
78 enum targ_type attacker,
82 struct shpstr *fship, int fx, int fy, int *nd);
83 static void do_defdam(struct emp_qelem *, double);
84 static int quiet_bigdef(int, struct emp_qelem *, natid, natid, coord,
86 static void use_ammo(struct emp_qelem *);
91 static int ef_with_guns[] = { EF_SECTOR, EF_SHIP, EF_LAND, EF_BAD };
116 enum targ_type target, attacker, orig_attacker;
119 struct nstr_item nbst;
125 struct emp_qelem fired, defended;
130 emp_initque(&defended);
131 if (!(p = getstarg(player->argp[1],
132 "Firing from ship(s), sect(s), or land unit(s)? ",
135 type = ef_byname_from(p, ef_with_guns);
136 if (type == EF_SECTOR) {
137 if (opt_NO_FORT_FIRE) {
138 pr("Fort firing is disabled.\n");
141 orig_attacker = attacker = targ_land;
143 } else if (type == EF_SHIP) {
144 orig_attacker = attacker = targ_ship;
145 } else if (type == EF_LAND) {
146 orig_attacker = attacker = targ_unit;
148 pr("Ships, land units or sectors only!\n");
151 if ((ptr = getstarg(player->argp[2], "Firing from? ", buf)) == 0
155 if (!snxtitem(&nbst, type, ptr))
158 if (player->aborted) {
159 pr("Fire aborted.\n");
162 while (nxtitem(&nbst, &item)) {
163 attacker = orig_attacker;
164 if (attacker == targ_unit) {
165 if (!getland(item.land.lnd_uid, &fland))
167 if (!getsect(item.land.lnd_x, item.land.lnd_y, &fsect))
169 if (item.land.lnd_own != player->cnum)
172 if (fland.lnd_frg == 0) {
173 pr("Unit %d cannot fire!\n", fland.lnd_uid);
176 if (lnd_getmil(&fland) < 1) {
177 pr("Unit %d cannot fire because it has no military!\n",
181 if (fland.lnd_ship >= 0) {
182 pr("Unit %d cannot fire because it is on a ship!\n",
186 if (fland.lnd_land >= 0) {
187 pr("Unit %d cannot fire because it is on a land unit!\n",
191 if (fland.lnd_effic < LAND_MINFIREEFF) {
192 pr("Unit %d cannot fire because it is less than %d%% efficient\n", fland.lnd_uid, LAND_MINFIREEFF);
195 resupply_commod(&fland, I_SHELL); /* Get more shells */
196 putland(fland.lnd_uid, &fland);
197 if (fland.lnd_item[I_SHELL] == 0) {
198 pr("%s -- not enough shells\n", prland(&fland));
201 } else if (attacker == targ_ship) {
202 if (!getship(item.ship.shp_uid, &fship))
204 if (item.ship.shp_own != player->cnum)
206 if (item.ship.shp_item[I_MILIT] < 1) {
207 pr("Not enough mil on ship #%d\n", item.ship.shp_uid);
210 gun = item.ship.shp_item[I_GUN];
211 gun = MIN(gun, item.ship.shp_glim);
212 if (item.ship.shp_frnge == 0) {
213 pr("Ships %d cannot fire guns!\n", item.ship.shp_uid);
217 pr("Not enough guns on ship #%d\n", item.ship.shp_uid);
220 if (item.ship.shp_item[I_SHELL] == 0) {
221 pr("Not enough shells on ship #%d\n", item.ship.shp_uid);
224 if (item.ship.shp_effic < 60) {
225 pr("Ship #%d is crippled!\n", item.ship.shp_uid);
228 fshipno = fship.shp_uid;
229 } else if (attacker == targ_land) {
230 if (!getsect(item.sect.sct_x, item.sect.sct_y, &fsect))
232 if (item.sect.sct_own != player->cnum)
234 if (item.sect.sct_type != SCT_FORTR)
236 if (item.sect.sct_effic < ((u_char)FORTEFF)) {
237 pr("Fort not efficient enough to fire!\n");
240 if (item.sect.sct_item[I_GUN] == 0) {
241 pr("Not enough guns in sector %s!\n",
242 xyas(item.sect.sct_x, item.sect.sct_y, player->cnum));
245 if (item.sect.sct_item[I_SHELL] == 0) {
246 pr("Not enough shells in sector %s!\n",
247 xyas(item.sect.sct_x, item.sect.sct_y, player->cnum));
250 if (item.sect.sct_item[I_MILIT] < 5) {
251 pr("Not enough military in sector %s!\n",
252 xyas(item.sect.sct_x, item.sect.sct_y, player->cnum));
255 pr("\nSector %s firing\n",
256 xyas(item.sect.sct_x, item.sect.sct_y, player->cnum));
258 if ((ptr = getstarg(player->argp[3], "Firing at? ", buf)) == 0
261 if (player->aborted) {
262 pr("Fire aborted.\n");
266 (void)strcpy(vbuf, ptr);
271 if (target == targ_ship) {
272 vshipno = atoi(vbuf);
273 if (vshipno < 0 || !getship(vshipno, &vship) ||
275 pr("No such ship exists!\n");
278 target = (mchr[(int)vship.shp_type].m_flags & M_SUB) ?
279 targ_sub : targ_ship;
280 vict = vship.shp_own;
283 if (!getsect(x, y, &vsect)) {
284 pr("No such sector exists!\n");
288 if (!sarg_xy(vbuf, &x, &y) || !getsect(x, y, &vsect)) {
289 pr("No such sector exists!\n");
292 /* We check the sector type, but we only use it for damage, not
293 reporting. That way, you don't get extra information you wouldn't
294 normally get. Besides, what if they want to slam water? :) */
295 if (vsect.sct_type == SCT_SANCT || vsect.sct_type == SCT_WATER)
299 vict = vsect.sct_own;
303 if (attacker == targ_ship) {
304 if (fship.shp_own != player->cnum) {
305 pr("Not your ship!\n");
308 if (target == targ_sub || target == targ_ship) {
309 if (fship.shp_uid == vship.shp_uid) {
310 pr("You can't fire upon yourself!\n");
317 attacker = (mchr[fship.shp_type].m_flags & M_SUB) ?
318 targ_sub : targ_ship;
319 if (attacker == targ_sub){
320 pr("Subs may not fire normally.. use torpedo.\n");
324 attacker = targ_ship;
325 if ((mil = fship.shp_item[I_MILIT]) < 1) {
326 pr("Not enough military for firing crew.\n");
329 gun = fship.shp_item[I_GUN];
330 gun = MIN(gun, fship.shp_glim);
331 if (fship.shp_frnge == 0 || gun == 0) {
332 pr("Insufficient arms.\n");
335 shell = fship.shp_item[I_SHELL];
337 shell += supply_commod(fship.shp_own, fship.shp_x,
338 fship.shp_y, I_SHELL, 2 - shell);
343 if (fship.shp_effic < 60) {
344 pr("Ship #%d is crippled (%d%%)\n", fshipno,
348 range = techfact(fship.shp_tech,
349 (double)fship.shp_frnge / 2.0);
350 range2 = (double)roundrange(range);
351 pr("range is %.2f (%.2f)\n", range2, range);
352 if (target == targ_sub) {
353 if ((mchr[(int)fship.shp_type].m_flags & M_DCH) == 0) {
354 /* Don't tell it's a sub */
356 } else if (shell < 2) {
357 pr("Not enough shells for depth charge!\n");
361 gun = MIN(gun, shell * 2);
362 gun = MIN(gun, mil / 2);
365 guneff = seagun(fship.shp_effic, shots);
367 shell -= ldround(((double)shots) / 2.0, 1);
368 fship.shp_item[I_SHELL] = shell;
369 if (opt_NOMOBCOST == 0)
370 fship.shp_mobil = MAX(fship.shp_mobil - 15, -100);
371 putship(fship.shp_uid, &fship);
372 } else if (attacker == targ_unit) {
373 if (fland.lnd_own != player->cnum) {
374 pr("Not your unit!\n");
378 if (target == targ_land) {
379 if (fland.lnd_x == vsect.sct_x
380 && fland.lnd_y == vsect.sct_y) {
381 pr("You can't fire upon yourself!\n");
389 if (fland.lnd_frg == 0) {
390 pr("Unit %d cannot fire!\n", fland.lnd_uid);
393 if (fland.lnd_item[I_SHELL] == 0) {
394 pr("%s -- not enough shells\n", prland(&fland));
398 shell = fland.lnd_item[I_SHELL];
400 range = techfact((int)fland.lnd_tech,
401 (double)fland.lnd_frg / 2.0);
402 range2 = (double)roundrange(range);
403 pr("range is %.2f (%.2f)\n", range2, range);
404 if (target == targ_sub) {
405 /* Don't tell it's a sub */
409 gun = fland.lnd_item[I_GUN];
411 pr("%s -- not enough guns\n", prland(&fland));
415 dam = (int)landunitgun(fland.lnd_effic, fland.lnd_dam, gun,
416 fland.lnd_ammo, shell);
417 if (target == targ_ship) {
418 if (chance(((double)fland.lnd_acc) / 100.0))
419 dam = ldround(((double)dam / 2.0), 1);
422 resupply_commod(&fland, I_SHELL); /* Get more shells */
423 putland(fland.lnd_uid, &fland);
427 if (fsect.sct_own != player->cnum ||
428 fsect.sct_type != SCT_FORTR) {
429 pr("No fortress at %s\n", xyas(fsect.sct_x,
430 fsect.sct_y, player->cnum));
433 if (target == targ_land) {
434 if (fsect.sct_x == vsect.sct_x
435 && fsect.sct_y == vsect.sct_y) {
436 pr("You can't fire upon yourself!\n");
440 attacker = targ_land;
441 if ((gun = fsect.sct_item[I_GUN]) == 0) {
442 pr("Insufficient arms.\n");
445 shell = fsect.sct_item[I_SHELL];
447 shell += supply_commod(fsect.sct_own, fsect.sct_x,
448 fsect.sct_y, I_SHELL, 1);
453 if (fsect.sct_item[I_MILIT] < 5) {
454 pr("Not enough military for firing crew.\n");
459 range = tfactfire(player->cnum, 7.0);
460 if (fsect.sct_effic > 59)
462 range2 = (double)roundrange(range);
463 pr("range is %.2f (%.2f)\n", range2, range);
464 if (target == targ_sub) {
465 /* Don't tell it's a sub */
468 guneff = landgun((int)fsect.sct_effic, gun);
471 fsect.sct_item[I_SHELL] = shell;
474 trange = mapdist(x, y, fx, fy);
475 if (trange > range2) {
476 pr("Target out of range.\n");
481 pr("Target out of range. Thud.\n");
484 pr("Target ship out of range. Splash.\n");
493 fland.lnd_mission = 0;
494 putland(fland.lnd_uid, &fland);
497 fship.shp_mission = 0;
498 putship(fship.shp_uid, &fship);
503 if (target == targ_bogus) {
504 if (vsect.sct_type == SCT_SANCT) {
505 pr("%s is a %s!!\n", vbuf,
506 dchr[SCT_SANCT].d_name);
508 } else if (vsect.sct_type == SCT_WATER) {
509 pr("You must specify a ship in sector %s!\n",
517 if (!trechk(player->cnum, vict, SEAFIR))
521 if (!trechk(player->cnum, vict, SUBFIR))
526 if (!trechk(player->cnum, vict, LANFIR))
534 if (target == targ_land) {
535 natp = getnatp(player->cnum);
536 rel = getrel(natp, vict);
537 if ((rel != AT_WAR) && (player->cnum != vict) &&
538 (vict) && (vsect.sct_oldown != player->cnum)) {
539 pr("You're not at war with them!\n");
549 if (vship.shp_rflags & RET_DCHRGED)
550 retreat_ship(&vship, 'd');
555 prb = (double)(range2 ? (trange / range2) : 1.0);
558 pr("Wind deflects shell%s.\n", splur(shots));
559 /* dam = (int)((double)dam / 2.0);*/
562 (double)((double)(90 - (random() % 11)) /
572 nreport(player->cnum, N_SCT_SHELL, vict, 1);
573 if (vict && vict != player->cnum)
575 "Country #%d shelled sector %s for %d damage.\n",
576 player->cnum, xyas(x, y, vict), dam);
577 pr("Shell%s hit sector %s for %d damage.\n",
578 splur(shots), xyas(x, y, player->cnum), dam);
579 /* Ok, it wasn't a bogus target, so do damage. */
580 if (target != targ_bogus)
581 sectdamage(&vsect, dam, 0);
584 nreport(player->cnum, N_SHP_SHELL, vict, 1);
587 if ((target != targ_sub) ||
588 ((vship.shp_rflags & RET_DCHRGED) == 0))
589 check_retreat_and_do_shipdamage(&vship, dam);
591 shipdamage(&vship, dam);
594 "Country #%d shelled %s in %s for %d damage.\n",
595 player->cnum, prship(&vship),
596 xyas(vship.shp_x, vship.shp_y, vict), dam);
598 pr("Shell%s hit %s in %s for %d damage.\n",
599 splur(shots), prsub(&vship),
600 xyas(vship.shp_x, vship.shp_y, player->cnum), dam);
602 if (vship.shp_effic < SHIP_MINEFF)
603 pr("%s sunk!\n", prsub(&vship));
607 /* Ok, now, check if we had a bogus target. If so,
608 just continue on, since there is no defender. */
609 if (target == targ_bogus)
611 if (attacker == targ_unit) {
612 attacker = targ_land;
613 getsect(fland.lnd_x, fland.lnd_y, &fsect);
616 defend(&fired, &defended, target, attacker, &vsect, &fsect,
617 &vship, &fship, fx, fy, &ndefending);
623 putship(vship.shp_uid, &vship);
626 if ((totaldefdam == 0) && (target == targ_ship))
627 if (vship.shp_rflags & RET_INJURED)
628 retreat_ship(&vship, 'h');
634 if ((target == targ_ship) || (target == targ_sub)) {
635 if (fship.shp_effic > SHIP_MINEFF) {
636 shp_missdef(&fship, vict);
639 putship(fship.shp_uid, &fship);
646 odds = ((double)ndefending) / ((double)nfiring);
649 do_defdam(&fired, odds);
654 defend(struct emp_qelem *al, struct emp_qelem *dl, enum targ_type target,
655 enum targ_type attacker, struct sctstr *vsect, struct sctstr *fsect,
656 struct shpstr *vship, struct shpstr *fship, int fx, int fy, int *nd)
660 int vict, nfiring = 0;
664 if (attacker == targ_land)
665 aown = fsect->sct_own;
667 aown = fship->shp_own;
669 if (target == targ_land)
670 vict = vsect->sct_own;
672 vict = vship->shp_own;
675 (dam = quiet_bigdef(attacker, dl, vict, aown, fx, fy, &nfiring))) {
678 fp = malloc(sizeof(struct flist));
679 memset(fp, 0, sizeof(struct flist));
684 fp->x = fsect->sct_x;
685 fp->y = fsect->sct_y;
686 fp->type = targ_land;
689 fp->type = targ_ship;
690 fp->uid = fship->shp_uid;
693 emp_insque(&fp->queue, al);
700 do_defdam(struct emp_qelem *list, double odds)
703 int dam, vict, first = 1;
707 struct emp_qelem *qp, *next;
709 for (qp = list->q_forw; qp != list; qp = next) {
711 fp = (struct flist *)qp;
712 if (fp->type == targ_ship) {
713 if (!getship(fp->uid, &ship) || !ship.shp_own)
718 pr("\nDefenders fire back!\n");
721 dam = (odds * (double)fp->defdam);
723 if (fp->type == targ_ship) {
725 pr("Return fire hit %s in %s for %d damage.\n",
727 xyas(ship.shp_x, ship.shp_y, player->cnum), dam);
730 "Return fire hit %s in %s for %d damage.\n",
731 prsub(&ship), xyas(ship.shp_x, ship.shp_y, vict), dam);
732 shipdamage(&ship, dam);
733 putship(ship.shp_uid, &ship);
735 getsect(fp->x, fp->y, §);
737 pr("Return fire hit sector %s for %d damage.\n",
738 xyas(fp->x, fp->y, player->cnum), dam);
739 sectdamage(§, dam, 0);
742 wu(0, vict, "Return fire hit sector %s for %d damage.\n",
743 xyas(fp->x, fp->y, vict), dam);
745 emp_remque(&fp->queue);
751 quiet_bigdef(int attacker, struct emp_qelem *list, natid own, natid aown,
752 coord ax, coord ay, int *nfiring)
755 double range, erange, hitchance;
759 int dam, dam2, rel, rel2;
761 struct sctstr firing;
769 snxtitem_dist(&ni, EF_SHIP, ax, ay, 8);
770 while (nxtitem(&ni, &ship)) {
771 if (ship.shp_own == 0)
774 if ((mchr[(int)ship.shp_type].m_flags & M_SUB) &&
775 (attacker == targ_land))
778 rel = getrel(getnatp(ship.shp_own), own);
779 rel2 = getrel(getnatp(ship.shp_own), aown);
780 if ((ship.shp_own != own) && ((rel != ALLIED) || (rel2 != AT_WAR)))
782 /* Don't shoot yourself */
783 if (ship.shp_own == aown)
785 if (ship.shp_effic < 60)
788 gun = ship.shp_item[I_GUN];
789 shell = ship.shp_item[I_SHELL];
791 if (ship.shp_item[I_MILIT] < 1)
794 if (mchr[(int)ship.shp_type].m_flags & M_SUB) {
795 if (shell < SHP_TORP_SHELLS)
796 shell += supply_commod(ship.shp_own, ship.shp_x, ship.shp_y,
797 I_SHELL, SHP_TORP_SHELLS - shell);
798 if (shell < SHP_TORP_SHELLS)
803 if (ship.shp_mobil <= 0)
806 erange = ship.shp_effic *
807 techfact(ship.shp_tech, ((double)ship.shp_frnge))
809 erange = (double)roundrange(erange);
810 range = mapdist(ship.shp_x, ship.shp_y, ax, ay);
813 if (!line_of_sight(NULL, ship.shp_x, ship.shp_y, ax, ay))
817 fp = malloc(sizeof(struct flist));
818 memset(fp, 0, sizeof(struct flist));
819 fp->type = targ_ship;
820 fp->uid = ship.shp_uid;
821 add_to_fired_queue(&fp->queue, list);
823 nreport(ship.shp_own, N_FIRE_BACK, player->cnum, 1);
825 hitchance = DTORP_HITCHANCE(range, ship.shp_visib);
826 if (!chance(hitchance))
829 dam += TORP_DAMAGE();
831 range = techfact(ship.shp_tech,
832 ship.shp_frnge * ship.shp_effic / 200.0);
833 range = (double)roundrange(range);
834 if (range < ni.curdist)
836 /* must have gun, shell, and milit to fire */
838 shell += supply_commod(ship.shp_own, ship.shp_x, ship.shp_y,
840 /* only need 1 shell, so don't check that */
843 nshot = MIN(gun, ship.shp_item[I_MILIT]);
844 nshot = MIN(nshot, ship.shp_glim);
848 fp = malloc(sizeof(struct flist));
849 memset(fp, 0, sizeof(struct flist));
850 fp->type = targ_ship;
851 fp->uid = ship.shp_uid;
852 add_to_fired_queue(&fp->queue, list);
853 nreport(ship.shp_own, N_FIRE_BACK, player->cnum, 1);
854 dam += seagun(ship.shp_effic, nshot);
857 snxtitem_dist(&ni, EF_LAND, ax, ay, 8);
858 while (nxtitem(&ni, &land)) {
859 if (land.lnd_own == 0)
861 if (land.lnd_effic < LAND_MINFIREEFF)
863 /* Can't fire if on a ship */
864 if (land.lnd_ship >= 0)
866 if (land.lnd_land >= 0)
868 /* Gotta have military */
869 if (lnd_getmil(&land) < 1)
871 /* Don't shoot yourself */
872 if (land.lnd_own == aown)
875 rel = getrel(getnatp(land.lnd_own), own);
876 rel2 = getrel(getnatp(land.lnd_own), aown);
878 if ((land.lnd_own != own) && ((rel != ALLIED) || (rel2 != AT_WAR)))
882 range = techfact((int)land.lnd_tech, (double)land.lnd_frg / 2.0);
883 range = (double)roundrange(range);
884 if (range < ni.curdist)
888 if (!has_supply(&land))
891 gun = land.lnd_item[I_GUN];
892 shell = land.lnd_item[I_SHELL];
894 if (land.lnd_item[I_MILIT] == 0 || shell == 0 || gun == 0)
897 dam2 = (int)landunitgun(land.lnd_effic, land.lnd_dam, gun,
898 land.lnd_ammo, shell);
901 fp = malloc(sizeof(struct flist));
902 memset(fp, 0, sizeof(struct flist));
903 fp->type = targ_unit;
904 fp->uid = land.lnd_uid;
905 add_to_fired_queue(&fp->queue, list);
907 putland(land.lnd_uid, &land);
908 nreport(land.lnd_own, N_FIRE_BACK, player->cnum, 1);
913 * Determine if any nearby gun-equipped sectors are within
914 * range and able to fire at an attacker. Firing sectors
915 * need to have guns, shells, and military. Sector being
916 * attacked is x,y -- attacker is at ax,ay.
919 if (!opt_NO_FORT_FIRE) {
920 snxtsct_dist(&ns, ax, ay, 8);
921 while (nxtsct(&ns, &firing)) {
923 if (firing.sct_type != SCT_FORTR)
925 if (firing.sct_own == 0)
927 rel = getrel(getnatp(firing.sct_own), own);
928 rel2 = getrel(getnatp(firing.sct_own), aown);
930 if ((firing.sct_own != own) &&
931 ((rel != ALLIED) || (rel2 != AT_WAR)))
933 /* Don't shoot yourself */
934 if (firing.sct_own == aown)
936 tech = tfactfire(firing.sct_own, 1.0);
938 if (firing.sct_effic > 59) /* fort bonus */
940 range = (double)roundrange(range);
941 if (range < ns.curdist)
944 gun = firing.sct_item[I_GUN];
945 shell = firing.sct_item[I_SHELL];
948 shell += supply_commod(firing.sct_own,
949 firing.sct_x, firing.sct_y,
951 if (gun == 0 || firing.sct_item[I_MILIT] < 5 || shell == 0)
954 fp = malloc(sizeof(struct flist));
955 memset(fp, 0, sizeof(struct flist));
956 fp->x = firing.sct_x;
957 fp->y = firing.sct_y;
958 fp->type = targ_land;
959 add_to_fired_queue(&fp->queue, list);
960 nreport(firing.sct_own, N_FIRE_BACK, player->cnum, 1);
963 dam += landgun((int)firing.sct_effic, gun);
967 return *nfiring == 0 ? 0 : dam / *nfiring;
971 use_ammo(struct emp_qelem *list)
973 struct emp_qelem *qp, *next;
983 /* use 1 shell from everyone */
984 for (qp = list->q_forw; qp != list; qp = next) {
986 fp = (struct flist *)qp;
987 if (fp->type == targ_ship) {
988 getship(fp->uid, &ship);
989 item = ship.shp_item;
990 if (mchr[(int)ship.shp_type].m_flags & M_SUB) {
991 shell = item[I_SHELL];
992 shell -= SHP_TORP_SHELLS - 1;
995 item[I_SHELL] = shell;
996 putship(ship.shp_uid, &ship);
997 mcp = &mchr[(int)ship.shp_type];
998 mobcost = ship.shp_effic * 0.01 * ship.shp_speed;
999 mobcost = (480.0 / (mobcost +
1000 techfact(ship.shp_tech, mobcost)));
1001 /* mob cost = 1/2 a sect's mob */
1003 ship.shp_mobil -= mobcost;
1005 } else if (fp->type == targ_land) {
1006 getsect(fp->x, fp->y, §);
1007 item = sect.sct_item;
1009 getland(fp->uid, &land);
1010 item = land.lnd_item;
1012 shell = item[I_SHELL];
1016 item[I_SHELL] = shell;
1017 if (fp->type == targ_ship)
1018 putship(ship.shp_uid, &ship);
1019 else if (fp->type == targ_land)
1022 putland(land.lnd_uid, &land);
1024 emp_remque(&fp->queue);
1031 add_to_fired_queue(struct emp_qelem *elem, struct emp_qelem *list)
1033 struct emp_qelem *qp;
1034 struct flist *fp, *ep;
1037 ep = (struct flist *)elem;
1039 /* Don't put them on the list if they're already there */
1040 for (qp = list->q_forw; qp != list; qp = qp->q_forw) {
1041 fp = (struct flist *)qp;
1042 if ((fp->type == targ_ship) && (fp->uid == ep->uid))
1044 if ((fp->type != targ_ship) && (fp->x == ep->x) &&
1050 emp_insque(elem, list);