1
/* This Source Code Form is subject to the terms of the Mozilla Public
2
* License, v. 2.0. If a copy of the MPL was not distributed with this
3
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8
* Routines used in signing archives.
19
typedef void (*ETVoidPtrFunc) (void * data);
21
/* key database wrapper */
22
/* static SECKEYKeyDBHandle *jar_open_key_database (void); */
23
/* CHUNQ is our bite size */
26
#define FILECHUNQ 32768
29
* J A R _ c a l c u l a t e _ d i g e s t
31
* Quick calculation of a digest for
32
* the specified block of memory. Will calculate
33
* for all supported algorithms, now MD5.
35
* This version supports huge pointers for WIN16.
38
JAR_Digest * PR_CALLBACK
39
JAR_calculate_digest(void *data, long length)
42
PK11Context *sha1 = 0;
43
JAR_Digest *dig = PORT_ZNew(JAR_Digest);
45
unsigned int md5_length, sha1_length;
48
/* out of memory allocating digest */
52
md5 = PK11_CreateDigestContext(SEC_OID_MD5);
53
sha1 = PK11_CreateDigestContext(SEC_OID_SHA1);
56
PK11_DigestBegin (md5);
57
PK11_DigestBegin (sha1);
62
PK11_DigestOp(md5, (unsigned char*)data, chunq);
63
PK11_DigestOp(sha1, (unsigned char*)data, chunq);
65
data = ((char *) data + chunq);
69
PK11_DigestFinal (md5, dig->md5, &md5_length, MD5_LENGTH);
70
PK11_DigestFinal (sha1, dig->sha1, &sha1_length, SHA1_LENGTH);
72
PK11_DestroyContext (md5, PR_TRUE);
73
PK11_DestroyContext (sha1, PR_TRUE);
79
* J A R _ d i g e s t _ f i l e
81
* Calculates the MD5 and SHA1 digests for a file
82
* present on disk, and returns these in JAR_Digest struct.
86
JAR_digest_file (char *filename, JAR_Digest *dig)
90
PK11Context *sha1 = 0;
91
unsigned char *buf = (unsigned char *) PORT_ZAlloc (FILECHUNQ);
93
unsigned int md5_length, sha1_length;
97
return JAR_ERR_MEMORY;
100
if ((fp = JAR_FOPEN (filename, "rb")) == 0) {
101
/* perror (filename); FIX XXX XXX XXX XXX XXX XXX */
106
md5 = PK11_CreateDigestContext (SEC_OID_MD5);
107
sha1 = PK11_CreateDigestContext (SEC_OID_SHA1);
109
if (md5 == NULL || sha1 == NULL) {
110
/* can't generate digest contexts */
113
return JAR_ERR_GENERAL;
116
PK11_DigestBegin (md5);
117
PK11_DigestBegin (sha1);
120
if ((num = JAR_FREAD (fp, buf, FILECHUNQ)) == 0)
123
PK11_DigestOp (md5, buf, num);
124
PK11_DigestOp (sha1, buf, num);
127
PK11_DigestFinal (md5, dig->md5, &md5_length, MD5_LENGTH);
128
PK11_DigestFinal (sha1, dig->sha1, &sha1_length, SHA1_LENGTH);
130
PK11_DestroyContext (md5, PR_TRUE);
131
PK11_DestroyContext (sha1, PR_TRUE);
140
* J A R _ o p e n _ k e y _ d a t a b a s e
145
jar_open_key_database(void)
151
jar_close_key_database(void *keydb)
153
/* We never do close it */
159
* j a r _ c r e a t e _ p k 7
163
static void jar_pk7_out (void *arg, const char *buf, unsigned long len)
165
JAR_FWRITE ((JAR_FILE) arg, buf, len);
169
jar_create_pk7(CERTCertDBHandle *certdb, void *keydb, CERTCertificate *cert,
170
char *password, JAR_FILE infp, JAR_FILE outfp)
172
SEC_PKCS7ContentInfo *cinfo;
173
const SECHashObject *hashObj;
181
unsigned char digestdata[32];
182
unsigned char buffer[4096];
184
if (outfp == NULL || infp == NULL || cert == NULL)
185
return JAR_ERR_GENERAL;
187
/* we sign with SHA */
188
hashObj = HASH_GetHashObject(HASH_AlgSHA1);
190
hashcx = (* hashObj->create)();
192
return JAR_ERR_GENERAL;
194
(* hashObj->begin)(hashcx);
196
int nb = JAR_FREAD(infp, buffer, sizeof buffer);
197
if (nb == 0) { /* eof */
200
(* hashObj->update) (hashcx, buffer, nb);
202
(* hashObj->end)(hashcx, digestdata, &len, 32);
203
(* hashObj->destroy)(hashcx, PR_TRUE);
205
digest.data = digestdata;
208
/* signtool must use any old context it can find since it's
209
calling from inside javaland. */
211
cinfo = SEC_PKCS7CreateSignedData(cert, certUsageObjectSigner, NULL,
212
SEC_OID_SHA1, &digest, NULL, mw);
216
rv = SEC_PKCS7IncludeCertChain(cinfo, NULL);
217
if (rv != SECSuccess) {
218
status = PORT_GetError();
219
SEC_PKCS7DestroyContentInfo(cinfo);
223
/* Having this here forces signtool to always include signing time. */
224
rv = SEC_PKCS7AddSigningTime(cinfo);
225
/* don't check error */
228
/* if calling from mozilla thread*/
229
rv = SEC_PKCS7Encode(cinfo, jar_pk7_out, outfp, NULL, NULL, mw);
230
if (rv != SECSuccess)
231
status = PORT_GetError();
232
SEC_PKCS7DestroyContentInfo (cinfo);
233
if (rv != SECSuccess) {
234
errstring = JAR_get_error (status);
235
return ((status < 0) ? status : JAR_ERR_GENERAL);