- Merged back bugfixes from trunk (pre 0.99-pre2):
    * Corrected parsing of UTCTime dates before 1990 and after 1950
    * Support more exotic OID's when parsing certificates
    * Support more exotic name representations when parsing certificates
    * Replaced the expired test certificates
    * Do not bail out if no client certificate specified. Try to negotiate anonymous connection (Fixes ticket #12)


diff --git a/library/x509parse.c b/library/x509parse.c
index ea9748c..31cfe34 100644
--- a/library/x509parse.c
+++ b/library/x509parse.c
@@ -269,9 +269,6 @@
 }
 
 /*
- *  RelativeDistinguishedName ::=
- *    SET OF AttributeTypeAndValue
- *
  *  AttributeTypeAndValue ::= SEQUENCE {
  *    type     AttributeType,
  *    value    AttributeValue }
@@ -280,30 +277,18 @@
  *
  *  AttributeValue ::= ANY DEFINED BY AttributeType
  */
-static int x509_get_name( unsigned char **p,
-                          const unsigned char *end,
-                          x509_name *cur )
+static int x509_get_attr_type_value( unsigned char **p,
+                                     const unsigned char *end,
+                                     x509_name *cur )
 {
     int ret, len;
-    const unsigned char *end2;
     x509_buf *oid;
     x509_buf *val;
 
     if( ( ret = asn1_get_tag( p, end, &len,
-            ASN1_CONSTRUCTED | ASN1_SET ) ) != 0 )
-        return( POLARSSL_ERR_X509_CERT_INVALID_NAME | ret );
-
-    end2 = end;
-    end  = *p + len;
-
-    if( ( ret = asn1_get_tag( p, end, &len,
             ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
         return( POLARSSL_ERR_X509_CERT_INVALID_NAME | ret );
 
-    if( *p + len != end )
-        return( POLARSSL_ERR_X509_CERT_INVALID_NAME |
-                POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
-
     oid = &cur->oid;
     oid->tag = **p;
 
@@ -334,9 +319,56 @@
 
     cur->next = NULL;
 
-    if( *p != end )
-        return( POLARSSL_ERR_X509_CERT_INVALID_NAME |
-                POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
+    return( 0 );
+}
+
+/*
+ *  RelativeDistinguishedName ::=
+ *    SET OF AttributeTypeAndValue
+ *
+ *  AttributeTypeAndValue ::= SEQUENCE {
+ *    type     AttributeType,
+ *    value    AttributeValue }
+ *
+ *  AttributeType ::= OBJECT IDENTIFIER
+ *
+ *  AttributeValue ::= ANY DEFINED BY AttributeType
+ */
+static int x509_get_name( unsigned char **p,
+                          const unsigned char *end,
+                          x509_name *cur )
+{
+    int ret, len;
+    const unsigned char *end2;
+    x509_name *use; 
+    
+    if( ( ret = asn1_get_tag( p, end, &len,
+            ASN1_CONSTRUCTED | ASN1_SET ) ) != 0 )
+        return( POLARSSL_ERR_X509_CERT_INVALID_NAME | ret );
+
+    end2 = end;
+    end  = *p + len;
+    use = cur;
+
+    do
+    {
+        if( ( ret = x509_get_attr_type_value( p, end, use ) ) != 0 )
+            return( ret );
+        
+        if( *p != end )
+        {
+            use->next = (x509_name *) malloc(
+                    sizeof( x509_name ) );
+
+            if( use->next == NULL )
+                return( 1 );
+            
+            memset( use->next, 0, sizeof( x509_name ) );
+
+            use = use->next;
+        }
+    }
+    while( *p != end );
 
     /*
      * recurse until end of SEQUENCE is reached
@@ -388,7 +420,7 @@
                     &time->hour, &time->min, &time->sec ) < 5 )
             return( POLARSSL_ERR_X509_CERT_INVALID_DATE );
 
-        time->year +=  100 * ( time->year < 90 );
+        time->year +=  100 * ( time->year < 50 );
         time->year += 1900;
 
         *p += len;
@@ -462,7 +494,7 @@
                             x509_buf *pk_alg_oid,
                             mpi *N, mpi *E )
 {
-    int ret, len;
+    int ret, len, can_handle;
     unsigned char *end2;
 
     if( ( ret = x509_get_alg( p, end, pk_alg_oid ) ) != 0 )
@@ -471,8 +503,27 @@
     /*
      * only RSA public keys handled at this time
      */
-    if( pk_alg_oid->len != 9 ||
-        memcmp( pk_alg_oid->p, OID_PKCS1_RSA, 9 ) != 0 )
+    can_handle = 0;
+
+    if( pk_alg_oid->len == 9 &&
+        memcmp( pk_alg_oid->p, OID_PKCS1_RSA, 9 ) == 0 )
+        can_handle = 1;
+
+    if( pk_alg_oid->len == 9 &&
+        memcmp( pk_alg_oid->p, OID_PKCS1, 8 ) == 0 )
+    {
+        if( pk_alg_oid->p[8] >= 2 && pk_alg_oid->p[8] <= 5 )
+            can_handle = 1;
+
+        if ( pk_alg_oid->p[8] >= 11 && pk_alg_oid->p[8] <= 14 )
+            can_handle = 1;
+    }
+
+    if( pk_alg_oid->len == 5 &&
+        memcmp( pk_alg_oid->p, OID_RSA_SHA_OBS, 5 ) == 0 )
+        can_handle = 1;
+
+    if( can_handle == 0 )
         return( POLARSSL_ERR_X509_CERT_UNKNOWN_PK_ALG );
 
     if( ( ret = asn1_get_tag( p, end, &len, ASN1_BIT_STRING ) ) != 0 )
@@ -811,6 +862,12 @@
 
         return( POLARSSL_ERR_X509_CERT_UNKNOWN_SIG_ALG );
     }
+    if( sig_oid->len == 5 &&
+        memcmp( sig_oid->p, OID_RSA_SHA_OBS, 5 ) == 0 )
+    {
+        *sig_alg = SIG_RSA_SHA1;
+        return( 0 );
+    }
 
     return( POLARSSL_ERR_X509_CERT_UNKNOWN_SIG_ALG );
 }
@@ -2561,6 +2618,7 @@
     ret = x509parse_verify( &clicert, &cacert, NULL, "PolarSSL Client 2", &i );
     if( ret != 0 )
     {
+        printf("%02x", i);
         if( verbose != 0 )
             printf( "failed\n" );