Added generic API for date range validation (with callbacks).
[BearSSL] / src / ec / ecdsa_atr.c
index 91a1d0c..3a11226 100644 (file)
@@ -33,6 +33,11 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
         * deviations to DER with regards to minimality of encoding of
         * lengths and integer values. These deviations are still
         * unambiguous.
         * deviations to DER with regards to minimality of encoding of
         * lengths and integer values. These deviations are still
         * unambiguous.
+        *
+        * Signature format is a SEQUENCE of two INTEGER values. We
+        * support only integers of less than 127 bytes each (signed
+        * encoding) so the resulting raw signature will have length
+        * at most 254 bytes.
         */
 
        unsigned char *buf, *r, *s;
         */
 
        unsigned char *buf, *r, *s;
@@ -43,9 +48,20 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
        if (sig_len < 8) {
                return 0;
        }
        if (sig_len < 8) {
                return 0;
        }
+
+       /*
+        * First byte is SEQUENCE tag.
+        */
        if (buf[0] != 0x30) {
                return 0;
        }
        if (buf[0] != 0x30) {
                return 0;
        }
+
+       /*
+        * The SEQUENCE length will be encoded over one or two bytes. We
+        * limit the total SEQUENCE contents to 255 bytes, because it
+        * makes things simpler; this is enough for subgroup orders up
+        * to 999 bits.
+        */
        zlen = buf[1];
        if (zlen > 0x80) {
                if (zlen != 0x81) {
        zlen = buf[1];
        if (zlen > 0x80) {
                if (zlen != 0x81) {
@@ -62,6 +78,10 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
                }
                off = 2;
        }
                }
                off = 2;
        }
+
+       /*
+        * First INTEGER (r).
+        */
        if (buf[off ++] != 0x02) {
                return 0;
        }
        if (buf[off ++] != 0x02) {
                return 0;
        }
@@ -71,6 +91,10 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
        }
        r = buf + off;
        off += rlen;
        }
        r = buf + off;
        off += rlen;
+
+       /*
+        * Second INTEGER (s).
+        */
        if (off + 2 > sig_len) {
                return 0;
        }
        if (off + 2 > sig_len) {
                return 0;
        }
@@ -83,6 +107,9 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
        }
        s = buf + off;
 
        }
        s = buf + off;
 
+       /*
+        * Removing leading zeros from r and s.
+        */
        while (rlen > 0 && *r == 0) {
                rlen --;
                r ++;
        while (rlen > 0 && *r == 0) {
                rlen --;
                r ++;
@@ -92,6 +119,11 @@ br_ecdsa_asn1_to_raw(void *sig, size_t sig_len)
                s ++;
        }
 
                s ++;
        }
 
+       /*
+        * Compute common length for the two integers, then copy integers
+        * into the temporary buffer, and finally copy it back over the
+        * signature buffer.
+        */
        zlen = rlen > slen ? rlen : slen;
        sig_len = zlen << 1;
        memset(tmp, 0, sig_len);
        zlen = rlen > slen ? rlen : slen;
        sig_len = zlen << 1;
        memset(tmp, 0, sig_len);