📄 crypt.c
字号:
status = iosb[0]; if (!(status & 1)) return status; /* copy old mode into new-mode buffer, then modify to be either NOECHO or * ECHO (depending on function argument opt) */ newmode[0] = oldmode[0]; newmode[1] = oldmode[1]; if (opt == 0) /* off */ newmode[1] |= TT$M_NOECHO; /* set NOECHO bit */ else newmode[1] &= ~((unsigned long) TT$M_NOECHO); /* clear NOECHO bit */ /* use the IO$_SETMODE function to change the tty status */ status = sys$qio(0, DevChan, IO$_SETMODE, &iosb, 0, 0, newmode, 8, 0, 0, 0, 0); if (!(status & 1)) return status; status = iosb[0]; if (!(status & 1)) return status; /* deassign the sys$input channel by way of clean-up */ status = sys$dassgn(DevChan); if (!(status & 1)) return status; return SS$_NORMAL; /* we be happy */} /* end function echo() */#else /* !VMS */#if (!defined(DOS_NT_OS2) && !defined(AMIGA) && !defined(MACOS))static int echofd=(-1); /* file descriptor whose echo is off *//*********************************************************************** * Turn echo off for file descriptor f. Assumes that f is a tty device. */void echoff(f) int f; /* file descriptor for which to turn echo off */{ struct sgttyb sg; /* tty device structure */ echofd = f; GTTY(f, &sg); /* get settings */ sg.sg_flags &= ~ECHO; /* turn echo off */ STTY(f, &sg);}/*********************************************************************** * Turn echo back on for file descriptor echofd. */void echon(){ struct sgttyb sg; /* tty device structure */ if (echofd != -1) { GTTY(echofd, &sg); /* get settings */ sg.sg_flags |= ECHO; /* turn echo on */ STTY(echofd, &sg); echofd = -1; }}#endif /* !(DOS_NT_OS2 || AMIGA || MACOS) */#endif /* ?VMS */#ifdef AMIGA/*********************************************************************** * Get a password of length n-1 or less into *p using the prompt *m. * The entered password is not echoed. * * On AMIGA, SAS/C 6.x provides raw console input via getch(). This is * also available in SAS/C 5.10b, if the separately chargeable ANSI * libraries are used. * * Aztec C provides functions set_raw() and set_con() which we use for * echoff() and echon(). * * Code for other compilers needs to provide routines or macros for * echoff() and echon() to either send ACTION_SET_CONSOLE packets or * provice "pseudo non-echo" input by setting the background and * foreground colors the same. Then, only spaces visibly echo. This * approach is the default in crypt.h. Unfortunately, the cursor * cannot be held stationary during input because the standard getc() * and getchar() system routines buffer input until CR entered (due to * the lack of switchable raw I/O). This may be considered an * advantage since it allows feedback for backspacing errors. * * Simulating true raw I/O on systems without getch() introduces * undesirable complexity and overhead, so we'll live with this * simpler method for those compilers. */char *getp(m, p, n) char *m,*p; int n;{ int i; int c; fputs (m,stderr); /* display prompt and flush */ fflush(stderr); echoff(2); i = 0; while ( i <= n ) { c=getch(); if ( (c == '\n') || (c == '\r')) break; /* until user hits CR */ if (c == 0x03) { /* ^C in input */ Signal(FindTask(NULL), SIGBREAKF_CTRL_C); break; } if (i < n) p[i++]=(char)c; /* truncate past n */ } ECHO_NEWLINE(); echon(); i = (i<n) ? i : (n-1); p[i]=0; /* terminate string */ return p;}#endif /* AMIGA */#ifdef DOS_NT_OS2char *getp(m, p, n) char *m; /* prompt for password */ char *p; /* return value: line input */ int n; /* bytes available in p[] */{ char c; /* one-byte buffer for read() to use */ int i; /* number of characters input */ char *w; /* warning on retry */ /* get password */ w = ""; do { fputs(w, stderr); /* warning if back again */ fputs(m, stderr); /* prompt */ fflush(stderr); i = 0; do { /* read line, keeping n */ if ((c = (char)getch()) == '\r') c = '\n'; if (i < n) p[i++] = c; } while (c != '\n'); PUTC('\n', stderr); fflush(stderr); w = "(line too long--try again)\n"; } while (p[i-1] != '\n'); p[i-1] = 0; /* terminate at newline */ /* return pointer to password */ return p;}#endif /* DOS_NT_OS2 */#ifdef MACOSchar *getp(m, p, n) char *m; /* prompt for password */ char *p; /* return value: line input */ int n; /* bytes available in p[] */{ WindowPtr whichWindow; EventRecord theEvent; char c; /* one-byte buffer for read() to use */ int i; /* number of characters input */ char *w; /* warning on retry */ /* get password */ w = ""; do { fputs(w, stderr); /* warning if back again */ fputs(m, stderr); /* prompt */ i = 0; do { /* read line, keeping n */ do { SystemTask(); if (!GetNextEvent(everyEvent, &theEvent)) theEvent.what = nullEvent; else { switch (theEvent.what) { case keyDown: c = theEvent.message & charCodeMask; break; case mouseDown: if (FindWindow(theEvent.where, &whichWindow) == inSysWindow) SystemClick(&theEvent, whichWindow); break; case updateEvt:#ifdef UNZIP screenUpdate((WindowPtr)theEvent.message);#endif break; } } } while (theEvent.what != keyDown); if (i < n) p[i++] = c; } while (c != '\r'); PUTC('\n', stderr); w = "(line too long--try again)\n"; } while (p[i-1] != '\r'); p[i-1] = 0; /* terminate at newline */ /* return pointer to password */ return p;}#endif /* MACOS */#if (defined(UNIX) || defined(__MINT__))char *getp(m, p, n) char *m; /* prompt for password */ char *p; /* return value: line input */ int n; /* bytes available in p[] */{ char c; /* one-byte buffer for read() to use */ int i; /* number of characters input */ char *w; /* warning on retry */ int f; /* file descriptor for tty device */#ifdef PASSWD_FROM_STDIN /* Read from stdin. This is unsafe if the password is stored on disk. */ f = 0;#else /* turn off echo on tty */ if (!isatty(2)) return NULL; /* error if not tty */ /* Convex C seems to want (char *) in front of ttyname: compiler bug? */ if ((f = open((char *)ttyname(2), 0)) == -1) return NULL;#endif /* get password */ w = ""; do { fputs(w, stderr); /* warning if back again */ fputs(m, stderr); /* prompt */ fflush(stderr); i = 0; echoff(f); do { /* read line, keeping n */ read(f, &c, 1); if (i < n) p[i++] = c; } while (c != '\n'); echon(); PUTC('\n', stderr); fflush(stderr); w = "(line too long--try again)\n"; } while (p[i-1] != '\n'); p[i-1] = 0; /* terminate at newline */#ifndef PASSWD_FROM_STDIN close(f);#endif /* return pointer to password */ return p;}#endif /* UNIX || __MINT__ */#ifdef VMSchar *getp(m, p, n) char *m; /* prompt for password */ char *p; /* return value: line input */ int n; /* bytes available in p[] */{ char c; /* one-byte buffer for read() to use */ int i; /* number of characters input */ char *w; /* warning on retry */ /* get password */ w = ""; do { if (*w) /* bug: VMS adds \n to NULL fputs (apparently) */ fputs(w, stderr); /* warning if back again */ fputs(m, stderr); /* prompt */ fflush(stderr); i = 0; echoff(f); do { /* read line, keeping n */ if ((c = (char)getch()) == '\r') c = '\n'; if (i < n) p[i++] = c; } while (c != '\n'); echon(); PUTC('\n', stderr); fflush(stderr); w = "(line too long--try again)\n"; } while (p[i-1] != '\n'); p[i-1] = 0; /* terminate at newline */ /* return pointer to password */ return p;}#endif /* VMS */#if (defined(UNZIP) && !defined(FUNZIP))/*********************************************************************** * Get the password and set up keys for current zipfile member. Return * PK_ class error. */int decrypt(){ ush b; int n, r; static int nopwd=FALSE; char *m, *prompt; uch h[RAND_HEAD_LEN]; Trace((stdout, "\n[incnt = %d]: ", incnt)); /* get header once (turn off "encrypted" flag temporarily so we don't * try to decrypt the same data twice) */ pInfo->encrypted = FALSE; for (n = 0; n < RAND_HEAD_LEN; n++) { b = NEXTBYTE; h[n] = (uch)b; Trace((stdout, " (%02x)", h[n])); } pInfo->encrypted = TRUE; if (newzip) { /* this is first encrypted member in this zipfile */ newzip = FALSE; if (key) { /* get rid of previous zipfile's key */ free(key); key = (char *)NULL; } } /* if have key already, test it; else allocate memory for it */ if (key) { if (!testp(h)) return PK_COOL; /* existing password OK (else prompt for new) */ else if (nopwd) return PK_WARN; /* user indicated no more prompting */ } else if ((key = (char *)malloc(PWLEN+1)) == (char *)NULL) return PK_MEM2; if ((prompt = (char *)malloc(FILNAMSIZ+15)) != (char *)NULL) { sprintf(prompt, "[%s] %s password: ", zipfn, filename); m = prompt; } else m = "Enter password: "; /* try a few keys */ for (r = 0; r < 3; ++r) { m = getp(m, key, PWLEN+1); if (prompt != (char *)NULL) { free(prompt); prompt = (char *)NULL; } if (m == (char *)NULL) return PK_MEM2; if (!testp(h)) return PK_COOL; if (*key == '\0') { nopwd = TRUE; return PK_WARN; } m = "password incorrect--reenter: "; } return PK_WARN;} /* end function decrypt() *//*********************************************************************** * Test the password. Return -1 if bad, 0 if OK. */local int testp(h) uch *h;{ ush b, c; int n; uch *p; uch hh[RAND_HEAD_LEN]; /* decrypted header */ /* set keys and save the encrypted header */ init_keys(key); memcpy(hh, h, RAND_HEAD_LEN); /* check password */ for (n = 0; n < RAND_HEAD_LEN; n++) { zdecode(hh[n]); Trace((stdout, " %02x", hh[n])); } c = hh[RAND_HEAD_LEN-2], b = hh[RAND_HEAD_LEN-1]; Trace((stdout, "\n lrec.crc= %08lx crec.crc= %08lx pInfo->ExtLocHdr= %s\n", lrec.crc32, pInfo->crc, pInfo->ExtLocHdr? "true":"false")); Trace((stdout, " incnt = %d unzip offset into zipfile = %ld\n", incnt, cur_zipfile_bufstart+(inptr-inbuf))); /* same test as in zipbare(): */#ifdef ZIP10 /* check two bytes */ Trace((stdout, " (c | (b<<8)) = %04x (crc >> 16) = %04x lrec.time = %04x\n", (ush)(c | (b<<8)), (ush)(lrec.crc32 >> 16), lrec.last_mod_file_time)); if ((ush)(c | (b<<8)) != (pInfo->ExtLocHdr? lrec.last_mod_file_time : (ush)(lrec.crc32 >> 16))) return -1; /* bad */#else Trace((stdout, " b = %02x (crc >> 24) = %02x (lrec.time >> 8) = %02x\n", b, (ush)(lrec.crc32 >> 24), (lrec.last_mod_file_time >> 8))); if (b != (pInfo->ExtLocHdr? lrec.last_mod_file_time >> 8 : (ush)(lrec.crc32 >> 24))) return -1; /* bad */ c++; /* avoid warning on unused variable */#endif /* password OK: decrypt current buffer contents before leaving */ for (n = (long)incnt > csize ? (int)csize : incnt, p = inptr; n--; p++) zdecode(*p); return 0; /* OK */} /* end function testp() */#endif /* UNZIP && !FUNZIP */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -