verify.c
上传用户:lyxiangda
上传日期:2007-01-12
资源大小:3042k
文件大小:9k
源码类别:

CA认证

开发平台:

WINDOWS

  1. /*
  2.  * The contents of this file are subject to the Mozilla Public
  3.  * License Version 1.1 (the "License"); you may not use this file
  4.  * except in compliance with the License. You may obtain a copy of
  5.  * the License at http://www.mozilla.org/MPL/
  6.  * 
  7.  * Software distributed under the License is distributed on an "AS
  8.  * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
  9.  * implied. See the License for the specific language governing
  10.  * rights and limitations under the License.
  11.  * 
  12.  * The Original Code is the Netscape security libraries.
  13.  * 
  14.  * The Initial Developer of the Original Code is Netscape
  15.  * Communications Corporation.  Portions created by Netscape are 
  16.  * Copyright (C) 1994-2000 Netscape Communications Corporation.  All
  17.  * Rights Reserved.
  18.  * 
  19.  * Contributor(s):
  20.  * 
  21.  * Alternatively, the contents of this file may be used under the
  22.  * terms of the GNU General Public License Version 2 or later (the
  23.  * "GPL"), in which case the provisions of the GPL are applicable 
  24.  * instead of those above.  If you wish to allow use of your 
  25.  * version of this file only under the terms of the GPL and not to
  26.  * allow others to use your version of this file under the MPL,
  27.  * indicate your decision by deleting the provisions above and
  28.  * replace them with the notice and other provisions required by
  29.  * the GPL.  If you do not delete the provisions above, a recipient
  30.  * may use your version of this file under either the MPL or the
  31.  * GPL.
  32.  */
  33. #include "signtool.h"
  34. static int jar_cb(int status, JAR *jar, const char *metafile, 
  35.              char *pathname, char *errortext);
  36. static int verify_global (JAR *jar);
  37. /*************************************************************************
  38.  *
  39.  * V e r i f y J a r
  40.  */
  41. int
  42. VerifyJar(char *filename)
  43. {
  44.   FILE *fp;
  45.   int ret;
  46.   int status;
  47.   char *err;
  48.   JAR *jar;
  49.   JAR_Context *ctx;
  50.   JAR_Item *it;
  51.   jar = JAR_new();
  52.   if ((fp = fopen (filename, "r")) == NULL)
  53.     {
  54.     perror (filename);
  55.     exit (ERRX);
  56.     }
  57.   else
  58.     fclose (fp);
  59.   JAR_set_callback (JAR_CB_SIGNAL, jar, jar_cb);
  60.   status = JAR_pass_archive (jar, jarArchGuess, filename, "some-url");
  61.   if (status < 0 || jar->valid < 0)
  62.     {
  63.     PR_fprintf(outputFD, "nNOTE -- "%s" archive DID NOT PASS crypto verification.n", filename);
  64.     if (status < 0)
  65.       {
  66.       char *errtext;
  67.       if (status >= JAR_BASE && status <= JAR_BASE_END)
  68.         {
  69.         errtext = JAR_get_error (status);
  70.         }
  71.       else
  72.         {
  73.         errtext = SECU_ErrorString ((int16) PORT_GetError());
  74.         }
  75.       PR_fprintf(outputFD, "  (reported reason: %s)nn", errtext);
  76.  
  77.       /* corrupt files should not have their contents listed */ 
  78.       if (status == JAR_ERR_CORRUPT)
  79.         return status;
  80.       }
  81.     PR_fprintf(outputFD,
  82. "entries shown below will have their digests checked only.n"); 
  83.     jar->valid = 0;
  84.     }
  85.   else
  86.     PR_fprintf(outputFD,
  87. "archive "%s" has passed crypto verification.n", filename);
  88.   verify_global (jar);
  89.   PR_fprintf(outputFD, "n");
  90.   PR_fprintf(outputFD, "%16s   %sn", "status", "path");
  91.   PR_fprintf(outputFD, "%16s   %sn", "------------", "-------------------");
  92.   ctx = JAR_find (jar, NULL, jarTypeMF);
  93.   while (JAR_find_next (ctx, &it) >= 0)
  94.     {
  95.     if (it && it->pathname)
  96.       {
  97. rm_dash_r(TMP_OUTPUT);
  98.       ret = JAR_verified_extract (jar, it->pathname, TMP_OUTPUT);
  99.       /* if (ret < 0) printf ("error %d on %sn", ret, it->pathname); */
  100.       if (ret == JAR_ERR_PNF)
  101.         err = "NOT PRESENT";
  102.       else if (ret == JAR_ERR_HASH)
  103.         err = "HASH FAILED";
  104.       else
  105.         err = "NOT VERIFIED";
  106.       PR_fprintf(outputFD, "%16s   %sn", 
  107.         ret >= 0 ? "verified" : err, it->pathname);
  108.       if (ret != 0 && ret != JAR_ERR_PNF && ret != JAR_ERR_HASH)
  109.         PR_fprintf(outputFD, "      (reason: %s)n", JAR_get_error (ret));
  110.       }
  111.     }
  112.   JAR_find_end (ctx);
  113.   if (status < 0 || jar->valid < 0)
  114.     {
  115.     PR_fprintf(outputFD,
  116. "nNOTE -- "%s" archive DID NOT PASS crypto verification.n", filename);
  117.     give_help (status);
  118.     }
  119.   JAR_destroy (jar);
  120.   return 0;
  121. }
  122. /***************************************************************************
  123.  *
  124.  * v e r i f y _ g l o b a l
  125.  */
  126. static int
  127. verify_global (JAR *jar)
  128. {
  129.   FILE *fp;
  130.   JAR_Context *ctx;
  131.   char *ext;
  132.   JAR_Item *it;
  133.   JAR_Digest *globaldig;
  134.   unsigned int sha1_length, md5_length;
  135.   char buf [BUFSIZ];
  136.   unsigned char *md5_digest, *sha1_digest;
  137.   ctx = JAR_find (jar, "*", jarTypePhy);
  138.   while (JAR_find_next (ctx, &it) >= 0) {
  139.     if (!PORT_Strncmp (it->pathname, "META-INF", 8)) {
  140.       for (ext = it->pathname; *ext; ext++);
  141.       while (ext > it->pathname && *ext != '.') ext--;
  142. if(verbosity >= 0) {
  143. if (!PORT_Strcasecmp (ext, ".rsa")) {
  144. PR_fprintf(outputFD, "found a RSA signature file: %sn",
  145.   it->pathname);
  146. }
  147. if(!PORT_Strcasecmp (ext, ".dsa")) {
  148. PR_fprintf(outputFD, "found a DSA signature file: %sn",
  149.   it->pathname);
  150. }
  151. if (!PORT_Strcasecmp (ext, ".mf")) {
  152. PR_fprintf(outputFD,
  153.   "found a MF master manifest file: %sn", it->pathname);
  154. }
  155. }
  156. if (!PORT_Strcasecmp (ext, ".sf")) {
  157. if(verbosity >= 0) {
  158. PR_fprintf(outputFD,
  159.   "found a SF signature manifest file: %sn", it->pathname);
  160. }
  161. rm_dash_r(TMP_OUTPUT);
  162. if (JAR_extract (jar, it->pathname, TMP_OUTPUT) < 0) {
  163. PR_fprintf(errorFD, "%s: error extracting %sn", PROGRAM_NAME,
  164.   it->pathname);
  165. errorCount++;
  166. continue;
  167. }
  168. md5_digest = NULL;
  169. sha1_digest = NULL;
  170. if ((fp = fopen (TMP_OUTPUT, "rb")) != NULL) {
  171. while (fgets (buf, BUFSIZ, fp)) {
  172. char *s;
  173. if (*buf == 0 || *buf == 'n' || *buf == 'r') break;
  174. for (s = buf; *s && *s != 'n' && *s != 'r'; s++);
  175. *s = 0;
  176. if (!PORT_Strncmp (buf, "MD5-Digest: ", 12)) {
  177. md5_digest = ATOB_AsciiToData (buf + 12, &md5_length);
  178. }
  179. if (!PORT_Strncmp (buf, "SHA1-Digest: ", 13)) {
  180. sha1_digest = ATOB_AsciiToData (buf + 13, &sha1_length);
  181. }
  182. if (!PORT_Strncmp (buf, "SHA-Digest: ", 12)) {
  183. sha1_digest = ATOB_AsciiToData (buf + 12, &sha1_length);
  184. }
  185. }
  186. globaldig = jar->globalmeta;
  187. if (globaldig && md5_digest) {
  188. if(verbosity >= 0) {
  189. PR_fprintf(outputFD,
  190.   "  md5 digest on global metainfo: %sn", 
  191.   PORT_Memcmp (md5_digest, globaldig->md5, MD5_LENGTH) ?
  192.   "no match" : "match");
  193. }
  194. }
  195. if (globaldig && sha1_digest) {
  196. if(verbosity >= 0) {
  197. PR_fprintf(outputFD,
  198.   "  sha digest on global metainfo: %sn", 
  199.   PORT_Memcmp(sha1_digest, globaldig->sha1,
  200.   SHA1_LENGTH) ? "no match" : "match");
  201. }
  202. }
  203. if (globaldig == NULL) {
  204. if(verbosity >= 0) {
  205. PR_fprintf(outputFD,
  206.   "global metadigest is not available, strange.n");
  207. }
  208. }
  209. fclose (fp);
  210. }
  211. }
  212. }
  213.   }
  214.   JAR_find_end (ctx);
  215.   return 0;
  216. }
  217. /************************************************************************
  218.  *
  219.  * J a r W h o
  220.  */
  221. void
  222. JarWho(char *filename)
  223.   {
  224.   FILE *fp;
  225.   JAR *jar;
  226.   JAR_Context *ctx;
  227.   int status;
  228.   JAR_Item *it;
  229.   JAR_Cert *fing;
  230.   CERTCertificate *cert, *prev = NULL;
  231.   jar = JAR_new();
  232.   if ((fp = fopen (filename, "r")) == NULL)
  233.     {
  234.     perror (filename);
  235.     exit (ERRX);
  236.     }
  237.   else
  238.     fclose (fp);
  239.   status = JAR_pass_archive (jar, jarArchGuess, filename, "some-url");
  240.   if (status < 0 || jar->valid < 0)
  241.     {
  242.     PR_fprintf(outputFD,
  243. "NOTE -- "%s" archive DID NOT PASS crypto verification.n", filename);
  244.     if (jar->valid < 0 || status != -1)
  245.       {
  246.       char *errtext;
  247.       if (status >= JAR_BASE && status <= JAR_BASE_END)
  248.         {
  249.         errtext = JAR_get_error (status);
  250.         }
  251.       else
  252.         {
  253.         errtext = SECU_ErrorString ((int16) PORT_GetError());
  254.         }
  255.       PR_fprintf(outputFD, "  (reported reason: %s)nn", errtext);
  256.       }
  257.     }
  258.   PR_fprintf(outputFD, "nSigner information:nn");
  259.   ctx = JAR_find (jar, NULL, jarTypeSign);
  260.   while (JAR_find_next (ctx, &it) >= 0)
  261.     {
  262.     fing = (JAR_Cert *) it->data;
  263.     cert = fing->cert;
  264.     if (cert)
  265.       {
  266.       if (prev == cert)
  267.         break;
  268.       if (cert->nickname) 
  269.         PR_fprintf(outputFD, "nickname: %sn", cert->nickname);
  270.       if (cert->subjectName)
  271.         PR_fprintf(outputFD, "subject name: %sn", cert->subjectName);
  272.       if (cert->issuerName)
  273.         PR_fprintf(outputFD, "issuer name: %sn", cert->issuerName);
  274.       }
  275.     else
  276.       PR_fprintf(outputFD, "no certificate could be foundn");
  277.     prev = cert;
  278.     }
  279.   JAR_find_end (ctx);
  280.   JAR_destroy (jar);
  281. }
  282. /************************************************************************
  283.  * j a r _ c b
  284.  */
  285. static int jar_cb(int status, JAR *jar, const char *metafile,
  286.              char *pathname, char *errortext)
  287. {
  288.   PR_fprintf(errorFD, "error %d: %s IN FILE %sn", status, errortext, pathname);
  289. errorCount++;
  290.   return 0;
  291. }