📄 uuxqt.c
字号:
/* notify user of exit status if: * 1. ok to notify user && ok to return any exit status * 2. ok to notify user && exit status was non zero && ok to send non zero exit status * 3. mail command failed - return mail to sender */ if (notiok && (!nonzero || (nonzero && ret != 0))) notify(user, Rmtname, cmd, retstat, ferr, retaddr); else if (ret != 0 && strcmp(xcmd, "rmail") == SAME) { /* mail failed - return letter to sender */ /* only if user really wants it */ if (!nonzero) retosndr(user, Rmtname, fin, ferr, retaddr); sprintf(buf, "ret (%o) from %s!%s", ret, Rmtname, user); logent("MAIL FAIL", buf); } DEBUG(4, "exit cmd - %d\n", ret); subchdir(Spool); rmxfiles(xfile); if (ret != 0) { /* exit status not zero */ dfp = fopen(subfile(dfile), "a"); ASSERT(dfp != NULL, "CAN'T OPEN", dfile, 0); fprintf(dfp, "exit status %d", ret); fclose(dfp); sprintf(buf, "cmd: %s; ret: %s", xcmd, retstat); logent("CMD FAILED", buf); } if (strcmp(fout, "/dev/null") != SAME) { if (prefix(sysout, Myname)) { xmv(dfile, fout); chmod(fout, BASEMODE); } else { gename(CMDPRE, sysout, 'O', cfile); fp = fopen(subfile(cfile), "w"); ASSERT(fp != NULL, "OPEN", cfile, 0); fprintf(fp, "S %s %s %s - %s 0666\n", dfile, fout, user, lastpart(dfile)); fclose(fp); } } rmfiles: /* on the chance that another uuxqt was working * on this file and removed it, keep going * - with the addition of per command uuxqts * it is possible for overlap when another daemon * starts up. */ if (xfp == NULL) { DEBUG(4, "xfp is null: %d\n", xfp ); continue; } fseek(xfp, 0l, 0); while (fgets(buf, BUFSIZ, xfp) != NULL) { if (buf[0] != X_RQDFILE) continue; sscanf(&buf[1], "%s", file); ret=unlink(subfile(file)); } fclose(xfp); ret=unlink(subfile(xfile)); ASSERT_NOFAIL(ret != -1,"CAN NOT UNLINK", subfile(xfile),errno); unlink(subfile(ferr)); } /* end doprocess loop */ } /* end nextsys loop */ if (stcico) xuucico("", ""); cleanup(0);}cleanup(code)int code;{ logcls(); rmlock(CNULL); exit(code);}/******* * gtxfile(file) get a file to execute * char *file; * * return codes: 0 - no file | 1 - file to execute * Mod to recheck for X-able files. Sept 1982, rti!trt. * Should use stuff like bldflst to keep files in sequence * Suggested by utzoo.2458 (utzoo!henry) */gtxfile(file)char *file;{ static int reopened; static DIR *dirp; static char xlock[MAXFULLNAME] = { '\0' }; char pre[3];retry: if (dirp == NULL) { dirp = opendir(subdir(Spool, XQTPRE)); ASSERT(dirp != NULL, "GTXFILE CAN'T OPEN", Spool, 0); } pre[0] = XQTPRE; pre[1] = '.'; pre[2] = '\0'; while (gnamef(dirp, file) != 0) { DEBUG(4, "file - %s\n", file); if (!prefix(pre, file)) continue;#ifndef UUDIR /* Skip spurious subdirectories */ if (strcmp(pre, file) == SAME) continue;#endif if (xlock[0] != '\0') { /* remove lock for previous X.file */ rmlock(xlock); xlock[0] = '\0'; } /* prevent concurrent uuxqts from working on the same * X.file. This can only happen when a command specific * uuxqt starts up after a general uuxqt. * This locking mechanism should permit concurrent general * uuxqts. */ sprintf(xlock,"%s/LCK.%s",SPOOL,file); if (ulockf(xlock, (time_t) X_LOCKTIME) != 0) { /* dont remove another daemons lock file */ xlock[0] = '\0'; DEBUG(8,"this xfile already processed: %s\n", file); continue; } if (gotfiles(file)) /* return file to execute */ return(1); } if (xlock[0] != '\0') { /* remove lock for previous X.file */ rmlock(xlock); xlock[0] = '\0'; } closedir(dirp); dirp = NULL; if (!reopened) { reopened++; goto retry; } return(0);}/*** * gotfiles(file) check for needed files * char *file; * * return codes: 0 - not ready | 1 - all files ready */gotfiles(file)char *file;{ struct stat stbuf; FILE *fp; char buf[BUFSIZ], rqfile[MAXFULLNAME]; fp = fopen(subfile(file), "r"); if (fp == NULL) return(0); while (fgets(buf, BUFSIZ, fp) != NULL) { DEBUG(4, "%s\n", buf); if (buf[0] != X_RQDFILE) continue; sscanf(&buf[1], "%s", rqfile); expfile(rqfile); if (stat(subfile(rqfile), &stbuf) == -1) { fclose(fp); return(0); } } fclose(fp); return(1);}/*** * rmxfiles(xfile) remove execute files to x-directory * char *xfile; * * return codes - none */rmxfiles(xfile)char *xfile;{ FILE *fp; char buf[BUFSIZ], file[MAXFULLNAME], tfile[MAXFULLNAME]; char tfull[MAXFULLNAME]; if((fp = fopen(subfile(xfile), "r")) == NULL) return; while (fgets(buf, BUFSIZ, fp) != NULL) { if (buf[0] != X_RQDFILE) continue; if (sscanf(&buf[1], "%s%s", file, tfile) < 2) continue; sprintf(tfull, "%s/%s", XQTDIR, tfile); unlink(subfile(tfull)); } fclose(fp); return;}/*** * mvxfiles(xfile) move execute files to x-directory * char *xfile; * * return codes - none */mvxfiles(xfile)char *xfile;{ FILE *fp; char buf[BUFSIZ], ffile[MAXFULLNAME], tfile[MAXFULLNAME]; char tfull[MAXFULLNAME]; int ret; if((fp = fopen(subfile(xfile), "r")) == NULL) return; while (fgets(buf, BUFSIZ, fp) != NULL) { if (buf[0] != X_RQDFILE) continue; if (sscanf(&buf[1], "%s%s", ffile, tfile) < 2) continue; expfile(ffile); sprintf(tfull, "%s/%s", XQTDIR, tfile); unlink(subfile(tfull)); ret = link(subfile(ffile), subfile(tfull)); ASSERT(ret == 0, "LINK ERROR", "", ret);/* unlink(subfile(ffile));*/ } fclose(fp); return;}/*** * argok(xc, cmd) check for valid command/argumanet * *NOTE - side effect is to set xc to the * command to be executed. * char *xc, *cmd; * * return 0 - ok | 1 nok */argok(xc, cmd)char *xc, *cmd;{ struct command *ptr;#ifndef ALLOK /* don't allow sh command strings `....` */ /* don't allow redirection of standard in or out */ /* don't allow other funny stuff */ /* but there are probably total holes here */ /* post-script. ittvax!swatt has a uuxqt that solves this. */ /* This version of uuxqt will shortly disappear */ if (index(cmd, '`') != NULL || index(cmd, '>') != NULL || index(cmd, ';') != NULL || index(cmd, '^') != NULL || index(cmd, '&') != NULL || index(cmd, '|') != NULL || index(cmd, '<') != NULL) return(1);#endif if (xc[0] != '\0') return(0);#ifndef ALLOK ptr = Cmds; while(ptr->cmd != NULL) { if (strcmp(cmd, ptr->cmd) == SAME) break; ptr++; } if (ptr->cmd == NULL) { DEBUG(4, "command not found: %s\n", cmd); return(1); }/* * If the USERFILE execution level for the remote system is less * than the execution level specified in L.cmds then do not * allow remote execution to proceed. */ if (getxeqlevel(Rmtname) < ptr->xeqlevel) { DEBUG(4, "Remote site (%s) can not execute command\n", Rmtname); logent("execute level too low", Rmtname); return(1); }#endif strcpy(xc, cmd); return(0);}/*** * notify send mail to user giving execution results * return code - none * This program assumes new mail command - send remote mail */notify(user, rmt, cmd, str, ferr, raddr)char *user, *rmt, *cmd, *str, *ferr, *raddr;{ char text[MAXFULLNAME]; char ruser[MAXFULLNAME]; sprintf(text, "uuxqt cmd (%.50s) status (%s)", cmd, str); if (prefix(rmt, Myname)) strcpy(ruser, user); else sprintf(ruser, "%s!%s", rmt, user); /* use return address if supplied */ if (raddr[0] != '\0') strcpy(ruser, raddr); mailst(ruser, text, "", ferr); return;}/*** * retosndr - return mail to sender * * return code - none */retosndr(user, rmt, file, ferr, raddr)char *user, *rmt, *file, *ferr, *raddr;{ struct stat stbuf; char ruser[MAXFULLNAME]; int ret; if (strcmp(rmt, Myname) == SAME) strcpy(ruser, user); else sprintf(ruser, "%s!%s", rmt, user); /* use return address if supplied */ if (raddr[0] != '\0') strcpy(ruser, raddr); ret = stat(subfile(file), &stbuf); if ((anyread(file) == 0) || (ret==0 && stbuf.st_uid == Euid)) mailst(ruser, "Mail failed. Letter returned to sender.\n", file, ferr); else mailst(ruser, "Mail failed. uuxqt can not read the letter \n", "", ferr); return;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -