|
|
1.1 ! root 1: /* ! 2: * build.c ! 3: * 07/01/93 COH 386 release ! 4: * ! 5: * Build (install) COHERENT on a system, part 1. ! 6: * The second part of the install procedure is in install.c. ! 7: * Uses common routines in build0.c, ! 8: * serial number checking in numtab.c and serialno.c. ! 9: * Requires floating point output: cc build.c build0.c numtab.c serialno.c -f ! 10: * Usage: build [ -dv ] ! 11: * Options: ! 12: * -d Debug, echo commands without executing ! 13: * -u Update, rather than full installation ! 14: * -v Verbose ! 15: * ! 16: * In addition to the files necessary to run the single user system ! 17: * (/coherent, /etc/init, /bin/sh, /dev/console, /dev/null, etc.), ! 18: * the build disk from which this program runs must contain: ! 19: * In /bin: chgrp, chown, cpdir, date, echo, ln, mkdir, mv, rm, touch ! 20: * In /conf: boot, mboot, patch, upd_suppress, upd_save ! 21: * In /dev: at[01][abcdx], rat[01][abcd] ! 22: * In /etc: ATclock, badscan, fdisk, mkdev, mkfs, mount, umount ! 23: * It must also contain directories /mnt and /tmp. ! 24: * This program runs from a write-protected floppy-disk-based COHERENT ! 25: * boot disk, so it writes only to directory /tmp (mounted on a RAM disk). ! 26: */ ! 27: ! 28: #include <stdio.h> ! 29: #include <canon.h> ! 30: #include <string.h> ! 31: #include <time.h> ! 32: #include <unistd.h> ! 33: #include <sys/devices.h> ! 34: #include <sys/fdisk.h> ! 35: #include <sys/filsys.h> ! 36: #include <sys/stat.h> ! 37: #include <sys/types.h> ! 38: #include "build0.h" ! 39: #include "serialno.h" ! 40: ! 41: /* File names. */ ! 42: #define DEVICE_FILE "/tmp/devices" ! 43: ! 44: /* Manifest constants. */ ! 45: #define VERSION "5.0" ! 46: #define USAGE "Usage: /etc/build [ -dv ]\n" ! 47: #define ATDEVS (NPARTN+NPARTN) /* number of AT disk devices */ ! 48: #define BSIZE 512 /* sector size */ ! 49: ! 50: #define BAR_BAR "_bar" /* 1st copy of serial # */ ! 51: #define BAR_ENTRY "_entry" /* 2nd copy of serial # */ ! 52: #define MAXSIZE 500 /* suggested max size (MB) */ ! 53: #define MINSIZE 10 /* required root size (MB) */ ! 54: #define NEEDSIZE 10 /* suggested min root size (MB) */ ! 55: #define PIPEDEV "pipedev" /* kernel pipe F.S. device */ ! 56: #define ROOTDEV "rootdev" /* kernel root F.S. device */ ! 57: ! 58: #define NAMESIZE 6 /* max device name buffer size */ ! 59: #define NDEVICES 24 /* number of disk devices */ ! 60: ! 61: /* (unsigned long) sectors to (double) megabytes. */ ! 62: #define meg(sec) ((double)sec * BSIZE / 1000000.) ! 63: ! 64: /* Device table structure. */ ! 65: typedef struct device { ! 66: char d_xname[NAMESIZE]; /* partition table name */ ! 67: char d_dname[NAMESIZE]; /* device name */ ! 68: int d_major; /* major number */ ! 69: int d_minor; /* minor number */ ! 70: int d_flags; /* flags */ ! 71: unsigned long d_size; /* size in blocks */ ! 72: } DEVICE; ! 73: ! 74: /* Flag bits. */ ! 75: #define F_COH 0x01 /* COHERENT partition */ ! 76: #define F_BOOT 0x02 /* Active */ ! 77: #define F_ROOT 0x04 /* Root */ ! 78: #define F_FS 0x08 /* File system exists */ ! 79: #define F_MOUNT 0x10 /* Mounted by /etc/rc */ ! 80: #define F_PROTO 0x20 /* Proto created */ ! 81: #define F_SCAN 0x40 /* Badscanned */ ! 82: #define F_ATDEV 0x80 /* AT device */ ! 83: #define isflag(i, f) ((devices[i].d_flags & (f)) != 0) ! 84: #define notflag(i, f) ((devices[i].d_flags & (f)) == 0) ! 85: #define clrflag(i, f) devices[i].d_flags &= ~(f) ! 86: #define setflag(i, f) devices[i].d_flags |= (f) ! 87: ! 88: /* ! 89: * Device table. ! 90: * add_devices() adds entries for devices created by /etc/mkdev. ! 91: * fdisk() zaps the entries for which the xdevice open fails. ! 92: */ ! 93: DEVICE devices[NDEVICES] = { ! 94: { "at0x", "at0a", AT_MAJOR, 0, F_ATDEV, 0L }, ! 95: { "at0x", "at0b", AT_MAJOR, 1, F_ATDEV, 0L }, ! 96: { "at0x", "at0c", AT_MAJOR, 2, F_ATDEV, 0L }, ! 97: { "at0x", "at0d", AT_MAJOR, 3, F_ATDEV, 0L }, ! 98: { "at1x", "at1a", AT_MAJOR, 4, F_ATDEV, 0L }, ! 99: { "at1x", "at1b", AT_MAJOR, 5, F_ATDEV, 0L }, ! 100: { "at1x", "at1c", AT_MAJOR, 6, F_ATDEV, 0L }, ! 101: { "at1x", "at1d", AT_MAJOR, 7, F_ATDEV, 0L } ! 102: }; ! 103: ! 104: /* Externals. */ ! 105: extern long atol(); ! 106: extern char *fgets(); ! 107: extern long lseek(); ! 108: extern time_t time(); ! 109: ! 110: /* Forward. */ ! 111: void add_devices(); ! 112: void badscan(); ! 113: void copy(); ! 114: char *devname(); ! 115: void done(); ! 116: int exists_and_nz(); ! 117: void fdisk(); ! 118: void get_timezone(); ! 119: int is_fs(); ! 120: void mkdev(); ! 121: void mkfs(); ! 122: void new_boot(); ! 123: void patches(); ! 124: char *protoname(); ! 125: char *rawname(); ! 126: void rootpatch(); ! 127: void save_files(); ! 128: void set_date(); ! 129: void uucp(); ! 130: void user_devices(); ! 131: void welcome(); ! 132: char *xname(); ! 133: ! 134: /* Globals. */ ! 135: int active = -1; /* active partition */ ! 136: char *activeos; /* active partition OS */ ! 137: char buf2[NBUF]; /* extra buffer */ ! 138: HDISK_S hd; /* hard disk boot block */ ! 139: int mboot; /* mboot replaced */ ! 140: int ncohdev; /* number of COHERENT devices */ ! 141: int ndevices = ATDEVS; /* number of devices */ ! 142: int protoflag; /* prototypes created */ ! 143: int root; /* root partition */ ! 144: char tzone[NBUF]; /* timezone */ ! 145: char tzone5[NBUF]; /* timezone for Sys V */ ! 146: int update; /* update, rather than install */ ! 147: ! 148: main(argc, argv) int argc; char *argv[]; ! 149: { ! 150: register char *s; ! 151: ! 152: argv0 = argv[0]; ! 153: abortmsg = 1; ! 154: usagemsg = USAGE; ! 155: if (argc > 1 && argv[1][0] == '-') { ! 156: for (s = &argv[1][1]; *s; ++s) { ! 157: switch(*s) { ! 158: case 'd': ++dflag; break; ! 159: case 'u': ++update; break; ! 160: case 'v': ++vflag; break; ! 161: case 'V': ! 162: fprintf(stderr, "%s: V%s\n", argv0, VERSION); ! 163: break; ! 164: default: usage(); break; ! 165: } ! 166: } ! 167: --argc; ! 168: ++argv; ! 169: } ! 170: if (argc != 1) ! 171: usage(); ! 172: ! 173: welcome(); ! 174: set_date(); ! 175: mkdev(); ! 176: ! 177: fdisk(); ! 178: if (update) { ! 179: new_boot(); /* write out new boot block for tboot */ ! 180: save_files(); ! 181: } else { ! 182: badscan(); ! 183: mkfs(); ! 184: } ! 185: copy(); ! 186: ! 187: if (!update) ! 188: user_devices(); ! 189: uucp(); ! 190: rootpatch(); ! 191: patches(); ! 192: sys("/bin/echo /etc/build: success >>/mnt/etc/install.log", S_NONFATAL); ! 193: sprintf(cmd, "TIMEZONE=\"%s\" /bin/date >>/mnt/etc/install.log", tzone); ! 194: sys(cmd, S_NONFATAL); ! 195: sys("/bin/echo >>/mnt/etc/install.log", S_NONFATAL); ! 196: done(); ! 197: sync(); ! 198: sys("/etc/reboot -p", S_IGNORE); ! 199: ! 200: /* NOTREACHED */ ! 201: exit(0); ! 202: } ! 203: ! 204: /* ! 205: * Append devices as specified by /etc/mkdev to devices table. ! 206: */ ! 207: void ! 208: add_devices() ! 209: { ! 210: register FILE *fp; ! 211: register int i, n; ! 212: ! 213: if ((fp = fopen(DEVICE_FILE, "r")) == NULL) ! 214: return; ! 215: for (i = ndevices; i < NDEVICES; i++) { ! 216: n = fscanf(fp, "%s %s %d %d\n", ! 217: devices[i].d_xname, devices[i].d_dname, ! 218: &devices[i].d_major, &devices[i].d_minor); ! 219: if (n == 0 || n == EOF) ! 220: break; ! 221: else if (n != 4) ! 222: fatal("scanf failed on %s, n=%d", DEVICE_FILE, n); ! 223: ++ndevices; ! 224: } ! 225: if (i == NDEVICES) ! 226: nonfatal("too many devices, excess ignored"); ! 227: fclose(fp); ! 228: } ! 229: ! 230: /* ! 231: * Scan each COHERENT device for bad blocks. ! 232: */ ! 233: void ! 234: badscan() ! 235: { ! 236: register int i; ! 237: register char *name; ! 238: ! 239: cls(1); ! 240: printf( ! 241: "The next step in installation is to scan each COHERENT partition\n" ! 242: "for bad blocks. This will not write to the partition being scanned.\n" ! 243: "Be patient. This takes a few minutes.\n" ! 244: ); ! 245: for (i = 0; i < ndevices; i++) { ! 246: if (notflag(i, F_COH) || notflag(i, F_ATDEV)) ! 247: continue; /* scan only AT device COH partitions */ ! 248: printf("\n"); ! 249: name = devname(i, 0); ! 250: if (isflag(i, F_FS)) { ! 251: printf( ! 252: "Partition %d (%s) already contains a COHERENT filesystem.\n" ! 253: "If you wish to continue to use the existing filesystem, you can skip\n" ! 254: "scanning it for bad blocks. If you want to replace it with an empty\n" ! 255: "filesystem, you must scan it for bad blocks first.\n", ! 256: i, name); ! 257: if (yes_no("Do you want to scan %s for bad blocks", ! 258: name) == 0) ! 259: continue; ! 260: } ! 261: printf("Scanning partition %d:\n", i); ! 262: setflag(i, F_SCAN); ! 263: sprintf(cmd, "/etc/badscan -v -o %s %s %s", ! 264: protoname(i), rawname(i, 1), xname(i, 1)); ! 265: if (sys(cmd, S_NONFATAL) == 0) { ! 266: setflag(i, F_PROTO); ! 267: ++protoflag; ! 268: } ! 269: } ! 270: } ! 271: ! 272: /* ! 273: * Mount the root filesystem, copy files to it, patch /coherent. ! 274: * Kludge around as required. ! 275: */ ! 276: void ! 277: copy() ! 278: { ! 279: cls(0); ! 280: printf( ! 281: "The next step is to copy some COHERENT files from the diskette to the\n" ! 282: "root filesystem of your hard disk. This will take a few minutes...\n" ! 283: ); ! 284: ! 285: /* Mount the filesystem. */ ! 286: sprintf(cmd, "/etc/mount %s /mnt", devname(root, 1)); ! 287: ! 288: sys(cmd, S_FATAL); ! 289: ! 290: if(update){ ! 291: printf( ! 292: "The existing /coherent kernel on the root file system will now be renamed to\n" ! 293: "coh.B4.420. After this the remainder of diskette #1 will be copied.\n\n" ! 294: ); ! 295: ! 296: /* move the existing kernel names /coherent to coh.B4.420 */ ! 297: sprintf(cmd,"/bin/cp /mnt/coherent /mnt/coh.B4.420 2>/dev/null"); ! 298: sys(cmd,S_NONFATAL); ! 299: } ! 300: ! 301: /* Copy the boot floppy. */ ! 302: sprintf(cmd, "/bin/cpdir -ad%s -smnt -sbegin -stmp %s / /mnt", ! 303: (vflag) ? "v" : "", (update) ? "`cat /conf/upd_suppress`" : ""); ! 304: sys(cmd, S_FATAL); ! 305: ! 306: /* Copy idtune and idenable data files. */ ! 307: sprintf(cmd, "/bin/cp %s %s /mnt/conf", IDCMDFILE, IDVARFILE); ! 308: sys(cmd, S_FATAL); ! 309: ! 310: /* Copy patch file for debugging. */ ! 311: sprintf(cmd, "/bin/cp %s /mnt/conf", PATCHFILE); ! 312: sys(cmd, S_FATAL); ! 313: ! 314: if (!is_dir("/mnt/mnt")) ! 315: sys("/bin/mkdir /mnt/mnt", S_FATAL); ! 316: sys("/bin/chmog 0755 bin bin /mnt/mnt", S_NONFATAL); ! 317: ! 318: /* Write entry to /etc/install.log. */ ! 319: sprintf(cmd, "/bin/echo /etc/build: %s %s >>/mnt/etc/install.log", ! 320: "386", ! 321: (update) ? "update" : "install"); ! 322: sys(cmd, S_NONFATAL); ! 323: sprintf(cmd, "TIMEZONE=\"%s\" /bin/date >>/mnt/etc/install.log", tzone); ! 324: sys(cmd, S_NONFATAL); ! 325: ! 326: /* If /etc/mkdev created devices in /tmp/dev, copy them to /dev. */ ! 327: /* Remove the copies in /tmp/dev on the hard disk. */ ! 328: if (exists("/tmp/dev")) ! 329: sys("/bin/cpdir -d /tmp/dev /mnt/dev", S_FATAL); ! 330: if (exists("/tmp/drvld.all")) { ! 331: sys("/bin/cp /tmp/drvld.all /mnt/etc/drvld.all", S_NONFATAL); ! 332: sys("/bin/chmog 0744 root root /mnt/etc/drvld.all", S_NONFATAL); ! 333: } ! 334: ! 335: sys("/bin/cat /tmp/ttys >>/mnt/etc/ttys", S_NONFATAL); ! 336: sys("/bin/cp /tmp/id-cmd /mnt/etc/conf/bin/id-cmd", S_NONFATAL); ! 337: sys("/bin/chmog 544 root root /mnt/etc/conf/bin/id-cmd", S_NONFATAL); ! 338: ! 339: /* Grow /lost+found to make room for files. */ ! 340: sys("cd /mnt/lost+found \n" ! 341: "/bin/touch `/bin/from 1 to 200` \n" ! 342: "/bin/rm *", S_IGNORE); ! 343: ! 344: /* Create /autoboot. */ ! 345: sys("/bin/ln -f /mnt/coherent /mnt/autoboot", S_FATAL); ! 346: ! 347: /* Replace the build version of /etc/brc with the install version. */ ! 348: sys("/bin/rm /mnt/etc/brc", S_NONFATAL); ! 349: if (update) ! 350: sys("/bin/ln -f /mnt/etc/brc.update /mnt/etc/brc", S_FATAL); ! 351: else ! 352: sys("/bin/ln -f /mnt/etc/brc.install /mnt/etc/brc", S_FATAL); ! 353: ! 354: /* Link root device to /dev/root. */ ! 355: sprintf(cmd, "/bin/ln -f /mnt%s /mnt/dev/root", devname(root, 0)); ! 356: sys(cmd, S_FATAL); ! 357: ! 358: /* Write the timezone to /etc/timezone. */ ! 359: sprintf(cmd, "/bin/echo export TIMEZONE=\\\"%s\\\" >/mnt/etc/timezone", tzone); ! 360: sys(cmd, S_NONFATAL); ! 361: sprintf(cmd, "/bin/echo export TZ=\\\"%s\\\" >>/mnt/etc/timezone", tzone5); ! 362: sys(cmd, S_NONFATAL); ! 363: ! 364: if (!update) { ! 365: /* Write the serial number to /etc/serialno. */ ! 366: sprintf(cmd, "/bin/echo %s >/mnt/etc/serialno", serialno); ! 367: sys(cmd, S_NONFATAL); ! 368: } ! 369: ! 370: /* Save the prototypes from /tmp to /conf. */ ! 371: if (protoflag) ! 372: sys("/bin/mv /tmp/*.proto /mnt/conf", S_NONFATAL); ! 373: } ! 374: ! 375: /* ! 376: * Generate a device name from a DEVICE entry name. ! 377: * Return a pointer to the statically allocated name. ! 378: * If flag and not one of the built-in AT device names, ! 379: * the device is in /tmp/dev rather than /dev. ! 380: * Sleazy hack: this always writes "/tmp/dev/..." in the buffer and ! 381: * massages the return value accordingly so that subsequent calls ! 382: * with same i but different flag will not clobber previous return values. ! 383: */ ! 384: char * ! 385: devname(i, flag) int i, flag; ! 386: { ! 387: static char name[4+4+1+NAMESIZE]; /* e.g. "/tmp/dev/at0a" */ ! 388: ! 389: sprintf(name, "/tmp/dev/%s", devices[i].d_dname); ! 390: return (flag && notflag(i, F_ATDEV)) ? name : name+4; ! 391: } ! 392: ! 393: /* ! 394: * Done. ! 395: * Print useful information. ! 396: */ ! 397: void ! 398: done() ! 399: { ! 400: cls(1); ! 401: printf( ! 402: "You have installed the COHERENT operating system onto your hard disk.\n" ! 403: "To install files from the remaining diskettes in the installation kit,\n" ! 404: "you must boot the COHERENT system from the hard disk. It will prompt\n" ! 405: "you to install the remaining diskettes in the installation kit.\n" ! 406: "\n" ! 407: "After you finish reading this information, remove the floppy disk,\n" ! 408: "hit <Enter> and your system will automatically reboot.\n" ! 409: "\n" ! 410: ); ! 411: if (mboot) { ! 412: printf( ! 413: "If you type a partition number (0 to 7) while\n" ! 414: "the boot procedure is trying to read the floppy disk,\n" ! 415: "your system will boot the operating system on that partition.\n" ! 416: ); ! 417: if (active != -1) { ! 418: printf("If you type nothing, your system will boot "); ! 419: if (active == root) ! 420: printf("COHERENT (partition %d).\n", active); ! 421: else { ! 422: printf("active partition %d", active); ! 423: if (activeos != NULL) ! 424: printf(" (%s)", activeos); ! 425: printf(".\n", active); ! 426: } ! 427: } ! 428: } else { ! 429: printf( ! 430: "You must boot the new COHERENT root filesystem on partition %d.\n", ! 431: root); ! 432: } ! 433: ! 434: printf( ! 435: "\nNow remove the floppy disk so your system does not boot from the floppy.\n"); ! 436: ! 437: if (mboot && root != active) ! 438: printf( ! 439: "You MUST type %d when the system tries to read the floppy disk during the boot\n" ! 440: "procedure to boot the partition containing the new COHERENT root filesystem.\n", ! 441: root); ! 442: } ! 443: ! 444: /* ! 445: * See if the specified file exists and has non-zero length. ! 446: */ ! 447: exists_and_nz(fn) ! 448: char *fn; ! 449: { ! 450: struct stat s; ! 451: ! 452: if (stat(fn, &s) == -1) ! 453: return 0; /* does not exist */ ! 454: return (s.st_size > 0); /* exists and length > 0 */ ! 455: } ! 456: ! 457: /* ! 458: * Get partition table information. ! 459: */ ! 460: void ! 461: fdisk() ! 462: { ! 463: register int fd, i, j, n, part, cohpart, flag; ! 464: char *fname, *s; ! 465: ! 466: cls(1); ! 467: if (update) { ! 468: printf("Reading existing partition tables...\n"); ! 469: } else { ! 470: printf( ! 471: "This installation procedure allows you to create one or more partitions\n" ! 472: "on your hard disk to contain the COHERENT system and its files.\n" ! 473: "Each disk drive may contain no more than four logical partitions.\n" ! 474: "If all four partitions on your disk are already in use, you will\n" ! 475: "have to overwrite at least one of them to install COHERENT.\n" ! 476: "If your disk uses fewer than four partitions and has enough unused space\n" ! 477: "for COHERENT (%d megabytes), you can install COHERENT into the unused space.\n" ! 478: "If you intend to install MS-DOS after installing COHERENT,\n" ! 479: "you must leave the first physical partition free for MS-DOS.\n" ! 480: "\n" ! 481: "The next part of the installation procedure will let you change the\n" ! 482: "partitions on your hard disk. Data on unchanged hard disk partitions\n" ! 483: "will not be changed. However, data already on your hard disk may be\n" ! 484: "destroyed if you change the base or the size of a logical partition,\n" ! 485: "or if you change the order of the partition table entries.\n" ! 486: "If you need to back up existing data from the hard disk,\n" ! 487: "type <Ctrl-C> now to interrupt COHERENT installation; then reboot your\n" ! 488: "system and back up your hard disk data onto diskettes.\n" ! 489: "\n", NEEDSIZE); ! 490: cls(1); ! 491: printf( ! 492: "COHERENT initialization normally writes a new master bootstrap program onto\n" ! 493: "your hard disk. The COHERENT master boot allows you to boot the operating\n" ! 494: "system on one selected disk partition (the active partition) automatically;\n" ! 495: "it also allows you to boot the operating system on any disk partition by\n" ! 496: "typing a key when you reboot. Mark Williams strongly recommends that you\n" ! 497: "use the COHERENT master boot. However, the COHERENT master boot may not\n" ! 498: "work with some operating systems (for example, Xenix) if you make the\n" ! 499: "COHERENT partition active; instead, leave the other partition (e.g. Xenix)\n" ! 500: "active and boot COHERENT by typing a key. If you do not use the COHERENT\n" ! 501: "bootstrap, you must understand how to boot the COHERENT partition using your\n" ! 502: "existing bootstrap program.\n" ! 503: "\n" ! 504: ); ! 505: if (yes_no("Do you want to use the COHERENT master boot")) ! 506: ++mboot; ! 507: ! 508: retry: ! 509: /* Construct an /etc/fdisk command with appropriate xdevice names. */ ! 510: strcpy(cmd, "/etc/fdisk -cB"); ! 511: if (mboot) ! 512: strcat(cmd, "b /conf/mboot"); ! 513: for (i = 0; i < ndevices; i++) { ! 514: if (i == 0 ! 515: || strcmp(devices[i-1].d_xname, devices[i].d_xname) != 0) { ! 516: if ((fd = open(xname(i, 1), 0)) < 0) ! 517: continue; ! 518: close(fd); ! 519: strcat(cmd, " "); ! 520: strcat(cmd, xname(i, 1)); ! 521: } ! 522: } ! 523: sys(cmd, S_FATAL); /* do the fdisk command */ ! 524: } /* !update */ ! 525: ! 526: /* Read the partition table and set device flags appropriately. */ ! 527: for (i = part = 0; i < ndevices; ++i) { ! 528: if (i != 0 ! 529: && strcmp(devices[i-1].d_xname, devices[i].d_xname) == 0) ! 530: continue; /* partition already done */ ! 531: fname = xname(i, 1); ! 532: if ((fd = open(fname, 0)) < 0) ! 533: continue; /* cannot open xdevice */ ! 534: if (read(fd, &hd, sizeof hd) != sizeof hd) ! 535: fatal("%s: read failed", fname); ! 536: close(fd); ! 537: if (hd.hd_sig != HDSIG) { ! 538: nonfatal("%s: invalid partition table", fname); ! 539: continue; ! 540: } ! 541: /* The partition table is valid, check its partitions. */ ! 542: for (j = 0; j < NPARTN && i + j < ndevices; j++) { ! 543: n = i + j; /* index in devices[] */ ! 544: if (part != n) { ! 545: /* ! 546: * Copy over unopenable partitions. ! 547: * This allows subsequent code to use ! 548: * the devices[] index as the partition number. ! 549: */ ! 550: devices[part] = devices[n]; ! 551: n = part; ! 552: } ! 553: part++; /* another valid partition */ ! 554: if (hd.hd_partn[j].p_boot != 0) { ! 555: setflag(n, F_BOOT); ! 556: if (active == -1) ! 557: active = n; /* first active partition */ ! 558: switch(hd.hd_partn[j].p_sys) { ! 559: case SYS_COH: ! 560: activeos = "COHERENT"; ! 561: break; ! 562: case SYS_DOS_12: ! 563: case SYS_DOS_16: ! 564: case SYS_DOS_XP: ! 565: case SYS_DOS_LARGE: ! 566: activeos = "MS-DOS"; ! 567: break; ! 568: case SYS_XENIX: ! 569: activeos = "Xenix"; ! 570: break; ! 571: default: ! 572: activeos = NULL; ! 573: break; ! 574: } ! 575: } ! 576: if (hd.hd_partn[j].p_sys != SYS_COH) ! 577: continue; ! 578: ! 579: /* Make sure the device can be accessed. */ ! 580: s = devname(n, 1); ! 581: if (!exists(s)) { ! 582: nonfatal("cannot open COHERENT partition %d (%s)", ! 583: n, devname(n, 0)); ! 584: continue; ! 585: } else if (hd.hd_partn[j].p_size == 0L) { ! 586: nonfatal("COHERENT partition %d (%s) is empty", ! 587: j, devname(n, 0)); ! 588: continue; ! 589: } ! 590: ! 591: /* OK, set flags in the device table. */ ! 592: ++ncohdev; ! 593: setflag(n, F_COH); ! 594: devices[n].d_size = hd.hd_partn[j].p_size; ! 595: if (is_fs(s, devices[n].d_size)) ! 596: setflag(n, F_FS); ! 597: ! 598: /* Make sure the device is not mounted. */ ! 599: sprintf(cmd, "/etc/umount %s 2>/dev/null", s); ! 600: sys(cmd, S_IGNORE); ! 601: } ! 602: } ! 603: ndevices = part; ! 604: if (ndevices == 0) ! 605: fatal("cannot open partition tables"); ! 606: else if (ncohdev == 0) ! 607: fatal("no COHERENT partition found"); ! 608: cls(0); ! 609: printf("Your system includes %d COHERENT partition%s:\n", ! 610: ncohdev, (ncohdev == 1) ? "" : "s"); ! 611: printf("Drive Partition\t Device\tMegabytes\n"); ! 612: for (flag = i = 0; i < ndevices; i++) ! 613: if (isflag(i, F_COH)) { ! 614: cohpart = i; ! 615: printf("%3d\t%3d\t%s\t%.2f\n", ! 616: i/NPARTN, ! 617: i, ! 618: devname(i, 0), ! 619: meg(devices[i].d_size)); ! 620: if (((int)meg(devices[i].d_size)) > MAXSIZE) ! 621: flag = 1; ! 622: } ! 623: if (!update && flag) { ! 624: printf( ! 625: "\n" ! 626: "Your system includes a large COHERENT filesystem (larger than %d megabytes).\n" ! 627: "You should repartition the hard disk to define smaller COHERENT partitions.\n", ! 628: MAXSIZE); ! 629: if (yes_no("Do you want to repartition the hard disk")) ! 630: goto retry; ! 631: printf("\n"); ! 632: } ! 633: ! 634: if (ncohdev == 1) { ! 635: root = cohpart; ! 636: setflag(root, F_ROOT); ! 637: return; ! 638: } ! 639: printf( ! 640: "You must specify one COHERENT partition as the root filesystem.\n" ! 641: ); ! 642: if (!update) ! 643: printf( ! 644: "The root filesystem contains the files normally used by COHERENT.\n" ! 645: "The root filesystem should contain at least %d megabytes.\n", ! 646: NEEDSIZE); ! 647: if (ndevices > ATDEVS) ! 648: printf( ! 649: "The COHERENT root filesystem must be on partition 0 through 7.\n" ! 650: ); ! 651: if (active != -1 && isflag(active, F_COH)) { ! 652: printf("COHERENT partition %d is marked as active in the partition table.\n", ! 653: active); ! 654: if (!update) ! 655: printf( ! 656: "If you choose it as the root, you can boot COHERENT automatically.\n" ! 657: ); ! 658: } ! 659: printf("\n"); ! 660: again: ! 661: if (update) ! 662: s = get_line("Which partition contains the COHERENT root filesystem?"); ! 663: else ! 664: s = get_line("Which partition do you want to be the root filesystem?"); ! 665: root = *s - '0'; ! 666: if (*++s != '\0' || root < 0 || root >= ATDEVS || notflag(root, F_COH)) { ! 667: printf("Enter a number between 0 and 7 which specifies a COHERENT partition.\n"); ! 668: goto again; ! 669: } ! 670: ! 671: if (meg(devices[root].d_size) < (double)NEEDSIZE) { ! 672: if (update) { ! 673: printf( ! 674: "\n" ! 675: "Your current COHERENT 4.0.x root filesystem is too small to contain the\n" ! 676: "COHERENT 4.2.0 update along with the on-line manual pages and the on-line\n" ! 677: "dictionary. If you wish to have the COHERENT 4.2.0 on-line manual pages and\n" ! 678: "the on-line dictionary installed, you will need to do the following:\n\n" ! 679: "\t1) Exit from the update.\n" ! 680: "\t2) Boot from your existing COHERENT root partition.\n" ! 681: "\t3) Perform a full \"backup\" of ALL PARTITIONS on your hard disk\n" ! 682: "\t include all of your existing programs, files, and any system\n" ! 683: "\t files that you have modified using backup utilities \"cpio\",\n" ! 684: "\t \"ustar\", or \"tar\". If your hard disk includes partitions\n" ! 685: "\t assigned to other operating systems, be sure to back these up also!\n" ! 686: "\t4) Perform a full installation of COHERENT 386 using the same disks\n" ! 687: "\t supplied for the update. Note that you will need to increase the\n" ! 688: "\t size of the root partition, or you will need to select a different\n" ! 689: "\t partition to contain the root filesystem. Please refer to the\n" ! 690: "\t chapter on installation found in the COHERENT 386 release notes.\n" ! 691: ); ! 692: sync(); ! 693: if (yes_no("Do you wish to abort the update")) ! 694: fatal("Insufficient disk space for update!"); ! 695: } else { ! 696: printf("Partition %d contains only %.2f megabytes.\n", ! 697: root, meg(devices[root].d_size)); ! 698: if (meg(devices[root].d_size) < (double)MINSIZE) { ! 699: printf("It is too small to contain the COHERENT root filesystem.\n"); ! 700: goto again; ! 701: } ! 702: if (!yes_no("Are you sure you want it to be the root partition")) ! 703: goto again; ! 704: } ! 705: } ! 706: setflag(root, F_ROOT); ! 707: } ! 708: ! 709: /* ! 710: * Set up a nonstandard timezone. ! 711: */ ! 712: void ! 713: get_timezone(dstflag) ! 714: int dstflag; ! 715: { ! 716: register char *s; ! 717: int diff; ! 718: char std_abbr[20], dst_abbr[20]; ! 719: int east_of_gr; ! 720: ! 721: /* tzone5 is like tzone except no colons and number is in hours */ ! 722: ! 723: printf( ! 724: "You need to specify an abbreviation for your timezone,\n" ! 725: "whether you are east or west of Greenwich, England,\n" ! 726: "and the difference in minutes between your timezone\n" ! 727: "and Greenwich Time (called UT or GMT). For example,\n" ! 728: "Germany is 60 minutes of time east of Greenwich.\n" ! 729: ); ! 730: s = get_line("Abbreviation for your timezone:"); ! 731: strcpy(std_abbr, s); ! 732: east_of_gr = yes_no("Is your timezone east of Greenwich"); ! 733: s = get_line("Difference in minutes from GMT:"); ! 734: diff = atoi(s); ! 735: if (east_of_gr) ! 736: diff = -diff; ! 737: if (dstflag) { ! 738: s = get_line("Abbreviation for your daylight savings timezone:"); ! 739: strcpy(dst_abbr, s); ! 740: sprintf(tzone, "%s:%d:%s:1.1.4", std_abbr, diff, dst_abbr); ! 741: sprintf(tzone5, "%s%d%s", std_abbr, diff/60, dst_abbr); ! 742: } else { ! 743: sprintf(tzone, "%s:%d:", std_abbr, diff); ! 744: sprintf(tzone5, "%s%d", std_abbr, diff/60); ! 745: } ! 746: } ! 747: ! 748: /* ! 749: * Check if a special file is a well-formed filesystem. ! 750: * This routine is derived from code in "mount.c". ! 751: * Here the check that "special" is a block special file is eliminated ! 752: * and the size is checked against the partition size. ! 753: */ ! 754: int ! 755: is_fs(special, size) char *special; unsigned long size; ! 756: { ! 757: static struct filsys f; ! 758: register int fd; ! 759: register struct filsys *fp; ! 760: register daddr_t *dp; ! 761: register ino_t *ip, maxinode; ! 762: ! 763: if ((fd = open(special, 0)) < 0 /* cannot open */ ! 764: || lseek(fd, (long)SUPERI*BSIZE, 0) == -1L /* seek failed */ ! 765: || read(fd, &f, sizeof(f)) != sizeof(f)) /* read failed */ ! 766: return 0; ! 767: close(fd); ! 768: ! 769: /* Canonical stuff. */ ! 770: fp = &f; ! 771: canshort(fp->s_isize); ! 772: candaddr(fp->s_fsize); ! 773: canshort(fp->s_nfree); ! 774: for (dp = &fp->s_free[0]; dp < &fp->s_free[NICFREE]; dp += 1) ! 775: candaddr(*dp); ! 776: canshort(fp->s_ninode); ! 777: for (ip = &fp->s_inode[0]; ip < &fp->s_inode[NICINOD]; ip += 1) ! 778: canino(*ip); ! 779: candaddr(fp->s_tfree); ! 780: canino(fp->s_tinode); ! 781: ! 782: /* Test for rationality. */ ! 783: maxinode = (fp->s_isize - INODEI) * INOPB + 1; ! 784: if (fp->s_isize >= fp->s_fsize) ! 785: return 0; ! 786: if ((fp->s_tfree < fp->s_nfree) ! 787: || (fp->s_tfree >= fp->s_fsize - fp->s_isize + 1)) ! 788: return 0; ! 789: if ((fp->s_tinode < fp->s_ninode) || (fp->s_tinode >= maxinode-1 )) ! 790: return 0; ! 791: for (dp = &fp->s_free[0]; dp < &fp->s_free[fp->s_nfree]; dp += 1) ! 792: if ((*dp < fp->s_isize) || (*dp >= fp->s_fsize)) ! 793: return 0; ! 794: for (ip = &fp->s_inode[0]; ip < &fp->s_inode[fp->s_ninode]; ip += 1) ! 795: if ((*ip < 1) || (*ip > maxinode)) ! 796: return 0; ! 797: if (fp->s_fsize > (daddr_t)size) ! 798: return 0; ! 799: if (fp->s_fsize > (daddr_t)size) ! 800: nonfatal("warning: filesystem size=%ld but partition size=%ld", ! 801: (long)fp->s_fsize, size); ! 802: return 1; ! 803: } ! 804: ! 805: /* ! 806: * Make new devices with /etc/mkdev if appropriate. ! 807: */ ! 808: void ! 809: mkdev() ! 810: { ! 811: int hdc; ! 812: ! 813: cls(0); ! 814: printf("Most PC compatible computer systems use MFM, RLL, IDE, or ESDI disk\n"); ! 815: printf("controllers and disk drives. A few percent use SCSI disk drives.\n"); ! 816: printf("Please indicate the type(s) of disk drive(s) used in your computer system.\n"); ! 817: printf("If you are uncertain of the type, please select choice 1.\n\n"); ! 818: printf("Are you using:\n\n"); ! 819: printf("1. AT-compatible hard drive controller (IDE/RLL/MFM/ESDI).\n"); ! 820: printf("2. SCSI hard drive controller.\n"); ! 821: printf("3. Both.\n\n"); ! 822: hdc = get_int(1, 3, "Enter your choice:"); ! 823: ! 824: /* ! 825: * Note: -b option to mkdev also OK for update ! 826: */ ! 827: sprintf(cmd, "/etc/mkdev -b%s%s %s %s", ! 828: (dflag) ? "d" : "", ! 829: (vflag) ? "v" : "", ! 830: (hdc == 1 || hdc == 3) ? "at" : "", ! 831: (hdc == 2 || hdc == 3) ? "scsi" : ""); ! 832: sys(cmd, S_NONFATAL); ! 833: if (hdc == 2 || hdc == 3) ! 834: add_devices(); ! 835: } ! 836: ! 837: /* ! 838: * Make filesystems on COHERENT partitions. ! 839: */ ! 840: void ! 841: mkfs() ! 842: { ! 843: register int i; ! 844: char *name; ! 845: ! 846: cls(0); ! 847: printf( ! 848: "You must create an empty COHERENT filesystem on each COHERENT partition\n" ! 849: "before you can use it. Creating an empty filesystem will destroy all\n" ! 850: "previously existing data on the partition.\n" ! 851: ); ! 852: for (i = 0; i < ndevices; i++) { ! 853: if (notflag(i, F_COH) || (isflag(i, F_ATDEV) && notflag(i, F_SCAN))) ! 854: continue; ! 855: printf("\n"); ! 856: if (isflag(i, F_FS)) ! 857: printf("Partition %d (%s) already contains a COHERENT filesystem.\n", ! 858: i, devname(i, 0)); ! 859: if (i == root) ! 860: printf( ! 861: "\nWARNING!!!\n\n" ! 862: "The installation process expects a NEW file system in the root partition.\n" ! 863: "If you are trying to update an existing COHERENT partition, you must run\n" ! 864: "the COHERENT update. If you are trying to install again after a partial\n" ! 865: "or failed installation, a new root file system must be created again now.\n\n" ! 866: ); ! 867: name = devname(i, 1); ! 868: again: ! 869: if (yes_no("Do you want to create a new COHERENT filesystem on partition %d", i)) { ! 870: if (notflag(i, F_ATDEV)) ! 871: sprintf(cmd, "/etc/mkfs %s %lu", name, devices[i].d_size); ! 872: else if (notflag(i, F_PROTO)) { ! 873: printf("The attempt to scan %s for bad blocks previously failed.", ! 874: name); ! 875: if (yes_no("Do you want to create a new filesystem on it without a bad block list")) ! 876: sprintf(cmd, "/etc/mkfs %s %lu", name, devices[i].d_size); ! 877: else ! 878: continue; ! 879: } else ! 880: sprintf(cmd, "/etc/mkfs %s %s", ! 881: name, protoname(i)); ! 882: clrflag(i, F_FS); ! 883: if (sys(cmd, S_NONFATAL) == 0) { ! 884: setflag(i, F_FS); ! 885: if (notflag(i, F_PROTO)) { ! 886: /* Stick a boot block on device. */ ! 887: /* The proto does it in the other case. */ ! 888: sprintf(cmd, "/bin/cp /conf/boot %s", name); ! 889: sys(cmd, S_NONFATAL); ! 890: } ! 891: ! 892: /* ! 893: * Mount the file system, ! 894: * create /lost+found, ! 895: * unmount it. ! 896: */ ! 897: sprintf(cmd, "/etc/mount %s /mnt", name); ! 898: if (sys(cmd, S_NONFATAL)) ! 899: continue; ! 900: sprintf(cmd, "/bin/mkdir /mnt/lost+found"); ! 901: if (sys(cmd, S_NONFATAL) == 0) ! 902: sys( ! 903: "cd /mnt/lost+found \n" ! 904: "/bin/touch `/bin/from 1 to 200` \n" ! 905: "/bin/rm *", ! 906: S_IGNORE); ! 907: sprintf(cmd, "/etc/umount %s", name); ! 908: sys(cmd, S_NONFATAL); ! 909: } else if (i == root) ! 910: fatal("%s: root partition mkfs failed", name); ! 911: } else if (i == root) { ! 912: if (notflag(i, F_FS)) { ! 913: printf("You must create a filesystem on the root partition.\n"); ! 914: goto again; ! 915: } else { ! 916: /* Stick a boot block on the root device. */ ! 917: sprintf(cmd, "/bin/cp /conf/boot %s", name); ! 918: sys(cmd, S_NONFATAL); ! 919: } ! 920: } ! 921: } ! 922: } ! 923: ! 924: /* ! 925: * Place a bootstrap on the root filesystem. ! 926: * This is only called from update. ! 927: */ ! 928: void ! 929: new_boot() ! 930: { ! 931: sprintf(cmd, "/bin/cp /conf/boot %s", devname(root, 1)); ! 932: sys(cmd, S_FATAL); ! 933: } ! 934: ! 935: /* ! 936: * Validate "name" to see if its an OK UUCP sitename or domain name. If ! 937: * anything suspicious is found, query the user and allow them to change ! 938: * their answer. The domain defaults to UUCP. In order to avoid having ! 939: * 10,000 machines called bbsuser, no default exists for the sitename. ! 940: * ! 941: * Return true if OK, false otherwise. ! 942: */ ! 943: int ! 944: ok_name(name, type) ! 945: unsigned char *name; /* User's response to site/domain question */ ! 946: int type; /* 'd' == domain, 'u' == uucpname/site */ ! 947: { ! 948: int warn = 0; ! 949: char save[NBUF]; /* save off name for caller */ ! 950: ! 951: if (type == 'd' && name[0] == '.') ! 952: strcpy(name, name+1); ! 953: strcpy(save, name); ! 954: if (name[0] == '\0') { /* no input ? */ ! 955: if (type == 'd') { ! 956: strcpy(name, "UUCP"); /* default to UUCP domain */ ! 957: return 1; ! 958: } else { ! 959: return 0; /* no defaults for sitename */ ! 960: } ! 961: } ! 962: if (type == 'u' && strlen(name) > 7) { ! 963: ++warn; ! 964: printf( ! 965: "The system name you chose is greater than seven characters in length.\n" ! 966: ); ! 967: } ! 968: if ((type == 'd' && strspn(name, "abcdefghijklmnopqrstuvwxyz" ! 969: "ABCDEFGHIJKLMNOPQRSTUVWXYZ" ! 970: "0123456789" ! 971: ".-_") != strlen(name)) ! 972: || (type == 'u' && strspn(name, "abcdefghijklmnopqrstuvwxyz" ! 973: "0123456789") != strlen(name))) { ! 974: ++warn; ! 975: printf("The name you chose contains invalid characters.\n"); ! 976: } ! 977: if (!warn) ! 978: return 1; ! 979: if (yes_no("Would you like to choose a different name")) ! 980: return 0; ! 981: strcpy(name, save); ! 982: return 1; ! 983: } ! 984: ! 985: /* ! 986: * If PATCHFILE exists, execute it. ! 987: */ ! 988: void ! 989: patches() ! 990: { ! 991: printf( ! 992: "\nThe kernel on your hard drive will now be patched to run on your system.\n"); ! 993: if (access(PATCHFILE, F_OK) == 0) { ! 994: sprintf(cmd, "/bin/sh %s", PATCHFILE); ! 995: sys(cmd, S_NONFATAL); ! 996: } ! 997: } ! 998: ! 999: /* ! 1000: * Generate a prototype name from a DEVICE entry name. ! 1001: * Return a pointer to the statically allocated name. ! 1002: */ ! 1003: char * ! 1004: protoname(i) int i; ! 1005: { ! 1006: static char pname[5+NAMESIZE+6]; /* e.g. "/tmp/at0a.proto" */ ! 1007: ! 1008: sprintf(pname, "/tmp/%s.proto", devices[i].d_dname); ! 1009: return pname; ! 1010: } ! 1011: ! 1012: /* ! 1013: * Generate a raw device name from a DEVICE entry name. ! 1014: * Return a pointer to the statically allocated name. ! 1015: * If flag and not one of the built-in AT device names, ! 1016: * the device is in /tmp/dev rather than /dev. ! 1017: */ ! 1018: char * ! 1019: rawname(i, flag) int i, flag; ! 1020: { ! 1021: static char rname[4+4+1+1+NAMESIZE]; /* e.g. "/tmp/dev/rat0a" */ ! 1022: ! 1023: sprintf(rname, "/tmp/dev/r%s", devices[i].d_dname); ! 1024: return (flag && notflag(i, F_ATDEV)) ? rname : rname+4; ! 1025: } ! 1026: ! 1027: /* ! 1028: * Patches to be done to the kernel - but can't do them yet because ! 1029: * kernel hasn't been linked. ! 1030: */ ! 1031: void ! 1032: rootpatch() ! 1033: { ! 1034: char line[120]; ! 1035: ! 1036: /* ! 1037: * After fdisk() we know "root". Write to PATCHFILE the patches ! 1038: * that will be needed when a new kernel is linked at /mnt/coherent. ! 1039: */ ! 1040: /* For third kernel. */ ! 1041: sprintf(line, "unsigned long\t%s = 0x%lx;", BAR_BAR, atol(serialno)); ! 1042: cohtune_ent("cohmain", BAR_BAR, line); ! 1043: ! 1044: sprintf(line, "unsigned long\t%s = 0x%lx;", BAR_ENTRY, atol(serialno)); ! 1045: cohtune_ent("cohmain", BAR_ENTRY, line); ! 1046: ! 1047: sprintf(line, "dev_t\t\t%s = makedev(%d,%d);", ! 1048: ROOTDEV, devices[root].d_major, devices[root].d_minor); ! 1049: cohtune_ent("cohmain", ROOTDEV, line); ! 1050: ! 1051: sprintf(line, "dev_t\t\t%s = makedev(%d,%d);", ! 1052: PIPEDEV, devices[root].d_major, devices[root].d_minor); ! 1053: cohtune_ent("cohmain", PIPEDEV, line); ! 1054: ! 1055: /* For the second kernel. */ ! 1056: sprintf(cmd, ! 1057: "echo /conf/patch -v /mnt/coherent ronflag=0 " ! 1058: "\\\"%s\\=makedev\\(%d,%d\\)\\\" " ! 1059: "\\\"%s\\=makedev\\(%d,%d\\)\\\" >> %s\n", ! 1060: ROOTDEV, devices[root].d_major, devices[root].d_minor, ! 1061: PIPEDEV, devices[root].d_major, devices[root].d_minor, PATCHFILE); ! 1062: sys(cmd, S_FATAL); ! 1063: } ! 1064: ! 1065: /* ! 1066: * Need to mount root. ! 1067: * Need to set serialno. ! 1068: * Remove /usr/man/{ALL,COHERENT,MULTI}, /usr/man/man.tar* ! 1069: * Save off any special files before copying in the update ! 1070: * Need to umount root. ! 1071: */ ! 1072: void ! 1073: save_files() ! 1074: { ! 1075: char buf[20]; /* more than enough for a serial # */ ! 1076: int fd; /* file descriptor */ ! 1077: int i; ! 1078: char *s; ! 1079: ! 1080: cls(1); ! 1081: printf("We will now mount your existing COHERENT root filesystem...\n"); ! 1082: sprintf(cmd, "/etc/mount %s /mnt", devname(root, 1)); ! 1083: sys(cmd, S_FATAL); ! 1084: ! 1085: if (!is_dir("/mnt/dev")) /* sanity check! */ ! 1086: fatal("Corrupt or incorrect root filesystem specified"); ! 1087: /* ! 1088: * Read in the old 286 serial number and save it off for later. ! 1089: * If it doesn't exist on the disk, make the user re-enter ! 1090: * the old serial number by hand. ! 1091: */ ! 1092: serialno[0] = '\0'; ! 1093: buf[0] = '\0'; ! 1094: if ((fd = open("/mnt/etc/serialno", 0)) >= 0) { ! 1095: read(fd, buf, sizeof(buf)-1); /* ignore errors */ ! 1096: close(fd); ! 1097: if (!isserial(buf)) /* sets serialno[] */ ! 1098: serialno[0] = '\0'; ! 1099: } ! 1100: if (serialno[0] == '\0') { ! 1101: printf( ! 1102: "\nA card included with your original COHERENT distribution gives the\n" ! 1103: "serial number of your copy of COHERENT.\n\n" ! 1104: ); ! 1105: for (i = 1; i <= 3; i++) { ! 1106: s = get_line("Type in the serial number from the card:"); ! 1107: if (isserial(s)) ! 1108: break; ! 1109: if (i < 3) ! 1110: printf("Invalid serial number, please try again.\n"); ! 1111: else ! 1112: fatal("invalid serial number"); ! 1113: } ! 1114: } ! 1115: ! 1116: printf("\nRemoving old on-line COHERENT manual pages -- please wait...\n"); ! 1117: sys("/bin/rm -rf /mnt/usr/man/ALL /mnt/usr/man/COHERENT " ! 1118: "/mnt/usr/man/MULTI /mnt/usr/man/man.tar*", S_NONFATAL); ! 1119: sync(); ! 1120: ! 1121: /* ! 1122: * Save off any special files just in case the user wants to ! 1123: * get the old ones back... ! 1124: */ ! 1125: if (!is_dir("/mnt/old_coh")) { ! 1126: printf( ! 1127: "\nSaving existing configuration files to directory /old_coh -- please wait...\n\n" ! 1128: ); ! 1129: sys("mkdir -r `cat /conf/upd_dirs`", S_NONFATAL); ! 1130: sys( ! 1131: "for a in `cat /conf/upd_save` ;" ! 1132: " do ;" ! 1133: " cp -d /mnt/$a /mnt/old_coh/$a 2>/dev/null && echo $a... ;" ! 1134: " done ;" ! 1135: " echo", S_IGNORE); ! 1136: sync(); ! 1137: } else ! 1138: printf("Directory /old_coh contains configuration file backups.\n"); ! 1139: ! 1140: ! 1141: sprintf(cmd, "rm -f /mnt/coherent.* /mnt/drv/*"); /* rm stale copies */ ! 1142: sys(cmd, S_FATAL); ! 1143: ! 1144: sprintf(cmd, "/etc/umount %s", devname(root, 1)); ! 1145: sys(cmd, S_FATAL); ! 1146: ! 1147: } ! 1148: ! 1149: /* ! 1150: * Date and time. ! 1151: */ ! 1152: void ! 1153: set_date() ! 1154: { ! 1155: register char *s; ! 1156: int dst_conv; /* 1 if DST conversion will be used */ ! 1157: int dst_now; /* 1 if DST in effect today */ ! 1158: int n; ! 1159: char *tz; ! 1160: time_t now; ! 1161: struct tm *tmp; ! 1162: char *timestr; ! 1163: ! 1164: again: ! 1165: #if 1 /* new set_date */ ! 1166: ! 1167: /* ! 1168: * yyy: ! 1169: * ! 1170: * dst_conv = FALSE ! 1171: * dst_now = FALSE ! 1172: * ! 1173: * if using DST conversion ! 1174: * dst_conv = TRUE ! 1175: * if DST in effect today ! 1176: * dst_now = TRUE ! 1177: * get date from system clock ! 1178: * if dst_conv and dst_now ! 1179: * add 1 hour to date fetched ! 1180: * display date ! 1181: * while date not correct ! 1182: * if proceed without setting clock ! 1183: * goto xxx ! 1184: * read date from kb ! 1185: * write date to CMOS clock and RAM clock ! 1186: * if dst_conv and dst_now ! 1187: * subtract 1 hour from date entered ! 1188: * write adjusted date to CMOS clock ! 1189: * xxx: ! 1190: * set TIMEZONE and TZ variables ! 1191: * if date, TIMEZONE, and TZ not all correct ! 1192: * goto yyy ! 1193: */ ! 1194: cls(0); ! 1195: dst_conv = 0; ! 1196: dst_now = 0; ! 1197: printf( ! 1198: "You can run COHERENT with or without conversion for daylight savings time\n" ! 1199: "(summer time). You should normally run with daylight savings time\n" ! 1200: "conversion. However, if you are going to use both COHERENT and MS-DOS\n" ! 1201: "and you choose to run with daylight savings time conversion,\n" ! 1202: "your time will be wrong (by one hour) during daylight savings time\n" ! 1203: "while you are running under MS-DOS.\n" ! 1204: "\n" ! 1205: ); ! 1206: if (yes_no( ! 1207: "Do you want COHERENT to use daylight savings time conversion")) { ! 1208: dst_conv = 1; ! 1209: printf( ! 1210: "\n" ! 1211: "By default, COHERENT assumes daylight savings time begins on the\n" ! 1212: "first Sunday in April and ends on the last Sunday in October.\n" ! 1213: "If you want to change the defaults, edit the file \"/etc/timezone\"\n" ! 1214: "after you finish installing COHERENT.\n" ! 1215: "\n" ! 1216: ); ! 1217: if (yes_no("Is daylight savings time currently in effect")) ! 1218: dst_now = 1; ! 1219: } ! 1220: sys("/bin/date `/etc/ATclock` > /dev/null", S_NONFATAL); ! 1221: now = time(0); ! 1222: if (dst_conv && dst_now) ! 1223: now += 3600; ! 1224: timestr = ctime(&now); ! 1225: printf( ! 1226: "\nAccording to your system clock, your local date and time are:\n" ! 1227: ); ! 1228: printf("%s\n", timestr); ! 1229: if (!yes_no("Is this correct")) { ! 1230: n = 0; ! 1231: do { ! 1232: if (++n > 3) { ! 1233: printf( ! 1234: "The command which sets the internal real-time clock of your system is\n" ! 1235: "failing repeatedly. Either you are entering the date and time incorrectly\n" ! 1236: "or your clock hardware is not completely AT-compatible. If your clock\n" ! 1237: "hardware is incompatible, you can continue with the installation without\n" ! 1238: "setting the clock correctly. However, if you do so, subsequent clock\n" ! 1239: "references (including file access and modification time information) will be\n" ! 1240: "incorrect and some commands (such as \"date\") will not function correctly.\n" ! 1241: ); ! 1242: if (yes_no("Do you want to proceed without setting the clock correctly")) ! 1243: break; ! 1244: n = 0; ! 1245: } ! 1246: s = get_line( ! 1247: "\nEnter the correct date and time in the form YYMMDDHHMM.SS:" ! 1248: ); ! 1249: sprintf(cmd, "/etc/ATclock %s >/dev/null", s); ! 1250: } while (sys(cmd, S_NONFATAL) != 0); ! 1251: sys("/bin/date `/etc/ATclock` >/dev/null", S_NONFATAL); ! 1252: ! 1253: if (dst_conv && dst_now) { ! 1254: /* Adjust for DST: set hardware clock back one hour. */ ! 1255: now = time(0) - 3600; ! 1256: tmp = localtime(&now); ! 1257: sprintf(cmd, ! 1258: "/etc/ATclock %02d%02d%02d%02d%02d.%02d >/dev/null", ! 1259: tmp->tm_year, tmp->tm_mon + 1, tmp->tm_mday, ! 1260: tmp->tm_hour, tmp->tm_min, tmp->tm_sec); ! 1261: sys(cmd, S_NONFATAL); ! 1262: } ! 1263: ! 1264: } ! 1265: ! 1266: /* Timezone. */ ! 1267: cls(0); ! 1268: printf( ! 1269: "Please choose one of the following timezones:\n" ! 1270: "\t0\tCentral European\n" ! 1271: "\t1\tGreenwich\n" ! 1272: "\t2\tNewfoundland\n" ! 1273: "\t3\tAtlantic\n" ! 1274: "\t4\tEastern\n" ! 1275: "\t5\tCentral\n" ! 1276: "\t6\tMountain\n" ! 1277: "\t7\tPacific\n" ! 1278: "\t8\tYukon\n" ! 1279: "\t9\tAlaska\n" ! 1280: "\t10\tBering\n" ! 1281: "\t11\tHawaii\n" ! 1282: "\t12\tOther\n" ! 1283: ); ! 1284: do { ! 1285: s = get_line("Timezone code:"); ! 1286: } while ((n = atoi(s)) < 0 || n > 12); ! 1287: switch (n) { ! 1288: /* N.B. entries truncated at tz[8] below if !dst_conv. */ ! 1289: case 0: tz = "EST:-60:EDT:1.1.4"; break; ! 1290: case 1: tz = "GMT:000:GDT:1.1.4"; break; ! 1291: case 2: tz = "NST:210:NDT:1.1.4"; break; ! 1292: case 3: tz = "AST:240:ADT:1.1.4"; break; ! 1293: case 4: tz = "EST:300:EDT:1.1.4"; break; ! 1294: case 5: tz = "CST:360:CDT:1.1.4"; break; ! 1295: case 6: tz = "MST:420:MDT:1.1.4"; break; ! 1296: case 7: tz = "PST:480:PDT:1.1.4"; break; ! 1297: case 8: tz = "YST:540:YDT:1.1.4"; break; ! 1298: case 9: tz = "AST:600:ADT:1.1.4"; break; ! 1299: case 10: tz = "BST:660:BDT:1.1.4"; break; ! 1300: case 11: tz = "HST:600:HDT:1.1.4"; break; ! 1301: case 12: tz = NULL; break; ! 1302: } ! 1303: ! 1304: if (tz == NULL) ! 1305: get_timezone(dst_conv); ! 1306: else { ! 1307: strcpy(tzone, tz); ! 1308: if (dst_conv) { ! 1309: /* for TZ, AST:240:ADT becomes AST4ADT */ ! 1310: sprintf(tzone5, "%.3s%d%cDT", ! 1311: tz, atoi(tzone + 4)/60, tz[0]); ! 1312: } else { ! 1313: /* for TZ, AST:240 becomes AST4 */ ! 1314: sprintf(tzone5, "%.3s%d", tz, atoi(tzone + 4)/60); ! 1315: tzone[8] = '\0'; ! 1316: } ! 1317: } ! 1318: /* Done, print current time and retry if user botched it. */ ! 1319: printf("\nYour current local date and time are now:\n"); ! 1320: sprintf(cmd, "TIMEZONE='%s' /bin/date -s `/etc/ATclock`", tzone); ! 1321: sys(cmd, S_NONFATAL); ! 1322: ! 1323: /* Write the timezone to /tmp/timezone for debug */ ! 1324: sprintf(cmd, "/bin/echo export TIMEZONE=\\\"%s\\\" >/tmp/timezone", tzone); ! 1325: sys(cmd, S_NONFATAL); ! 1326: sprintf(cmd, "/bin/echo export TZ=\\\"%s\\\" >>/tmp/timezone", tzone5); ! 1327: sys(cmd, S_NONFATAL); ! 1328: #else ! 1329: cls(0); ! 1330: /* Get correct local time, set system time accordingly. */ ! 1331: printf( ! 1332: "It is important for the COHERENT system to know the correct date and time.\n" ! 1333: "You must provide information about your timezone and daylight savings time.\n" ! 1334: "\n" ! 1335: "According to your computer system clock, your current local date and time are:\n" ! 1336: ); ! 1337: sys("/bin/date `/etc/ATclock`", S_NONFATAL); ! 1338: if (!yes_no("Is this correct")) { ! 1339: n = 0; ! 1340: do { ! 1341: if (++n > 3) { ! 1342: printf( ! 1343: "The command which sets the internal real-time clock of your system is\n" ! 1344: "failing repeatedly. Either you are entering the date and time incorrectly\n" ! 1345: "or your clock hardware is not completely AT-compatible. If your clock\n" ! 1346: "hardware is incompatible, you can continue with the installation without\n" ! 1347: "setting the clock correctly. However, if you do so, subsequent clock\n" ! 1348: "references (including file access and modification time information) will be\n" ! 1349: "incorrect and some commands (such as \"date\") will not function correctly.\n" ! 1350: ); ! 1351: if (yes_no("Do you want to proceed without setting the clock correctly")) ! 1352: break; ! 1353: n = 0; ! 1354: } ! 1355: s = get_line( ! 1356: "Enter the correct date and time in the form YYMMDDHHMM.SS:" ! 1357: ); ! 1358: sprintf(cmd, "/etc/ATclock %s >/dev/null", s); ! 1359: } while (sys(cmd, S_NONFATAL) != 0); ! 1360: sys("/bin/date `/etc/ATclock` >/dev/null", S_NONFATAL); ! 1361: } ! 1362: ! 1363: /* DST. */ ! 1364: cls(0); ! 1365: printf( ! 1366: "You can run COHERENT with or without conversion for daylight savings time\n" ! 1367: "(summer time). You should normally run with daylight savings time\n" ! 1368: "conversion. However, if you are going to use both COHERENT and MS-DOS\n" ! 1369: "and you choose to run with daylight savings time conversion,\n" ! 1370: "your time will be wrong (by one hour) during daylight savings time\n" ! 1371: "while you are running under MS-DOS.\n" ! 1372: "\n" ! 1373: ); ! 1374: dst_conv = yes_no("Do you want COHERENT to use daylight savings time conversion"); ! 1375: if (dst_conv) { ! 1376: printf( ! 1377: "\n" ! 1378: "By default, COHERENT assumes daylight savings time begins on the\n" ! 1379: "first Sunday in April and ends on the last Sunday in October.\n" ! 1380: "If you want to change the defaults, edit the file \"/etc/timezone\"\n" ! 1381: "after you finish installing COHERENT.\n" ! 1382: "\n" ! 1383: ); ! 1384: if (yes_no("Is daylight savings time currently in effect")) { ! 1385: /* Adjust for DST: set hardware clock back one hour. */ ! 1386: now = time(NULL) - 60 * 60; ! 1387: tmp = localtime(&now); ! 1388: sprintf(cmd, "/etc/ATclock %02d%02d%02d%02d%02d.%02d >/dev/null", ! 1389: tmp->tm_year, tmp->tm_mon + 1, tmp->tm_mday, ! 1390: tmp->tm_hour, tmp->tm_min, tmp->tm_sec); ! 1391: sys(cmd, S_NONFATAL); ! 1392: } ! 1393: } ! 1394: ! 1395: /* Timezone. */ ! 1396: cls(0); ! 1397: printf( ! 1398: "Please choose one of the following timezones:\n" ! 1399: "\t0\tCentral European\n" ! 1400: "\t1\tGreenwich\n" ! 1401: "\t2\tNewfoundland\n" ! 1402: "\t3\tAtlantic\n" ! 1403: "\t4\tEastern\n" ! 1404: "\t5\tCentral\n" ! 1405: "\t6\tMountain\n" ! 1406: "\t7\tPacific\n" ! 1407: "\t8\tYukon\n" ! 1408: "\t9\tAlaska\n" ! 1409: "\t10\tBering\n" ! 1410: "\t11\tHawaii\n" ! 1411: "\t12\tOther\n" ! 1412: ); ! 1413: do { ! 1414: s = get_line("Timezone code:"); ! 1415: } while ((n = atoi(s)) < 0 || n > 12); ! 1416: switch (n) { ! 1417: /* N.B. entries truncated at tz[8] below if !dst_conv. */ ! 1418: case 0: tz = "EST:-60:EDT:1.1.4"; break; ! 1419: case 1: tz = "GMT:000:GDT:1.1.4"; break; ! 1420: case 2: tz = "NST:210:NDT:1.1.4"; break; ! 1421: case 3: tz = "AST:240:ADT:1.1.4"; break; ! 1422: case 4: tz = "EST:300:EDT:1.1.4"; break; ! 1423: case 5: tz = "CST:360:CDT:1.1.4"; break; ! 1424: case 6: tz = "MST:420:MDT:1.1.4"; break; ! 1425: case 7: tz = "PST:480:PDT:1.1.4"; break; ! 1426: case 8: tz = "YST:540:YDT:1.1.4"; break; ! 1427: case 9: tz = "AST:600:ADT:1.1.4"; break; ! 1428: case 10: tz = "BST:660:BDT:1.1.4"; break; ! 1429: case 11: tz = "HST:600:HDT:1.1.4"; break; ! 1430: case 12: tz = NULL; break; ! 1431: } ! 1432: ! 1433: if (tz == NULL) ! 1434: get_timezone(dst_conv); ! 1435: else { ! 1436: strcpy(tzone, tz); ! 1437: if (!dst_conv) ! 1438: tzone[8] = '\0'; ! 1439: } ! 1440: ! 1441: /* Done, print current time and retry if user botched it. */ ! 1442: printf("\nYour current local date and time are now:\n"); ! 1443: sprintf(cmd, "TIMEZONE='%s' /bin/date -s `/etc/ATclock`", tzone); ! 1444: sys(cmd, S_NONFATAL); ! 1445: #endif /* new set_date */ ! 1446: if (!yes_no("Is this correct")) ! 1447: goto again; ! 1448: } ! 1449: ! 1450: /* ! 1451: * Configure user devices. ! 1452: * Assumes hard disk filesystem mounted on /mnt. ! 1453: * Write lines to /etc/mount.all, /etc/umount.all to [u]mount the user devices. ! 1454: */ ! 1455: void ! 1456: user_devices() ! 1457: { ! 1458: register int i, status; ! 1459: register char *s, *s2, *name, *rname; ! 1460: ! 1461: if (ncohdev == 1) { ! 1462: sys("/bin/echo /dev/root >>/mnt/etc/checklist", S_NONFATAL); ! 1463: return; ! 1464: } ! 1465: ! 1466: /* Create user device names. */ ! 1467: cls(0); ! 1468: printf( ! 1469: "Your system includes %d partition%s in addition to the root partition.\n" ! 1470: "These partitions are usually mounted on directories in the COHERENT\n" ! 1471: "root filesystem when the system goes into multiuser mode.\n" ! 1472: "For example, one non-root partition might be mounted on\n" ! 1473: "directory \"/u\", another on \"/v\", and so on.\n" ! 1474: "You now may specify where you want each partition mounted.\n", ! 1475: ncohdev - 1, ncohdev == 2 ? "" : "s"); ! 1476: for (i = 0; i < ndevices; i++) { ! 1477: if (notflag(i, F_COH) || notflag(i, F_FS) || isflag(i, F_ROOT)) ! 1478: continue; ! 1479: name = devname(i, 0); ! 1480: rname = rawname(i, 0); ! 1481: printf("\nPartition %d (%s):\n", i, name); ! 1482: if (yes_no("Do you want %s mounted", name)) { ! 1483: setflag(i, F_MOUNT); ! 1484: again: ! 1485: s = get_line("Where do you want to mount it?"); ! 1486: if (*s != '/') { ! 1487: printf("Type a directory name beginning with '/', such as \"/u\".\n"); ! 1488: goto again; ! 1489: } else if ((s2 = strchr(s, ' ')) != NULL) ! 1490: *s2 = '\0'; ! 1491: sprintf(cmd, "/mnt/%s", s); ! 1492: if ((status = is_dir(cmd)) == -1) { ! 1493: printf("%s exists but is not a directory.\n", s); ! 1494: goto again; ! 1495: } else if (status == 1) { ! 1496: strcpy(buf2, s); ! 1497: printf("Directory %s already exists.\n", s); ! 1498: if (!yes_no("Are you sure you want %s mounted on %s", name, s)) ! 1499: goto again; ! 1500: s = buf; ! 1501: strcpy(s, buf2); ! 1502: } else { ! 1503: /* Make the target directory, uid=bin, gid=bin. */ ! 1504: sprintf(cmd, "/bin/mkdir -r /mnt%s", s); ! 1505: if (sys(cmd, S_NONFATAL)) ! 1506: goto again; ! 1507: sprintf(cmd, "/bin/chown bin /mnt%s", s); ! 1508: sys(cmd, S_NONFATAL); ! 1509: sprintf(cmd, "/bin/chgrp bin /mnt%s", s); ! 1510: sys(cmd, S_NONFATAL); ! 1511: } ! 1512: printf("%s will be mounted on %s when COHERENT goes multiuser.\n", ! 1513: name, s); ! 1514: ! 1515: /* Change e.g. /usr/src to usr_src. */ ! 1516: strcpy(buf2, &s[1]); ! 1517: while ((s2 = strchr(buf2, '/')) != NULL) ! 1518: *s2 = '_'; ! 1519: ! 1520: /* Make link to pseudo-device, e.g. "/dev/usr_src". */ ! 1521: sprintf(cmd, "/mnt/dev/%s", buf2); ! 1522: if (exists(cmd)) ! 1523: status = 1; /* use normal name */ ! 1524: else { ! 1525: sprintf(cmd, "/bin/ln -f /mnt%s /mnt/dev/%s", ! 1526: name, buf2); ! 1527: if ((status = sys(cmd, S_NONFATAL)) == 0) ! 1528: printf( ! 1529: "/dev/%s is linked to %s to provide a mnemonic device name.\n", ! 1530: buf2, name); ! 1531: } ! 1532: ! 1533: /* Add lines to /etc/mount.all, /etc/umount.all. */ ! 1534: if (status == 0) ! 1535: sprintf(cmd, "/bin/echo /etc/mount /dev/%s %s >>/mnt/etc/mount.all", ! 1536: buf2, s); ! 1537: else ! 1538: sprintf(cmd, "/bin/echo /etc/mount %s %s >>/mnt/etc/mount.all", ! 1539: name, s); ! 1540: sys(cmd, S_NONFATAL); ! 1541: if (status == 0) ! 1542: sprintf(cmd, "/bin/echo /etc/umount /dev/%s >>/mnt/etc/umount.all", ! 1543: buf2); ! 1544: else ! 1545: sprintf(cmd, "/bin/echo /etc/umount %s >>/mnt/etc/umount.all", ! 1546: name); ! 1547: sys(cmd, S_NONFATAL); ! 1548: ! 1549: /* And again, for the raw device. */ ! 1550: sprintf(cmd, "/mnt/dev/r%s", buf2); ! 1551: if (exists(cmd)) ! 1552: status = 1; ! 1553: else { ! 1554: sprintf(cmd, "/bin/ln -f /mnt%s /mnt/dev/r%s", ! 1555: rname, buf2); ! 1556: if ((status = sys(cmd, S_NONFATAL)) == 0) ! 1557: printf( ! 1558: "/dev/r%s is linked to %s to provide a mnemonic device name.\n", ! 1559: buf2, rname); ! 1560: } ! 1561: ! 1562: /* Add raw device line to /etc/checklist. */ ! 1563: if (status == 0) ! 1564: sprintf(cmd, "/bin/echo /dev/r%s >>/mnt/etc/checklist", ! 1565: buf2); ! 1566: else ! 1567: sprintf(cmd, "/bin/echo %s >>/mnt/etc/checklist", ! 1568: rname); ! 1569: sys(cmd, S_NONFATAL); ! 1570: } else { ! 1571: /* Not mounted, check using standard name. */ ! 1572: sprintf(cmd, "/bin/echo %s >>/mnt/etc/checklist", rname); ! 1573: sys(cmd, S_NONFATAL); ! 1574: } ! 1575: } ! 1576: sys("/bin/echo /dev/root >>/mnt/etc/checklist", S_NONFATAL); ! 1577: ! 1578: /* Link /dev/dos if desired. */ ! 1579: if (yes_no("Do you use both COHERENT and MS-DOS on your hard disk")) { ! 1580: i = get_int(0, ndevices-1, "Enter the partition number of your MS-DOS partition:"); ! 1581: sprintf(cmd, "/bin/ln -f /mnt%s /mnt/dev/dos", devname(i, 0)); ! 1582: if (sys(cmd, S_NONFATAL) == 0) ! 1583: printf( ! 1584: "Device name /dev/dos is now linked to %s for use as a mnemonic\n" ! 1585: "device name. You may use the \"dos*\" family of commands to transfer files\n" ! 1586: "to and from the MS-DOS partition on your hard disk as well as MS-DOS floppies.\n", ! 1587: devname(i, 0)); ! 1588: printf("\n"); ! 1589: } ! 1590: } ! 1591: ! 1592: ! 1593: /* ! 1594: * Set up site/machine specific info in files /etc/uucpname and /etc/domain ! 1595: */ ! 1596: void ! 1597: uucp() ! 1598: { ! 1599: unsigned char *cp; ! 1600: ! 1601: cls(1); ! 1602: if (!update || !exists_and_nz("/mnt/etc/uucpname")) { ! 1603: printf( ! 1604: "In order to use COHERENT's electronic mail facility and UUCP subsystem,\n" ! 1605: "you must choose a \"site name\" for your computer system. In general, a site\n" ! 1606: "name consists of lower case letters or digits and should be at most seven\n" ! 1607: "characters in length. The name you choose should be unique if you intend\n" ! 1608: "to access any other computer systems. Some of the more well known site\n" ! 1609: "names include \"mwc\", \"uunet\", \"clout\", \"decwrl\", \"hp\", \"kgbvax\", " ! 1610: "\"prep\",\n\"seismo\", and \"ucbvax\".\n\n" ! 1611: ); ! 1612: for (;;) { ! 1613: cp = get_line("Please enter the site name for this system: "); ! 1614: if (ok_name(cp, 'u')) ! 1615: break; ! 1616: } ! 1617: sprintf(cmd, "/bin/echo \"%s\" >/mnt/etc/uucpname", cp); ! 1618: sys(cmd, S_NONFATAL); ! 1619: } ! 1620: ! 1621: if (!update || !exists_and_nz("/mnt/etc/domain")) { ! 1622: printf( ! 1623: "\nThe COHERENT mail subsystem supports \"domain addressing\" in addition to\n" ! 1624: "traditional \"bang paths\". Until your system becomes part of a registered\n" ! 1625: "domain, you may use the UUCP pseudo-domain. Domain names consist of groups\n" ! 1626: "of letters and digits separated by periods (dots). Some of the more well\n" ! 1627: "known domains include \"com\", \"edu\", \"gov\", \"org\", \"net\", as well as domains\n" ! 1628: "covering a geographical area, such as the Chicago area \"chi.il.us\" domain.\n" ! 1629: "If you are not registered in a domain, or if you are uncertain about this\n" ! 1630: "question, simply press the <Enter> key to default to the UUCP pseudo-domain.\n\n" ! 1631: ); ! 1632: for (;;) { ! 1633: cp = get_line("Please enter the domain name for this system: "); ! 1634: if (ok_name(cp, 'd')) ! 1635: break; ! 1636: } ! 1637: sprintf(cmd, "/bin/echo \"%s\" >/mnt/etc/domain", cp); ! 1638: sys(cmd, S_NONFATAL); ! 1639: } ! 1640: } ! 1641: ! 1642: /* ! 1643: * Hi there. ! 1644: */ ! 1645: void ! 1646: welcome() ! 1647: { ! 1648: register char *s; ! 1649: int i; ! 1650: ! 1651: cls(0); ! 1652: printf( ! 1653: "\n\n\n\n\n\n\n\n" ! 1654: " The COHERENT System\n\n" ! 1655: " Copyright (c) 1982, 1992 by Mark Williams Company\n\n" ! 1656: " 60 Revere Drive, Northbrook, IL 60062\n\n" ! 1657: " 708-291-6700, 708-291-6750 (FAX)\n" ! 1658: "\n\n\n\n\n\n" ! 1659: ); ! 1660: ! 1661: cls(1); ! 1662: printf( ! 1663: "Welcome to the COHERENT operating system!\n\n" ! 1664: "Your computer is now running COHERENT " ! 1665: "386" ! 1666: " from the floppy disk.\n"); ! 1667: if (update) ! 1668: printf( ! 1669: "This program will update your existing COHERENT 4.0.x system to COHERENT 4.2.0.\n" ! 1670: "\n" ! 1671: "Be sure to read the section on \"Updating\" in the COHERENT 386 Release\n" ! 1672: "Notes prior to attempting this update!\n\n" ! 1673: "Please be patient and read the instructions on the screen carefully.\n" ! 1674: "\n" ! 1675: ); ! 1676: else ! 1677: printf( ! 1678: "This program will install COHERENT onto your hard disk.\n" ! 1679: "\n" ! 1680: "If you are already running COHERENT on your hard disk, you must perform an\n" ! 1681: "update rather than a full installation. To do so, please REBOOT NOW and\n" ! 1682: "follow the detailed update instructions in the COHERENT release notes supplied\n" ! 1683: "with this release.\n" ! 1684: "\n" ! 1685: "You can interrupt installation at any time by typing <Ctrl-C>;\n" ! 1686: "then reboot and start the installation procedure again.\n" ! 1687: "Please be patient and read the instructions on the screen carefully.\n" ! 1688: "\n" ! 1689: ); ! 1690: cls(1); ! 1691: if (update) ! 1692: sys("/etc/kbdinstall -u", S_NONFATAL); ! 1693: else ! 1694: sys("/etc/kbdinstall -b", S_NONFATAL); ! 1695: ! 1696: cls(1); ! 1697: if (!update) { ! 1698: printf( ! 1699: "A card included with your distribution gives the serial number\n" ! 1700: "of your copy of COHERENT.\n" ! 1701: ); ! 1702: for (i = 1; i <= 3; i++) { ! 1703: s = get_line("Type in the serial number from the card:"); ! 1704: if (isserial(s)) ! 1705: return; ! 1706: printf("Invalid serial number, please try again.\n"); ! 1707: } ! 1708: fatal("invalid serial number"); ! 1709: } ! 1710: } ! 1711: ! 1712: /* ! 1713: * Generate a partition table device name from a DEVICE entry name. ! 1714: * Return a pointer to the statically allocated name. ! 1715: * If flag and not one of the built-in AT device names, ! 1716: * the device is in /tmp/dev rather than /dev. ! 1717: */ ! 1718: char * ! 1719: xname(i, flag) int i, flag; ! 1720: { ! 1721: static char xname[4+4+1+NAMESIZE]; /* e.g. "/tmp/dev/at0x" */ ! 1722: ! 1723: sprintf(xname, "/tmp/dev/%s", devices[i].d_xname); ! 1724: return (flag && notflag(i, F_ATDEV)) ? xname : xname+4; ! 1725: } ! 1726: ! 1727: /* end of build.c */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.