static void frecverr(const char *msg, ...) { extern char fromb[]; va_list ap; va_start(ap, msg); rcleanup(0); syslog(LOG_ERR, "%s", fromb); vsyslog(LOG_ERR, msg, ap); va_end(ap); putchar('\1'); /* return error code */ exit(1); }
/* * Read printer jobs sent by lpd and copy them to the spooling directory. * Return the number of jobs successfully transfered. */ static int readjob() { register int size, nfiles; register char *cp; ack(); nfiles = 0; for (;;) { /* * Read a command to tell us what to do */ cp = line; do { if ((size = read(1, cp, 1)) != 1) { if (size < 0) frecverr("%s: Lost connection",printer); return(nfiles); } } while (*cp++ != '\n'); *--cp = '\0'; cp = line; switch (*cp++) { case '\1': /* cleanup because data sent was bad */ rcleanup(0); continue; case '\2': /* read cf file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; /* * host name has been authenticated, we use our * view of the host name since we may be passed * something different than what gethostbyaddr() * returns */ strcpy(cp + 6, from); strcpy(tfname, cp); tfname[0] = 't'; if (!chksize(size)) { (void) write(1, "\2", 1); continue; } if (!readfile(tfname, size)) { rcleanup(0); continue; } if (link(tfname, cp) < 0) frecverr("%s: %m", tfname); (void) unlink(tfname); tfname[0] = '\0'; nfiles++; continue; case '\3': /* read df file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; if (!chksize(size)) { (void) write(1, "\2", 1); continue; } (void) strcpy(dfname, cp); if (index(dfname, '/')) frecverr("readjob: %s: illegal path name", dfname); (void) readfile(dfname, size); continue; } frecverr("protocol screwup: %s", line); } }
/* * Read printer jobs sent by lpd and copy them to the spooling directory. * Return the number of jobs successfully transferred. */ static int readjob(void) { int size, nfiles; char *cp; ack(); nfiles = 0; for (;;) { /* * Read a command to tell us what to do */ cp = line; do { if ((size = read(STDOUT_FILENO, cp, 1)) != 1) { if (size < 0) frecverr("%s: Lost connection", printer); return(nfiles); } } while (*cp++ != '\n' && (cp - line + 1) < sizeof(line)); if (cp - line + 1 >= sizeof(line)) frecverr("readjob overflow"); *--cp = '\0'; cp = line; switch (*cp++) { case '\1': /* cleanup because data sent was bad */ rcleanup(0); continue; case '\2': /* read cf file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; /* * host name has been authenticated, we use our * view of the host name since we may be passed * something different than what gethostbyaddr() * returns */ strlcpy(cp + 6, from, sizeof(line) + line - cp - 6); if (strchr(cp, '/')) frecverr("readjob: %s: illegal path name", cp); strlcpy(tfname, cp, sizeof(tfname)); tfname[0] = 't'; if (!chksize(size)) { (void)write(STDOUT_FILENO, "\2", 1); continue; } /* * XXX * We blindly believe what the remote host puts * for the path to the df file. In general this * is OK since we don't allow paths with '/' in * them. Still, it would be better to sanity * check the cf file sent to us and make the * df name match the cf name we used. That way * we avoid any possible collisions. */ if (!readfile(tfname, size)) { rcleanup(0); continue; } if (link(tfname, cp) < 0) frecverr("link %s %s: %m", tfname, cp); (void)unlink(tfname); tfname[0] = '\0'; nfiles++; continue; case '\3': /* read df file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; if (strchr(cp, '/')) frecverr("readjob: %s: illegal path name", cp); if (!chksize(size)) { (void)write(STDOUT_FILENO, "\2", 1); continue; } (void)strlcpy(dfname, cp, sizeof(dfname)); (void)readfile(dfname, size); continue; } frecverr("protocol screwup: %s", line); } }