1 /* 2 * Copyright (c) 1980 The Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 */ 7 8 #ifndef lint 9 char copyright[] = 10 "@(#) Copyright (c) 1980 The Regents of the University of California.\n\ 11 All rights reserved.\n"; 12 #endif /* not lint */ 13 14 #ifndef lint 15 static char sccsid[] = "@(#)mt.c 5.5 (Berkeley) 01/14/91"; 16 #endif /* not lint */ 17 18 /* 19 * mt -- 20 * magnetic tape manipulation program 21 */ 22 #include <sys/types.h> 23 #include <sys/ioctl.h> 24 #include <sys/mtio.h> 25 #include <stdio.h> 26 #include <ctype.h> 27 28 #define equal(s1,s2) (strcmp(s1, s2) == 0) 29 30 struct commands { 31 char *c_name; 32 int c_code; 33 int c_ronly; 34 } com[] = { 35 { "weof", MTWEOF, 0 }, 36 { "eof", MTWEOF, 0 }, 37 { "fsf", MTFSF, 1 }, 38 { "bsf", MTBSF, 1 }, 39 { "fsr", MTFSR, 1 }, 40 { "bsr", MTBSR, 1 }, 41 { "rewind", MTREW, 1 }, 42 { "offline", MTOFFL, 1 }, 43 { "rewoffl", MTOFFL, 1 }, 44 { "status", MTNOP, 1 }, 45 { 0 } 46 }; 47 48 int mtfd; 49 struct mtop mt_com; 50 struct mtget mt_status; 51 char *tape; 52 53 main(argc, argv) 54 char **argv; 55 { 56 char line[80], *getenv(); 57 register char *cp; 58 register struct commands *comp; 59 60 if (argc > 2 && (equal(argv[1], "-t") || equal(argv[1], "-f"))) { 61 argc -= 2; 62 tape = argv[2]; 63 argv += 2; 64 } else 65 if ((tape = getenv("TAPE")) == NULL) 66 tape = DEFTAPE; 67 if (argc < 2) { 68 fprintf(stderr, "usage: mt [ -f device ] command [ count ]\n"); 69 exit(1); 70 } 71 cp = argv[1]; 72 for (comp = com; comp->c_name != NULL; comp++) 73 if (strncmp(cp, comp->c_name, strlen(cp)) == 0) 74 break; 75 if (comp->c_name == NULL) { 76 fprintf(stderr, "mt: don't grok \"%s\"\n", cp); 77 exit(1); 78 } 79 if ((mtfd = open(tape, comp->c_ronly ? 0 : 2)) < 0) { 80 perror(tape); 81 exit(1); 82 } 83 if (comp->c_code != MTNOP) { 84 mt_com.mt_op = comp->c_code; 85 mt_com.mt_count = (argc > 2 ? atoi(argv[2]) : 1); 86 if (mt_com.mt_count < 0) { 87 fprintf(stderr, "mt: negative repeat count\n"); 88 exit(1); 89 } 90 if (ioctl(mtfd, MTIOCTOP, &mt_com) < 0) { 91 fprintf(stderr, "%s %s %d ", tape, comp->c_name, 92 mt_com.mt_count); 93 perror("failed"); 94 exit(2); 95 } 96 } else { 97 if (ioctl(mtfd, MTIOCGET, (char *)&mt_status) < 0) { 98 perror("mt"); 99 exit(2); 100 } 101 status(&mt_status); 102 } 103 } 104 105 #ifdef vax 106 #include <vaxmba/mtreg.h> 107 #include <vaxmba/htreg.h> 108 109 #include <vaxuba/utreg.h> 110 #include <vaxuba/tmreg.h> 111 #undef b_repcnt /* argh */ 112 #include <vaxuba/tsreg.h> 113 #endif 114 115 #ifdef sun 116 #include <sundev/tmreg.h> 117 #include <sundev/arreg.h> 118 #endif 119 120 #ifdef tahoe 121 #include <tahoe/vba/cyreg.h> 122 #endif 123 124 struct tape_desc { 125 short t_type; /* type of magtape device */ 126 char *t_name; /* printing name */ 127 char *t_dsbits; /* "drive status" register */ 128 char *t_erbits; /* "error" register */ 129 } tapes[] = { 130 #ifdef vax 131 { MT_ISTS, "ts11", 0, TSXS0_BITS }, 132 { MT_ISHT, "tm03", HTDS_BITS, HTER_BITS }, 133 { MT_ISTM, "tm11", 0, TMER_BITS }, 134 { MT_ISMT, "tu78", MTDS_BITS, 0 }, 135 { MT_ISUT, "tu45", UTDS_BITS, UTER_BITS }, 136 #endif 137 #ifdef sun 138 { MT_ISCPC, "TapeMaster", TMS_BITS, 0 }, 139 { MT_ISAR, "Archive", ARCH_CTRL_BITS, ARCH_BITS }, 140 #endif 141 #ifdef tahoe 142 { MT_ISCY, "cipher", CYS_BITS, CYCW_BITS }, 143 #endif 144 { 0 } 145 }; 146 147 /* 148 * Interpret the status buffer returned 149 */ 150 status(bp) 151 register struct mtget *bp; 152 { 153 register struct tape_desc *mt; 154 155 for (mt = tapes; mt->t_type; mt++) 156 if (mt->t_type == bp->mt_type) 157 break; 158 if (mt->t_type == 0) { 159 printf("unknown tape drive type (%d)\n", bp->mt_type); 160 return; 161 } 162 printf("%s tape drive, residual=%d\n", mt->t_name, bp->mt_resid); 163 printreg("ds", bp->mt_dsreg, mt->t_dsbits); 164 printreg("\ner", bp->mt_erreg, mt->t_erbits); 165 putchar('\n'); 166 } 167 168 /* 169 * Print a register a la the %b format of the kernel's printf 170 */ 171 printreg(s, v, bits) 172 char *s; 173 register char *bits; 174 register unsigned short v; 175 { 176 register int i, any = 0; 177 register char c; 178 179 if (bits && *bits == 8) 180 printf("%s=%o", s, v); 181 else 182 printf("%s=%x", s, v); 183 bits++; 184 if (v && bits) { 185 putchar('<'); 186 while (i = *bits++) { 187 if (v & (1 << (i-1))) { 188 if (any) 189 putchar(','); 190 any = 1; 191 for (; (c = *bits) > 32; bits++) 192 putchar(c); 193 } else 194 for (; *bits > 32; bits++) 195 ; 196 } 197 putchar('>'); 198 } 199 } 200