6
|
1 /*--------------------------------------------------------------------------
|
|
2 NETREK II -- Paradise
|
|
3
|
|
4 Permission to use, copy, modify, and distribute this software and its
|
|
5 documentation, or any derivative works thereof, for any NON-COMMERCIAL
|
|
6 purpose and without fee is hereby granted, provided that this copyright
|
|
7 notice appear in all copies. No representations are made about the
|
|
8 suitability of this software for any purpose. This software is provided
|
|
9 "as is" without express or implied warranty.
|
|
10
|
|
11 Xtrek Copyright 1986 Chris Guthrie
|
|
12 Netrek (Xtrek II) Copyright 1989 Kevin P. Smith
|
|
13 Scott Silvey
|
|
14 Paradise II (Netrek II) Copyright 1993 Larry Denys
|
|
15 Kurt Olsen
|
|
16 Brandon Gillespie
|
|
17 --------------------------------------------------------------------------*/
|
|
18
|
|
19 #include "config.h"
|
|
20 #include <stdio.h>
|
|
21 #include <sys/types.h>
|
|
22 #include <sys/ipc.h>
|
|
23 #include <sys/shm.h>
|
|
24 #include <errno.h>
|
|
25 #include <signal.h>
|
|
26
|
|
27 #include "shmem.h"
|
|
28 #include "path.h"
|
|
29 #include "data.h"
|
|
30
|
|
31 /*---------------------------SHARED MEMORY STRUCTURE----------------------*/
|
|
32
|
|
33 #include "shmemP.h"
|
|
34
|
|
35 /*-------------------------------------------------------------------------*/
|
|
36
|
|
37 struct player *players;
|
|
38 struct torp *torps;
|
|
39 struct missile *missiles;
|
|
40 struct thingy *thingies;
|
|
41 struct plasmatorp *plasmatorps;
|
|
42 struct status *status;
|
|
43 struct status2 *status2;
|
|
44 struct planet *planets;
|
|
45 struct t_unit *terrain_grid;
|
|
46 struct phaser *phasers;
|
|
47 int *stars;
|
|
48 struct mctl *mctl;
|
|
49 struct message *messages;
|
|
50 struct team *teams;
|
|
51
|
|
52 struct ship *shipvals;
|
|
53 struct configuration *configvals;
|
|
54 int *shipsallowed; /* points inside configvals */
|
|
55 int *weaponsallowed; /* ditto */
|
|
56 int *sun_effect;
|
|
57 int *ast_effect;
|
|
58 int *neb_effect;
|
|
59 int *wh_effect;
|
|
60 int *num_nebula;
|
|
61 int *nebula_density;
|
|
62 int *nebula_subclouds;
|
|
63 int *num_asteroid;
|
|
64 float *asteroid_thickness;
|
|
65 int *asteroid_density;
|
|
66 int *asteroid_radius;
|
|
67 float *asteroid_thick_variance;
|
|
68 int *asteroid_dens_variance;
|
|
69 int *asteroid_rad_variance;
|
|
70 int *improved_tracking;
|
|
71 int *tstart;
|
|
72 int *newgalaxy;
|
|
73 int *nontteamlock;
|
|
74 char *cluephrase_storage;
|
|
75
|
|
76 static int PKEY = 128;
|
|
77
|
|
78 /*------------------------------STARTDAEMON---------------------------------*/
|
|
79 /*
|
|
80 * This function starts the daemon. It get the path to where the daemon
|
|
81 * resides, then tries to start it up.
|
|
82 */
|
|
83
|
|
84
|
|
85 #ifndef SYSV /* HP/UX hates this */
|
|
86 extern int fprintf();
|
|
87 #endif
|
|
88 extern pid_t fork();
|
|
89 extern int execl();
|
|
90 extern void perror();
|
|
91 extern int shmget();
|
|
92 #ifndef IRIX
|
|
93 extern int shmctl();
|
|
94 #endif
|
|
95 extern unsigned int sleep();
|
|
96 extern uid_t geteuid();
|
|
97
|
|
98 void
|
|
99 startdaemon(leagueflag, restart)
|
|
100 int leagueflag, restart;
|
|
101 {
|
|
102 int i; /* temp var */
|
|
103 char *hell; /* to hold path to daemon */
|
|
104
|
|
105 if (restart)
|
|
106 {
|
|
107 fprintf(stderr, "RE-");
|
|
108 kill(status->nukegame, SIGKILL); /* daemon is killed without giving it
|
|
109 * a chance to blast the shmem */
|
|
110 sleep(2);
|
|
111 }
|
|
112 fprintf(stderr, "Starting daemon...\n"); /* record that deaemon is */
|
|
113 i = fork(); /* starting */
|
|
114 if (i == 0)
|
|
115 { /* if successful */
|
|
116 char *nargv[10];
|
|
117 int argc = 0;
|
|
118 hell = build_path(DAEMON);
|
|
119 nargv[argc++] = "daemon";
|
|
120 if (leagueflag)
|
|
121 nargv[argc++] = "-l";
|
|
122 if (restart)
|
|
123 nargv[argc++] = "-a";
|
|
124 nargv[argc] = 0;
|
|
125 execv(hell, nargv);
|
|
126
|
|
127 perror(hell); /* did it work */
|
|
128 fprintf(stderr, "Couldn't start daemon!!!\n");
|
|
129 _exit(1); /* let's get out of here */
|
|
130 }
|
|
131 }
|
|
132
|
|
133
|
|
134
|
|
135 static int shmid = -1; /* ID number of shared mem */
|
|
136
|
|
137
|
|
138 /*--------------------------------OPENMEM----------------------------------*/
|
|
139 /*
|
|
140 * if code is 0, openmem will exit(1) upon finding the memory gone. if code
|
|
141 * is 1, openmem will fork a netrek daemon and retry. if code is 2, openmem
|
|
142 * will blast any already existing shared memory.
|
|
143 */
|
|
144
|
|
145 void
|
|
146 openmem(code, leagueflag)
|
|
147 int code;
|
|
148 int leagueflag; /* only used if code==1 */
|
|
149 {
|
|
150 extern int errno; /* to get error number */
|
|
151 key_t shmemKey = PKEY; /* shared memory's key */
|
|
152 struct memory *sharedMemory; /* to point to shared memory */
|
|
153 char *k;
|
|
154
|
|
155 k = getenv("TREKSHMKEY"); /* grab shared mem id environment variable */
|
|
156 if (k)
|
|
157 { /* if it's set... */
|
|
158 int i;
|
|
159 if (sscanf(k, "%d", &i) > 0 && i > 0) /* ...grab its value... */
|
|
160 shmemKey = i; /* ...and use it */
|
|
161 }
|
|
162
|
|
163 errno = 0; /* clear error number */
|
|
164 shmid = shmget(shmemKey, 0, 0); /* get id of shared mem */
|
|
165 if (code == 2)
|
|
166 {
|
|
167 if (shmid >= 0)
|
|
168 {
|
|
169 /* If we're in daemon mode and we opened the memory */
|
|
170 /* "There can be only one". */
|
|
171 fprintf(stderr, "Killing existing segment\n");
|
|
172 shmctl(shmid, IPC_RMID, (struct shmid_ds *) 0);
|
|
173 /* create a new one */
|
|
174 }
|
|
175 shmid = shmget(shmemKey, sizeof(struct memory), IPC_CREAT | 0666);
|
|
176 }
|
|
177 if (shmid < 0)
|
|
178 { /* if shared mem does not exist */
|
|
179 switch (code)
|
|
180 {
|
|
181 case 0:
|
|
182 if (errno != ENOENT)
|
|
183 { /* catastrophic, sell all your stock */
|
|
184 perror("shmget"); /* and leave the country type of */
|
|
185 exit(1); /* error--suicide */
|
|
186 }
|
|
187 fprintf(stderr, "Daemon not running (err:%d)\n", errno);
|
|
188 exit(1);
|
|
189 case 1:
|
|
190 if (errno != ENOENT)
|
|
191 { /* catastrophic, sell all your stock */
|
|
192 perror("shmget"); /* and leave the country type of */
|
|
193 exit(1); /* error--suicide */
|
|
194 }
|
|
195 startdaemon(leagueflag, 0); /* try to start the daemon */
|
|
196 sleep(2); /* wait for a sec for deamon to start */
|
|
197 shmid = shmget(shmemKey, 0, 0); /* try again to get shared mem */
|
|
198 if (shmid < 0)
|
|
199 { /* failure again then get out of here */
|
|
200 fprintf(stderr, "Daemon not running (err:%d)\n", errno);
|
|
201 exit(1);
|
|
202 }
|
|
203 break;
|
|
204 case 2:
|
|
205 perror("daemon: can't open shared memory");
|
|
206 exit(1);
|
|
207 }
|
|
208 }
|
|
209 if (code == 2)
|
|
210 {
|
|
211 struct shmid_ds smbuf;
|
|
212
|
|
213 shmctl(shmid, IPC_STAT, &smbuf); /* Hose Ed's robots */
|
|
214 smbuf.shm_perm.uid = geteuid();
|
|
215 smbuf.shm_perm.mode = 0666;
|
|
216 shmctl(shmid, IPC_SET, &smbuf);
|
|
217 }
|
|
218 sharedMemory = (struct memory *) shmat(shmid, (char *) 0, 0);
|
|
219 if (sharedMemory == (struct memory *) - 1)
|
|
220 {
|
|
221 perror("shared memory");
|
|
222 exit(1);
|
|
223 }
|
|
224 if (code == 2)
|
|
225 {
|
|
226 /* set the magic number */
|
|
227 sharedMemory->shmem_size = sizeof(struct memory);
|
|
228 }
|
|
229 else
|
|
230 {
|
|
231 if (sharedMemory->shmem_size != sizeof(struct memory))
|
|
232 {
|
|
233 fprintf(stderr, "shared memory segment magic number mismatch!\
|
|
234 (%d != %ld)\n aborting to prevent corruption of game data\n",
|
|
235 sharedMemory->shmem_size, (long) sizeof(struct memory));
|
|
236 exit(1);
|
|
237 }
|
|
238 }
|
|
239 players = sharedMemory->players; /* set pointer to fields */
|
|
240 torps = sharedMemory->torps; /* in shared memory structure */
|
|
241 missiles = sharedMemory->missiles; /* for easy access */
|
|
242 thingies = sharedMemory->thingies;
|
|
243 plasmatorps = sharedMemory->plasmatorps;
|
|
244 status = &sharedMemory->status;
|
|
245 status2 = &sharedMemory->status2;
|
|
246 planets = sharedMemory->planets;
|
|
247 terrain_grid = sharedMemory->terrain_grid;
|
|
248 phasers = sharedMemory->phasers;
|
|
249 stars = sharedMemory->stars;
|
|
250 mctl = &sharedMemory->mctl;
|
|
251 messages = sharedMemory->messages;
|
|
252 teams = sharedMemory->teams;
|
|
253 shipvals = sharedMemory->shipvals;
|
|
254 configvals = &sharedMemory->configvals;
|
|
255 galaxyValid = &sharedMemory->galaxyValid;
|
|
256 /* configvals->gwidth = 200000; *//* pick up from galaxy generator later */
|
|
257 /* configvals->numplanets = 60; *//* this too */
|
|
258
|
|
259 shipsallowed = configvals->shipsallowed;
|
|
260 weaponsallowed = configvals->weaponsallowed;
|
|
261 sun_effect = configvals->sun_effect;
|
|
262 ast_effect = configvals->ast_effect;
|
|
263 neb_effect = configvals->neb_effect;
|
|
264 wh_effect = configvals->wh_effect;
|
|
265 num_nebula = &(configvals->num_nebula);
|
|
266 nebula_density = &(configvals->nebula_density);
|
|
267 nebula_subclouds = &(configvals->nebula_subclouds);
|
|
268 num_asteroid = &(configvals->num_asteroid);
|
|
269 asteroid_thickness = &(configvals->asteroid_thickness);
|
|
270 asteroid_density = &(configvals->asteroid_density);
|
|
271 asteroid_radius = &(configvals->asteroid_radius);
|
|
272 asteroid_thick_variance = &(configvals->asteroid_thick_variance);
|
|
273 asteroid_dens_variance = &(configvals->asteroid_dens_variance);
|
|
274 asteroid_rad_variance = &(configvals->asteroid_rad_variance);
|
|
275 improved_tracking = configvals->improved_tracking;
|
|
276
|
|
277 cluephrase_storage = sharedMemory->cluephrase_storage;
|
|
278
|
|
279 stars[1] = -1;
|
|
280 }
|
|
281
|
|
282 void
|
|
283 blast_shmem()
|
|
284 {
|
|
285 shmctl(shmid, IPC_RMID, (struct shmid_ds *) 0);
|
|
286 }
|