aboutsummaryrefslogtreecommitdiff
path: root/src/cmd/auth/factotum/pkcs1.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/auth/factotum/pkcs1.c')
-rw-r--r--src/cmd/auth/factotum/pkcs1.c57
1 files changed, 53 insertions, 4 deletions
diff --git a/src/cmd/auth/factotum/pkcs1.c b/src/cmd/auth/factotum/pkcs1.c
index fb35ce83..f3278454 100644
--- a/src/cmd/auth/factotum/pkcs1.c
+++ b/src/cmd/auth/factotum/pkcs1.c
@@ -36,7 +36,7 @@ rsasign(RSApriv *key, DigestAlg *hash, uchar *digest, uint dlen,
/*
* Create number to sign.
*/
- len = (mpsignif(key->pub.n)+7)/8;
+ len = (mpsignif(key->pub.n)+7)/8 - 1;
if(len < n+2){
werrstr("rsa key too short");
return -1;
@@ -65,9 +65,41 @@ rsasign(RSApriv *key, DigestAlg *hash, uchar *digest, uint dlen,
mpfree(m);
if(s == nil)
return -1;
- mptoberjust(s, sig, len);
+ mptoberjust(s, sig, len+1);
mpfree(s);
- return len;
+ return len+1;
+}
+
+int
+rsaverify(RSApub *key, DigestAlg *hash, uchar *digest, uint dlen,
+ uchar *sig, uint siglen)
+{
+ uchar asn1[64], xasn1[64];
+ int n, nn;
+ mpint *m, *s;
+
+ /*
+ * Create ASN.1
+ */
+ n = mkasn1(asn1, hash, digest, dlen);
+
+ /*
+ * Extract plaintext of signature.
+ */
+ s = betomp(sig, siglen, nil);
+ if(s == nil)
+ return -1;
+ m = rsaencrypt(key, s, nil);
+ mpfree(s);
+ if(m == nil)
+ return -1;
+ nn = mptobe(m, xasn1, sizeof xasn1, nil);
+ mpfree(m);
+ if(n != nn || memcmp(asn1, xasn1, n) != 0){
+ werrstr("signature did not verify");
+ return -1;
+ }
+ return 0;
}
/*
@@ -116,6 +148,15 @@ uchar oidmd5[] = { O0(1, 2), O2(840), O3(113549), 2, 5 };
* digestAlgorithm AlgorithmIdentifier,
* digest OCTET STRING
* }
+ *
+ * except that OpenSSL seems to sign
+ *
+ * DigestInfo ::= SEQUENCE {
+ * SEQUENCE{ digestAlgorithm AlgorithmIdentifier, NULL }
+ * digest OCTET STRING
+ * }
+ *
+ * instead. Sigh.
*/
static int
mkasn1(uchar *asn1, DigestAlg *alg, uchar *d, uint dlen)
@@ -138,17 +179,25 @@ mkasn1(uchar *asn1, DigestAlg *alg, uchar *d, uint dlen)
*p++ = 0x30; /* sequence */
p++;
+ *p++ = 0x30; /* another sequence */
+ p++;
+
*p++ = 0x06; /* object id */
*p++ = olen;
memmove(p, obj, olen);
p += olen;
+ *p++ = 0x05; /* null */
+ *p++ = 0;
+
+ asn1[3] = p - (asn1+4); /* end of inner sequence */
+
*p++ = 0x04; /* octet string */
*p++ = dlen;
memmove(p, d, dlen);
p += dlen;
- asn1[1] = p - (asn1+2);
+ asn1[1] = p - (asn1+2); /* end of outer sequence */
return p-asn1;
}