1: /* $Header: util.c,v 7.0.1.2 86/10/20 12:07:46 lwall Exp $ */ 2: 3: /* $Log: util.c,v $ 4: * Revision 7.0.1.2 86/10/20 12:07:46 lwall 5: * Made all exits reset tty. 6: * 7: * Revision 7.0.1.1 86/10/16 10:54:02 lwall 8: * Added Damage. Fixed random bugs. 9: * 10: * Revision 7.0 86/10/08 15:14:31 lwall 11: * Split into separate files. Added amoebas and pirates. 12: * 13: */ 14: 15: #include "EXTERN.h" 16: #include "warp.h" 17: #include "ndir.h" 18: #include "object.h" 19: #include "sig.h" 20: #include "term.h" 21: #include "INTERN.h" 22: #include "util.h" 23: 24: void 25: util_init() 26: { 27: ; 28: } 29: 30: void 31: movc3(len,src,dest) 32: #ifdef vax 33: char *dest, *src; 34: int len; 35: { 36: asm("movc3 4(ap),*8(ap),*12(ap)"); 37: } 38: #else 39: Reg1 char *dest; 40: Reg2 char *src; 41: Reg3 int len; 42: { 43: if (dest <= src) { 44: for (; len; len--) { 45: *dest++ = *src++; 46: } 47: } 48: else { 49: dest += len; 50: src += len; 51: for (; len; len--) { 52: *--dest = *--src; 53: } 54: } 55: } 56: #endif 57: 58: void 59: no_can_do(what) 60: char *what; 61: { 62: fprintf(stderr,"Sorry, your terminal is too %s to play warp.\r\n",what); 63: finalize(1); 64: } 65: 66: int 67: exdis(maxnum) 68: int maxnum; 69: { 70: double temp, temp2; 71: double exp(); 72: double log(); 73: 74: temp = (double) maxnum; 75: #ifndef lint 76: temp2 = (double) myrand(); 77: #else 78: temp2 = 0.0; 79: #endif 80: #if RANDBITS == 15 81: return (int) exp(temp2 * log(temp)/0x7fff); 82: #else 83: #if RANDBITS == 16 84: return (int) exp(temp2 * log(temp)/0xffff); 85: #else 86: return (int) exp(temp2 * log(temp)/0x7fffffff); 87: #endif 88: #endif 89: } 90: 91: static char nomem[] = "warp: out of memory!\r\n"; 92: 93: /* paranoid version of malloc */ 94: 95: char * 96: safemalloc(size) 97: MEM_SIZE size; 98: { 99: char *ptr; 100: char *malloc(); 101: 102: ptr = malloc(size?size:1); /* malloc(0) is NASTY on our system */ 103: if (ptr != Nullch) 104: return ptr; 105: else { 106: fputs(nomem,stdout); 107: sig_catcher(0); 108: } 109: /*NOTREACHED*/ 110: } 111: 112: /* safe version of string copy */ 113: 114: char * 115: safecpy(to,from,len) 116: char *to; 117: Reg2 char *from; 118: Reg1 int len; 119: { 120: Reg3 char *dest = to; 121: 122: if (from != Nullch) 123: for (len--; len && (*dest++ = *from++); len--) ; 124: *dest = '\0'; 125: return to; 126: } 127: 128: /* copy a string up to some (non-backslashed) delimiter, if any */ 129: 130: char * 131: cpytill(to,from,delim) 132: Reg2 char *to; 133: Reg1 char *from; 134: Reg3 int delim; 135: { 136: for (; *from; from++,to++) { 137: if (*from == '\\' && from[1] == delim) 138: from++; 139: else if (*from == delim) 140: break; 141: *to = *from; 142: } 143: *to = '\0'; 144: return from; 145: } 146: 147: /* return ptr to little string in big string, NULL if not found */ 148: 149: char * 150: instr(big, little) 151: char *big, *little; 152: 153: { 154: Reg3 char *t; 155: Reg1 char *s; 156: Reg2 char *x; 157: 158: for (t = big; *t; t++) { 159: for (x=t,s=little; *s; x++,s++) { 160: if (!*x) 161: return Nullch; 162: if (*s != *x) 163: break; 164: } 165: if (!*s) 166: return t; 167: } 168: return Nullch; 169: } 170: 171: /* effective access */ 172: 173: #ifdef SETUIDGID 174: int 175: eaccess(filename, mod) 176: char *filename; 177: int mod; 178: { 179: int protection, euid; 180: 181: mod &= 7; /* remove extraneous garbage */ 182: if (stat(filename, &filestat) < 0) 183: return -1; 184: euid = geteuid(); 185: if (euid == ROOTID) 186: return 0; 187: protection = 7 & (filestat.st_mode >> 188: (filestat.st_uid == euid ? 6 : 189: (filestat.st_gid == getegid() ? 3 : 0) 190: )); 191: if ((mod & protection) == mod) 192: return 0; 193: errno = EACCES; 194: return -1; 195: } 196: #endif 197: 198: /* 199: * Get working directory 200: */ 201: 202: #ifdef GETWD 203: #define dot "." 204: #define dotdot ".." 205: 206: static char *name; 207: 208: static DIR *dirp; 209: static int off; 210: static struct stat d, dd; 211: static struct direct *dir; 212: 213: char * 214: getwd(np) 215: char *np; 216: { 217: long rdev, rino; 218: 219: *np++ = '/'; 220: *np = 0; 221: name = np; 222: off = -1; 223: stat("/", &d); 224: rdev = d.st_dev; 225: rino = d.st_ino; 226: for (;;) { 227: stat(dot, &d); 228: if (d.st_ino==rino && d.st_dev==rdev) 229: goto done; 230: if ((dirp = opendir(dotdot)) == Null(DIR *)) 231: prexit("getwd: cannot open ..\r\n"); 232: stat(dotdot, &dd); 233: chdir(dotdot); 234: if(d.st_dev == dd.st_dev) { 235: if(d.st_ino == dd.st_ino) 236: goto done; 237: do 238: if ((dir = readdir(dirp)) == Null(struct direct *)) 239: prexit("getwd: read error in ..\r\n"); 240: while (dir->d_ino != d.st_ino); 241: } 242: else do { 243: if ((dir = readdir(dirp)) == Null(struct direct *)) 244: prexit("getwd: read error in ..\r\n"); 245: stat(dir->d_name, &dd); 246: } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 247: cat(); 248: closedir(dirp); 249: } 250: done: 251: name--; 252: if (chdir(name) < 0) { 253: printf("getwd: can't cd back to %s\r\n",name); 254: sig_catcher(0); 255: } 256: return (name); 257: } 258: 259: void 260: cat() 261: { 262: Reg1 int i; 263: Reg2 int j; 264: 265: i = -1; 266: while (dir->d_name[++i] != 0); 267: if ((off+i+2) > 1024-1) 268: return; 269: for(j=off+1; j>=0; --j) 270: name[j+i+1] = name[j]; 271: if (off >= 0) 272: name[i] = '/'; 273: off=i+off+1; 274: name[off] = 0; 275: for(--i; i>=0; --i) 276: name[i] = dir->d_name[i]; 277: } 278: 279: void 280: prexit(cp) 281: char *cp; 282: { 283: write(2, cp, strlen(cp)); 284: sig_catcher(0); 285: } 286: #else 287: char * 288: getwd(np) /* shorter but slower */ 289: char *np; 290: { 291: FILE *popen(); 292: FILE *pipefp = popen("/bin/pwd","r"); 293: 294: if (pipefp == Nullfp) { 295: printf("Can't run /bin/pwd\r\n"); 296: finalize(1); 297: } 298: Fgets(np,512,pipefp); 299: np[strlen(np)-1] = '\0'; /* wipe out newline */ 300: pclose(pipefp); 301: return np; 302: } 303: #endif 304: 305: /* copy a string to a safe spot */ 306: 307: char * 308: savestr(str) 309: char *str; 310: { 311: Reg1 char *newaddr = safemalloc((MEM_SIZE)(strlen(str)+1)); 312: 313: strcpy(newaddr,str); 314: return newaddr; 315: } 316: 317: char * 318: getval(nam,def) 319: char *nam,*def; 320: { 321: char *val; 322: 323: if ((val = getenv(nam)) == Nullch || !*val) 324: val = def; 325: return val; 326: }