1 static char *sccsid = "@(#)dumprmt.c 1.8 (Berkeley) 12/19/84"; 2 3 #include <sys/param.h> 4 #include <sys/mtio.h> 5 #include <sys/ioctl.h> 6 #include <sys/socket.h> 7 #include <sys/inode.h> 8 9 #include <netinet/in.h> 10 11 #include <stdio.h> 12 #include <pwd.h> 13 #include <netdb.h> 14 #include <dumprestor.h> 15 16 #define TS_CLOSED 0 17 #define TS_OPEN 1 18 19 static int rmtstate = TS_CLOSED; 20 int rmtape; 21 int rmtconnaborted(); 22 char *rmtpeer; 23 24 extern int ntrec; /* blocking factor on tape */ 25 26 rmthost(host) 27 char *host; 28 { 29 30 rmtpeer = host; 31 signal(SIGPIPE, rmtconnaborted); 32 rmtgetconn(); 33 if (rmtape < 0) 34 return (0); 35 return (1); 36 } 37 38 rmtconnaborted() 39 { 40 41 fprintf(stderr, "rdump: Lost connection to remote host.\n"); 42 exit(1); 43 } 44 45 rmtgetconn() 46 { 47 static struct servent *sp = 0; 48 struct passwd *pw; 49 char *name = "root"; 50 int size; 51 52 if (sp == 0) { 53 sp = getservbyname("shell", "tcp"); 54 if (sp == 0) { 55 fprintf(stderr, "rdump: shell/tcp: unknown service\n"); 56 exit(1); 57 } 58 } 59 pw = getpwuid(getuid()); 60 if (pw && pw->pw_name) 61 name = pw->pw_name; 62 rmtape = rcmd(&rmtpeer, sp->s_port, name, name, "/etc/rmt", 0); 63 size = ntrec * TP_BSIZE; 64 if (setsockopt(rmtape, SOL_SOCKET, SO_SNDBUF, &size, sizeof (size)) < 0) 65 fprintf(stderr, "rdump: Warning: setsockopt buffer size failed.\n"); 66 } 67 68 rmtopen(tape, mode) 69 char *tape; 70 int mode; 71 { 72 char buf[256]; 73 74 sprintf(buf, "O%s\n%d\n", tape, mode); 75 rmtcall(tape, buf); 76 rmtstate = TS_OPEN; 77 } 78 79 rmtclose() 80 { 81 82 if (rmtstate != TS_OPEN) 83 return; 84 rmtcall("close", "C\n"); 85 rmtstate = TS_CLOSED; 86 } 87 88 rmtread(buf, count) 89 char *buf; 90 int count; 91 { 92 char line[30]; 93 int n, i, cc; 94 extern errno; 95 96 sprintf(line, "R%d\n", count); 97 n = rmtcall("read", line); 98 if (n < 0) { 99 errno = n; 100 return (-1); 101 } 102 for (i = 0; i < n; i += cc) { 103 cc = read(rmtape, buf+i, n - i); 104 if (cc <= 0) { 105 rmtconnaborted(); 106 } 107 } 108 return (n); 109 } 110 111 rmtwrite(buf, count) 112 char *buf; 113 int count; 114 { 115 char line[30]; 116 117 sprintf(line, "W%d\n", count); 118 write(rmtape, line, strlen(line)); 119 write(rmtape, buf, count); 120 return (rmtreply("write")); 121 } 122 123 rmtwrite0(count) 124 int count; 125 { 126 char line[30]; 127 128 sprintf(line, "W%d\n", count); 129 write(rmtape, line, strlen(line)); 130 } 131 132 rmtwrite1(buf, count) 133 char *buf; 134 int count; 135 { 136 137 write(rmtape, buf, count); 138 } 139 140 rmtwrite2() 141 { 142 int i; 143 144 return (rmtreply("write")); 145 } 146 147 rmtseek(offset, pos) 148 int offset, pos; 149 { 150 char line[80]; 151 152 sprintf(line, "L%d\n%d\n", offset, pos); 153 return (rmtcall("seek", line)); 154 } 155 156 struct mtget mts; 157 158 struct mtget * 159 rmtstatus() 160 { 161 register int i; 162 register char *cp; 163 164 if (rmtstate != TS_OPEN) 165 return (0); 166 rmtcall("status", "S\n"); 167 for (i = 0, cp = (char *)&mts; i < sizeof(mts); i++) 168 *cp++ = rmtgetb(); 169 return (&mts); 170 } 171 172 rmtioctl(cmd, count) 173 int cmd, count; 174 { 175 char buf[256]; 176 177 if (count < 0) 178 return (-1); 179 sprintf(buf, "I%d\n%d\n", cmd, count); 180 return (rmtcall("ioctl", buf)); 181 } 182 183 rmtcall(cmd, buf) 184 char *cmd, *buf; 185 { 186 187 if (write(rmtape, buf, strlen(buf)) != strlen(buf)) 188 rmtconnaborted(); 189 return (rmtreply(cmd)); 190 } 191 192 rmtreply(cmd) 193 char *cmd; 194 { 195 register int c; 196 char code[30], emsg[BUFSIZ]; 197 198 rmtgets(code, sizeof (code)); 199 if (*code == 'E' || *code == 'F') { 200 rmtgets(emsg, sizeof (emsg)); 201 msg("%s: %s\n", cmd, emsg, code + 1); 202 if (*code == 'F') { 203 rmtstate = TS_CLOSED; 204 return (-1); 205 } 206 return (-1); 207 } 208 if (*code != 'A') { 209 msg("Protocol to remote tape server botched (code %s?).\n", 210 code); 211 rmtconnaborted(); 212 } 213 return (atoi(code + 1)); 214 } 215 216 rmtgetb() 217 { 218 char c; 219 220 if (read(rmtape, &c, 1) != 1) 221 rmtconnaborted(); 222 return (c); 223 } 224 225 rmtgets(cp, len) 226 char *cp; 227 int len; 228 { 229 230 while (len > 1) { 231 *cp = rmtgetb(); 232 if (*cp == '\n') { 233 cp[1] = 0; 234 return; 235 } 236 cp++; 237 len--; 238 } 239 msg("Protocol to remote tape server botched (in rmtgets).\n"); 240 rmtconnaborted(); 241 } 242