|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1983 Regents of the University of California. ! 3: * All rights reserved. The Berkeley software License Agreement ! 4: * specifies the terms and conditions for redistribution. ! 5: */ ! 6: ! 7: #ifndef lint ! 8: static char sccsid[] = "@(#)sync.c 5.2 (Berkeley) 1/21/86"; ! 9: #endif not lint ! 10: ! 11: #include "externs.h" ! 12: #include <sys/file.h> ! 13: #include <sys/errno.h> ! 14: ! 15: #define BUFSIZE 4096 ! 16: ! 17: static char sync_buf[BUFSIZE]; ! 18: static char *sync_bp = sync_buf; ! 19: static char sync_lock[25]; ! 20: static char sync_file[25]; ! 21: static long sync_seek; ! 22: static FILE *sync_fp; ! 23: #define SF "/tmp/#sailsink.%d" ! 24: #define LF "/tmp/#saillock.%d" ! 25: ! 26: /*VARARGS3*/ ! 27: makesignal(from, fmt, ship, a, b, c) ! 28: struct ship *from; ! 29: char *fmt; ! 30: register struct ship *ship; ! 31: { ! 32: char message[80]; ! 33: ! 34: if (ship == 0) ! 35: (void) sprintf(message, fmt, a, b, c); ! 36: else ! 37: (void) sprintf(message, fmt, ! 38: ship->shipname, colours(ship), ! 39: sterncolour(ship), a, b, c); ! 40: Write(W_SIGNAL, from, 1, (int)message, 0, 0, 0); ! 41: } ! 42: ! 43: #include <sys/types.h> ! 44: #include <sys/stat.h> ! 45: sync_exists(game) ! 46: { ! 47: char buf[sizeof sync_file]; ! 48: struct stat s; ! 49: time_t t; ! 50: ! 51: (void) sprintf(buf, SF, game); ! 52: (void) time(&t); ! 53: if (stat(buf, &s) < 0) ! 54: return 0; ! 55: if (s.st_mtime < t - 60*60*2) { /* 2 hours */ ! 56: (void) unlink(buf); ! 57: (void) sprintf(buf, LF, game); ! 58: (void) unlink(buf); ! 59: return 0; ! 60: } else ! 61: return 1; ! 62: } ! 63: ! 64: sync_open() ! 65: { ! 66: if (sync_fp != NULL) ! 67: (void) fclose(sync_fp); ! 68: (void) sprintf(sync_lock, LF, game); ! 69: (void) sprintf(sync_file, SF, game); ! 70: if (access(sync_file, 0) < 0) { ! 71: int omask = umask(issetuid ? 077 : 011); ! 72: sync_fp = fopen(sync_file, "w+"); ! 73: (void) umask(omask); ! 74: } else ! 75: sync_fp = fopen(sync_file, "r+"); ! 76: if (sync_fp == NULL) ! 77: return -1; ! 78: sync_seek = 0; ! 79: return 0; ! 80: } ! 81: ! 82: sync_close(remove) ! 83: char remove; ! 84: { ! 85: if (sync_fp != 0) ! 86: (void) fclose(sync_fp); ! 87: if (remove) ! 88: (void) unlink(sync_file); ! 89: } ! 90: ! 91: Write(type, ship, isstr, a, b, c, d) ! 92: int type; ! 93: struct ship *ship; ! 94: char isstr; ! 95: int a, b, c, d; ! 96: { ! 97: if (isstr) ! 98: (void) sprintf(sync_bp, "%d %d %d %s\n", ! 99: type, ship->file->index, isstr, a); ! 100: else ! 101: (void) sprintf(sync_bp, "%d %d %d %d %d %d %d\n", ! 102: type, ship->file->index, isstr, a, b, c, d); ! 103: while (*sync_bp++) ! 104: ; ! 105: sync_bp--; ! 106: if (sync_bp >= &sync_buf[sizeof sync_buf]) ! 107: abort(); ! 108: (void) sync_update(type, ship, a, b, c, d); ! 109: } ! 110: ! 111: Sync() ! 112: { ! 113: int (*sighup)(), (*sigint)(); ! 114: register n; ! 115: int type, shipnum, isstr, a, b, c, d; ! 116: char buf[80]; ! 117: char erred = 0; ! 118: extern errno; ! 119: ! 120: sighup = signal(SIGHUP, SIG_IGN); ! 121: sigint = signal(SIGINT, SIG_IGN); ! 122: for (n = TIMEOUT; --n >= 0;) { ! 123: #ifdef LOCK_EX ! 124: if (flock(fileno(sync_fp), LOCK_EX|LOCK_NB) >= 0) ! 125: break; ! 126: if (errno != EWOULDBLOCK) ! 127: return -1; ! 128: #else ! 129: if (link(sync_file, sync_lock) >= 0) ! 130: break; ! 131: if (errno != EEXIST) ! 132: return -1; ! 133: #endif ! 134: sleep(1); ! 135: } ! 136: if (n <= 0) ! 137: return -1; ! 138: (void) fseek(sync_fp, sync_seek, 0); ! 139: for (;;) { ! 140: switch (fscanf(sync_fp, "%d%d%d", &type, &shipnum, &isstr)) { ! 141: case 3: ! 142: break; ! 143: case EOF: ! 144: goto out; ! 145: default: ! 146: goto bad; ! 147: } ! 148: if (shipnum < 0 || shipnum >= cc->vessels) ! 149: goto bad; ! 150: if (isstr != 0 && isstr != 1) ! 151: goto bad; ! 152: if (isstr) { ! 153: register char *p; ! 154: for (p = buf;;) { ! 155: switch (*p++ = getc(sync_fp)) { ! 156: case '\n': ! 157: p--; ! 158: case EOF: ! 159: break; ! 160: default: ! 161: if (p >= buf + sizeof buf) ! 162: p--; ! 163: continue; ! 164: } ! 165: break; ! 166: } ! 167: *p = 0; ! 168: for (p = buf; *p == ' '; p++) ! 169: ; ! 170: a = (int)p; ! 171: b = c = d = 0; ! 172: } else ! 173: if (fscanf(sync_fp, "%d%d%d%d", &a, &b, &c, &d) != 4) ! 174: goto bad; ! 175: if (sync_update(type, SHIP(shipnum), a, b, c, d) < 0) ! 176: goto bad; ! 177: } ! 178: bad: ! 179: erred++; ! 180: out: ! 181: if (!erred && sync_bp != sync_buf) { ! 182: (void) fseek(sync_fp, 0L, 2); ! 183: (void) fwrite(sync_buf, sizeof *sync_buf, sync_bp - sync_buf, ! 184: sync_fp); ! 185: (void) fflush(sync_fp); ! 186: sync_bp = sync_buf; ! 187: } ! 188: sync_seek = ftell(sync_fp); ! 189: #ifdef LOCK_EX ! 190: (void) flock(fileno(sync_fp), LOCK_UN); ! 191: #else ! 192: (void) unlink(sync_lock); ! 193: #endif ! 194: (void) signal(SIGHUP, sighup); ! 195: (void) signal(SIGINT, sigint); ! 196: return erred ? -1 : 0; ! 197: } ! 198: ! 199: sync_update(type, ship, a, b, c, d) ! 200: int type; ! 201: register struct ship *ship; ! 202: int a, b, c, d; ! 203: { ! 204: switch (type) { ! 205: case W_DBP: { ! 206: register struct BP *p = &ship->file->DBP[a]; ! 207: p->turnsent = b; ! 208: p->toship = SHIP(c); ! 209: p->mensent = d; ! 210: break; ! 211: } ! 212: case W_OBP: { ! 213: register struct BP *p = &ship->file->OBP[a]; ! 214: p->turnsent = b; ! 215: p->toship = SHIP(c); ! 216: p->mensent = d; ! 217: break; ! 218: } ! 219: case W_FOUL: { ! 220: register struct snag *p = &ship->file->foul[a]; ! 221: if (SHIP(a)->file->dir == 0) ! 222: break; ! 223: if (p->sn_count++ == 0) ! 224: p->sn_turn = turn; ! 225: ship->file->nfoul++; ! 226: break; ! 227: } ! 228: case W_GRAP: { ! 229: register struct snag *p = &ship->file->grap[a]; ! 230: if (SHIP(a)->file->dir == 0) ! 231: break; ! 232: if (p->sn_count++ == 0) ! 233: p->sn_turn = turn; ! 234: ship->file->ngrap++; ! 235: break; ! 236: } ! 237: case W_UNFOUL: { ! 238: register struct snag *p = &ship->file->foul[a]; ! 239: if (p->sn_count > 0) ! 240: if (b) { ! 241: ship->file->nfoul -= p->sn_count; ! 242: p->sn_count = 0; ! 243: } else { ! 244: ship->file->nfoul--; ! 245: p->sn_count--; ! 246: } ! 247: break; ! 248: } ! 249: case W_UNGRAP: { ! 250: register struct snag *p = &ship->file->grap[a]; ! 251: if (p->sn_count > 0) ! 252: if (b) { ! 253: ship->file->ngrap -= p->sn_count; ! 254: p->sn_count = 0; ! 255: } else { ! 256: ship->file->ngrap--; ! 257: p->sn_count--; ! 258: } ! 259: break; ! 260: } ! 261: case W_SIGNAL: ! 262: if (mode == MODE_PLAYER) ! 263: if (nobells) ! 264: Signal("%s (%c%c): %s", ship, a); ! 265: else ! 266: Signal("\7%s (%c%c): %s", ship, a); ! 267: break; ! 268: case W_CREW: { ! 269: register struct shipspecs *s = ship->specs; ! 270: s->crew1 = a; ! 271: s->crew2 = b; ! 272: s->crew3 = c; ! 273: break; ! 274: } ! 275: case W_CAPTAIN: ! 276: (void) strncpy(ship->file->captain, (char *)a, ! 277: sizeof ship->file->captain - 1); ! 278: ship->file->captain[sizeof ship->file->captain - 1] = 0; ! 279: break; ! 280: case W_CAPTURED: ! 281: if (a < 0) ! 282: ship->file->captured = 0; ! 283: else ! 284: ship->file->captured = SHIP(a); ! 285: break; ! 286: case W_CLASS: ! 287: ship->specs->class = a; ! 288: break; ! 289: case W_DRIFT: ! 290: ship->file->drift = a; ! 291: break; ! 292: case W_EXPLODE: ! 293: if ((ship->file->explode = a) == 2) ! 294: ship->file->dir = 0; ! 295: break; ! 296: case W_FS: ! 297: ship->file->FS = a; ! 298: break; ! 299: case W_GUNL: { ! 300: register struct shipspecs *s = ship->specs; ! 301: s->gunL = a; ! 302: s->carL = b; ! 303: break; ! 304: } ! 305: case W_GUNR: { ! 306: register struct shipspecs *s = ship->specs; ! 307: s->gunR = a; ! 308: s->carR = b; ! 309: break; ! 310: } ! 311: case W_HULL: ! 312: ship->specs->hull = a; ! 313: break; ! 314: case W_MOVE: ! 315: (void) strncpy(ship->file->movebuf, (char *)a, ! 316: sizeof ship->file->movebuf - 1); ! 317: ship->file->movebuf[sizeof ship->file->movebuf - 1] = 0; ! 318: break; ! 319: case W_PCREW: ! 320: ship->file->pcrew = a; ! 321: break; ! 322: case W_POINTS: ! 323: ship->file->points = a; ! 324: break; ! 325: case W_QUAL: ! 326: ship->specs->qual = a; ! 327: break; ! 328: case W_RIGG: { ! 329: register struct shipspecs *s = ship->specs; ! 330: s->rig1 = a; ! 331: s->rig2 = b; ! 332: s->rig3 = c; ! 333: s->rig4 = d; ! 334: break; ! 335: } ! 336: case W_RIG1: ! 337: ship->specs->rig1 = a; ! 338: break; ! 339: case W_RIG2: ! 340: ship->specs->rig2 = a; ! 341: break; ! 342: case W_RIG3: ! 343: ship->specs->rig3 = a; ! 344: break; ! 345: case W_RIG4: ! 346: ship->specs->rig4 = a; ! 347: break; ! 348: case W_COL: ! 349: ship->file->col = a; ! 350: break; ! 351: case W_DIR: ! 352: ship->file->dir = a; ! 353: break; ! 354: case W_ROW: ! 355: ship->file->row = a; ! 356: break; ! 357: case W_SINK: ! 358: if ((ship->file->sink = a) == 2) ! 359: ship->file->dir = 0; ! 360: break; ! 361: case W_STRUCK: ! 362: ship->file->struck = a; ! 363: break; ! 364: case W_TA: ! 365: ship->specs->ta = a; ! 366: break; ! 367: case W_ALIVE: ! 368: alive = 1; ! 369: break; ! 370: case W_TURN: ! 371: turn = a; ! 372: break; ! 373: case W_WIND: ! 374: winddir = a; ! 375: windspeed = b; ! 376: break; ! 377: case W_BEGIN: ! 378: (void) strcpy(ship->file->captain, "begin"); ! 379: people++; ! 380: break; ! 381: case W_END: ! 382: *ship->file->captain = 0; ! 383: ship->file->points = 0; ! 384: people--; ! 385: break; ! 386: case W_DDEAD: ! 387: hasdriver = 0; ! 388: break; ! 389: default: ! 390: fprintf(stderr, "sync_update: unknown type %d\r\n", type); ! 391: return -1; ! 392: } ! 393: return 0; ! 394: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.