Gerrit v d Hul wrote:
Hi list,

I've build OpenSSL version 0.9.7b on OS390 (zOS) with 'Configure OS390-Unix'

I want to check/read a CRL, but this gives a problem: the time values are not
given.

The command 'openssl crl -noout -text -in 5a5d2711.r0' gives:

Certificate Revocation List (CRL):
        Version 2 (0x1)
        Signature Algorithm: sha1WithRSAEncryption
        Issuer: /C=....
        Last Update: Bad time value
        Next Update: Bad time value
        CRL extensions:
[...]
>
The command 'Make test' also gives bad results (but I'm not sure this problem is
related to the 'Bad time value'-problem):

./md4test
test 1 ok
error calculating MD4 on 'a'
got 9d16e62335fbfc2946dd98546d5ca3e6 instead of bde52cb31de33e46245e05fbdbd6fb24
>[...]

I have tried to compile OpenSSL with the -0 option (no optimizations), but this gives the same bad results.

Any ideas?

Both problems are probably due to missing ASCII-EBCDIC conversions. I attach the EBCDIC patches which i have made so far for 0.9.7b. For the test programs i don't have a patch, but it should suffice to convert the appropriate text strings from EBCDIC to ASCII before computing the digests.
Please report whether the attached patches solve your first problem (i haven't tried them with CRLs).
Ciao,
Richard
--
Dr. Richard W. Könning
Fujitsu Siemens Computers GmbH
--- /home2/openssl/tmp/openssl-0.9.7a/apps/ca.c Thu Jan 30 18:37:35 2003
+++ apps/ca.c   Thu Mar 27 21:19:44 2003
@@ -3203,13 +3203,22 @@
        p=(char *)str->data;
        for (j=str->length; j>0; j--)
                {
+#ifdef CHARSET_EBCDIC
+               if ((*p >= 0x20) && (*p <= 0x7e))
+                       BIO_printf(bp,"%c",os_toebcdic[*p]);
+#else
                if ((*p >= ' ') && (*p <= '~'))
                        BIO_printf(bp,"%c",*p);
+#endif
                else if (*p & 0x80)
                        BIO_printf(bp,"\\0x%02X",*p);
                else if ((unsigned char)*p == 0xf7)
                        BIO_printf(bp,"^?");
+#ifdef CHARSET_EBCDIC
+               else    BIO_printf(bp,"^%c",os_toebcdic[*p+0x40]);
+#else
                else    BIO_printf(bp,"^%c",*p+'@');
+#endif
                p++;
                }
        BIO_printf(bp,"'\n");
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/a_print.c     Fri Dec  8 20:06:56 
2000
+++ crypto/asn1/a_print.c       Thu Mar 27 21:23:47 2003
@@ -72,27 +72,18 @@
        while ((*s) && (len-- != 0))
                {
                c= *(s++);
-#ifndef CHARSET_EBCDIC
-               if (!(  ((c >= 'a') && (c <= 'z')) ||
-                       ((c >= 'A') && (c <= 'Z')) ||
-                       (c == ' ') ||
-                       ((c >= '0') && (c <= '9')) ||
-                       (c == ' ') || (c == '\'') ||
-                       (c == '(') || (c == ')') ||
-                       (c == '+') || (c == ',') ||
-                       (c == '-') || (c == '.') ||
-                       (c == '/') || (c == ':') ||
-                       (c == '=') || (c == '?')))
-                       ia5=1;
                if (c&0x80)
+                       {
                        t61=1;
-#else
-               if (!isalnum(c) && (c != ' ') &&
-                   strchr("'()+,-./:=?", c) == NULL)
+                       break;
+                       }
+               if (!(  ((c > 0x40) && (c < 0x5b)) ||   /* AZ */
+                       ((c > 0x60) && (c < 0x7b)) ||   /* az */
+                       ((c > 0x2a) && (c < 0x3b)) ||   /* +,-./09: */
+                       (c == 0x20) || (c == 0x27) ||   /* SPC, ' */
+                       (c == 0x28) || (c == 0x29) ||   /* () */
+                       (c == 0x3d) || (c == 0x3f)))    /* =? */
                        ia5=1;
-               if (os_toascii[c] & 0x80)
-                       t61=1;
-#endif
                }
        if (t61) return(V_ASN1_T61STRING);
        if (ia5) return(V_ASN1_IA5STRING);
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/a_gentm.c     Fri Sep 28 02:44:44 
2001
+++ crypto/asn1/a_gentm.c       Tue Apr  1 19:51:52 2003
@@ -121,10 +121,18 @@
        static int max[9]={99, 99,12,31,23,59,59,12,59};
        char *a;
        int n,i,l,o;
+#ifdef CHARSET_EBCDIC
+
char a_e[17];
+#endif
 
        if (d->type != V_ASN1_GENERALIZEDTIME) return(0);
        l=d->length;
+#ifdef CHARSET_EBCDIC
+       ascii2ebcdic(a_e, d->data, l < 17 ? l : 17);
+       a = &a_e[0];
+#else
        a=(char *)d->data;
+#endif
        o=0;
        /* GENERALIZEDTIME is similar to UTCTIME except the year is
          * represented as YYYY. This stuff treats everything as a two digit
@@ -195,6 +203,10 @@
                        ASN1_STRING_set((ASN1_STRING *)s,
                                (unsigned char *)str,t.length);
                        s->type=V_ASN1_GENERALIZEDTIME;
+#ifdef CHARSET_EBCDIC
+/* Assume that str is an EBCDIC string. */
+                       ebcdic2ascii(s->data, s->data, s->length);
+#endif
                        }
                return(1);
                }
@@ -232,7 +244,7 @@
                ts->tm_mon+1,ts->tm_mday,ts->tm_hour,ts->tm_min,ts->tm_sec);
        s->length=strlen(p);
        s->type=V_ASN1_GENERALIZEDTIME;
-#ifdef CHARSET_EBCDIC_not
+#ifdef CHARSET_EBCDIC
        ebcdic2ascii(s->data, s->data, s->length);
 #endif
        return(s);
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/x509v3/v3_utl.c    Thu Nov 14 01:45:04 
2002
+++ crypto/x509v3/v3_utl.c      Fri Apr 25 19:39:02 2003
@@ -111,17 +111,45 @@
        OPENSSL_free(conf);
 }
 
+#ifdef CHARSET_EBCDIC
+static const char asc_true[] = {0x74, 0x72, 0x75, 0x65, 0x00};
+static const char asc_TRUE[] = {0x54, 0x52, 0x55, 0x45, 0x00};
+static const char asc_false[] = {0x66, 0x61, 0x6c, 0x73, 0x65, 0x00};
+static const char asc_FALSE[] = {0x46, 0x41, 0x4c, 0x53, 0x45, 0x00};
+static const char asc_yes[] = {0x79, 0x65, 0x73, 0x00};
+static const char asc_YES[] = {0x59, 0x45, 0x53, 0x00};
+static const char asc_y[] = {0x79, 0x00};
+static const char asc_Y[] = {0x59, 0x00};
+static const char asc_no[] = {0x6e, 0x6f, 0x00};
+static const char asc_NO[] = {0x4e, 0x4f, 0x00};
+static const char asc_n[] = {0x6e, 0x00};
+static const char asc_N[] = {0x4e, 0x00};
+#else
+static const char asc_true[] = "true";
+static const char asc_TRUE[] = "TRUE";
+static const char asc_false[] = "false";
+static const char asc_FALSE[] = "FALSE";
+static const char asc_yes[] = "yes";
+static const char asc_YES[] = "YES";
+static const char asc_y[] = "y";
+static const char asc_Y[] = "Y";
+static const char asc_no[] = "no";
+static const char asc_NO[] = "NO";
+static const char asc_n[] = "n";
+static const char asc_N[] = "N";
+#endif
+
 int X509V3_add_value_bool(const char *name, int asn1_bool,
                                                STACK_OF(CONF_VALUE) **extlist)
 {
-       if(asn1_bool) return X509V3_add_value(name, "TRUE", extlist);
-       return X509V3_add_value(name, "FALSE", extlist);
+       if(asn1_bool) return X509V3_add_value(name, asc_TRUE, extlist);
+       return X509V3_add_value(name, asc_FALSE, extlist);
 }
 
 int X509V3_add_value_bool_nf(char *name, int asn1_bool,
                                                STACK_OF(CONF_VALUE) **extlist)
 {
-       if(asn1_bool) return X509V3_add_value(name, "TRUE", extlist);
+       if(asn1_bool) return X509V3_add_value(name, asc_TRUE, extlist);
        return 1;
 }
 
@@ -207,14 +235,14 @@
 {
        char *btmp;
        if(!(btmp = value->value)) goto err;
-       if(!strcmp(btmp, "TRUE") || !strcmp(btmp, "true")
-                || !strcmp(btmp, "Y") || !strcmp(btmp, "y")
-               || !strcmp(btmp, "YES") || !strcmp(btmp, "yes")) {
+       if(!strcmp(btmp, asc_TRUE) || !strcmp(btmp, asc_true)
+                || !strcmp(btmp, asc_Y) || !strcmp(btmp, asc_y)
+               || !strcmp(btmp, asc_YES) || !strcmp(btmp, asc_yes)) {
                *asn1_bool = 0xff;
                return 1;
-       } else if(!strcmp(btmp, "FALSE") || !strcmp(btmp, "false")
-                || !strcmp(btmp, "N") || !strcmp(btmp, "n")
-               || !strcmp(btmp, "NO") || !strcmp(btmp, "no")) {
+       } else if(!strcmp(btmp, asc_FALSE) || !strcmp(btmp, asc_false)
+                || !strcmp(btmp, asc_N) || !strcmp(btmp, asc_n)
+               || !strcmp(btmp, asc_NO) || !strcmp(btmp, asc_no)) {
                *asn1_bool = 0;
                return 1;
        }
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/a_time.c      Fri Jan 24 01:42:50 
2003
+++ crypto/asn1/a_time.c        Tue Apr  1 19:52:06 2003
@@ -128,6 +128,15 @@
        {
        ASN1_GENERALIZEDTIME *ret;
        char *str;
+#ifdef CHARSET_EBCDIC
+
char five = '5';
+
char nineteen[3] = {'1', '9', '\0'};
+
char twenty[3] = {'2', '0', '\0'};
+
+
ebcdic2ascii(five, five, 1);
+
ebcdic2ascii(nineteen, nineteen, 2);
+
ebcdic2ascii(twenty, twenty, 2);
+#endif
 
        if (!ASN1_TIME_check(t)) return NULL;
 
@@ -152,8 +161,13 @@
                return NULL;
        str = (char *)ret->data;
        /* Work out the century and prepend */
+#ifdef CHARSET_EBCDIC
+       if (t->data[0] >= five) strcpy(str, nineteen);
+       else strcpy(str, twenty);
+#else
        if (t->data[0] >= '5') strcpy(str, "19");
        else strcpy(str, "20");
+#endif
 
        BUF_strlcat(str, (char *)t->data, t->length+3); /* Include space for a '\0' */
 
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/a_utctm.c     Wed Jun  5 15:47:15 
2002
+++ crypto/asn1/a_utctm.c       Wed Apr  2 16:04:42 2003
@@ -118,10 +118,18 @@
        static int max[8]={99,12,31,23,59,59,12,59};
        char *a;
        int n,i,l,o;
+#ifdef CHARSET_EBCDIC
+
char a_e[17];
+#endif
 
        if (d->type != V_ASN1_UTCTIME) return(0);
        l=d->length;
+#ifdef CHARSET_EBCDIC
+       ascii2ebcdic(a_e, d->data, l < 17 ? l : 17);
+       a = &a_e[0];
+#else
        a=(char *)d->data;
+#endif
        o=0;
 
        if (l < 11) goto err;
@@ -176,6 +184,10 @@
                        ASN1_STRING_set((ASN1_STRING *)s,
                                (unsigned char *)str,t.length);
                        s->type = V_ASN1_UTCTIME;
+#ifdef CHARSET_EBCDIC
+/* Assume that str is an EBCDIC string. */
+                       ebcdic2ascii(s->data, s->data, s->length);
+#endif
                        }
                return(1);
                }
@@ -212,7 +224,7 @@
                ts->tm_mon+1,ts->tm_mday,ts->tm_hour,ts->tm_min,ts->tm_sec);
        s->length=strlen(p);
        s->type=V_ASN1_UTCTIME;
-#ifdef CHARSET_EBCDIC_not
+#ifdef CHARSET_EBCDIC
        ebcdic2ascii(s->data, s->data, s->length);
 #endif
        return(s);
@@ -226,6 +238,25 @@
        int offset;
        int year;
 
+{/* RWK */
+int i;
+printf("cmp_time1: ");
+for (i = 0; i < s->length; i++)
+  printf("%02X", s->data[i]);
+printf("\n");
+}
+#ifdef CHARSET_EBCDIC
+
s = ASN1_STRING_dup(s);
+
ascii2ebcdic(s->data, s->data, s->length);
+#endif
+{/* RWK */
+int i;
+printf("cmp_time2: ");
+for (i = 0; i < s->length; i++)
+  printf("%02X", s->data[i]);
+printf(": %*.*s\n", s->length, s->length, s->data);
+}
+
 #define g2(p) (((p)[0]-'0')*10+(p)[1]-'0')
 
        if (s->data[12] == 'Z')
@@ -241,7 +272,11 @@
 
        tm = OPENSSL_gmtime(&t, &data);
        
+#ifdef CHARSET_EBCDIC
+#define return_cmp(a,b) if ((a)<(b)) {ASN1_STRING_free(s); return -1;} else if 
((a)>(b)) {ASN1_STRING_free(s); return 1;}
+#else
 #define return_cmp(a,b) if ((a)<(b)) return -1; else if ((a)>(b)) return 1
+#endif
        year = g2(s->data);
        if (year < 50)
                year += 100;
@@ -254,6 +289,9 @@
 #undef g2
 #undef return_cmp
 
+#ifdef CHARSET_EBCDIC
+
ASN1_STRING_free(s);
+#endif
        return 0;
        }
 
@@ -264,6 +302,11 @@
        struct tm tm;
        int offset;
 
+#ifdef CHARSET_EBCDIC
+
s = ASN1_STRING_dup(s);
+
ascii2ebcdic(s->data, s->data, s->length);
+#endif
+
        memset(&tm,'\0',sizeof tm);
 
 #define g2(p) (((p)[0]-'0')*10+(p)[1]-'0')
@@ -284,6 +327,10 @@
                        offset= -offset;
                }
 #undef g2
+
+#ifdef CHARSET_EBCDIC
+
ASN1_STRING_free(s);
+#endif
 
        return mktime(&tm)-offset*60; /* FIXME: mktime assumes the current timezone
                                       * instead of UTC, and unless we rewrite OpenSSL
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/t_x509.c      Wed Nov 13 21:25:56 
2002
+++ crypto/asn1/t_x509.c        Tue Apr  1 19:52:43 2003
@@ -368,9 +368,17 @@
        int gmt=0;
        int i;
        int y=0,M=0,d=0,h=0,m=0,s=0;
+#ifdef CHARSET_EBCDIC
+
char v_e[14];
+#endif
 
        i=tm->length;
+#ifdef CHARSET_EBCDIC
+       ascii2ebcdic(v_e, tm->data, i < 14 ? i : 14);
+
v = &v_e[0];
+#else
        v=(char *)tm->data;
+#endif
 
        if (i < 12) goto err;
        if (v[i-1] == 'Z') gmt=1;
@@ -402,9 +410,17 @@
        int gmt=0;
        int i;
        int y=0,M=0,d=0,h=0,m=0,s=0;
+#ifdef CHARSET_EBCDIC
+
char v_e[14];
+#endif
 
        i=tm->length;
+#ifdef CHARSET_EBCDIC
+       ascii2ebcdic(v_e, tm->data, i < 14 ? i : 14);
+
v = &v_e[0];
+#else
        v=(char *)tm->data;
+#endif
 
        if (i < 10) goto err;
        if (v[i-1] == 'Z') gmt=1;
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/x509/x509_vfy.c    Tue Dec 10 09:26:10 
2002
+++ crypto/x509/x509_vfy.c      Wed Apr  2 20:03:41 2003
@@ -759,10 +759,19 @@
        long offset;
        char buff1[24],buff2[24],*p;
        int i,j;
+#ifdef CHARSET_EBCDIC
+
char str_e[17];
+#endif
 
        p=buff1;
        i=ctm->length;
+#ifdef CHARSET_EBCDIC
+
memset(str_e, '\0', sizeof str_e);
+       ascii2ebcdic(str_e, ctm->data, i < 17 ? i : 17);
+       str = &str_e[0];
+#else
        str=(char *)ctm->data;
+#endif
        if (ctm->type == V_ASN1_UTCTIME)
                {
                if ((i < 11) || (i > 17)) return 0;
@@ -811,6 +820,9 @@
        atm.data=(unsigned char *)buff2;
 
        X509_time_adj(&atm,-offset*60, cmp_time);
+#ifdef CHARSET_EBCDIC
+       ascii2ebcdic(atm.data, atm.data, atm.length);
+#endif
 
        if (ctm->type == V_ASN1_UTCTIME)
                {
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/x509v3/v3_alt.c    Wed Apr 11 14:55:06 
2001
+++ crypto/x509v3/v3_alt.c      Fri Apr 25 14:33:19 2003
@@ -94,6 +94,15 @@
        return ret;
 }
 
+#ifdef CHARSET_EBCDIC
+static const char asc_unsup[] = {0x3c, 0x75, 0x6e, 0x73, 0x75, 0x70, 0x70, 0x6f,
+                                 0x72, 0x74, 0x65, 0x64, 0x3e, 0};
+static const char asc_inval[] = {0x3c, 0x69, 0x6e, 0x76, 0x61, 0x6c, 0x69, 0x64, 
0x3e, 0};
+#else
+static const char asc_unsup[] = "<unsupported>";
+static const char asc_inval[] = "<invalid>";
+#endif
+
 STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method,
                                GENERAL_NAME *gen, STACK_OF(CONF_VALUE) *ret)
 {
@@ -102,15 +111,15 @@
        switch (gen->type)
        {
                case GEN_OTHERNAME:
-               X509V3_add_value("othername","<unsupported>", &ret);
+               X509V3_add_value("othername", asc_unsup, &ret);
                break;
 
                case GEN_X400:
-               X509V3_add_value("X400Name","<unsupported>", &ret);
+               X509V3_add_value("X400Name", asc_unsup, &ret);
                break;
 
                case GEN_EDIPARTY:
-               X509V3_add_value("EdiPartyName","<unsupported>", &ret);
+               X509V3_add_value("EdiPartyName", asc_unsup, &ret);
                break;
 
                case GEN_EMAIL:
@@ -127,6 +136,9 @@
 
                case GEN_DIRNAME:
                X509_NAME_oneline(gen->d.dirn, oline, 256);
+#ifdef CHARSET_EBCDIC
+               ebcdic2ascii(oline, oline, strlen(oline));
+#endif
                X509V3_add_value("DirName",oline, &ret);
                break;
 
@@ -134,15 +146,21 @@
                p = gen->d.ip->data;
                /* BUG: doesn't support IPV6 */
                if(gen->d.ip->length != 4) {
-                       X509V3_add_value("IP Address","<invalid>", &ret);
+                       X509V3_add_value("IP Address", asc_inval, &ret);
                        break;
                }
                sprintf(oline, "%d.%d.%d.%d", p[0], p[1], p[2], p[3]);
+#ifdef CHARSET_EBCDIC
+               ebcdic2ascii(oline, oline, strlen(oline));
+#endif
                X509V3_add_value("IP Address",oline, &ret);
                break;
 
                case GEN_RID:
                i2t_ASN1_OBJECT(oline, 256, gen->d.rid);
+#ifdef CHARSET_EBCDIC
+               ebcdic2ascii(oline, oline, strlen(oline));
+#endif
                X509V3_add_value("Registered ID",oline, &ret);
                break;
        }
@@ -439,6 +457,9 @@
 }
 
 if(is_string) {
+#ifdef CHARSET_EBCDIC
+       ebcdic2ascii(value, value, strlen(value));
+#endif
        if(!(gen->d.ia5 = M_ASN1_IA5STRING_new()) ||
                      !ASN1_STRING_set(gen->d.ia5, (unsigned char*)value,
                                       strlen(value))) {
--- /home2/openssl/tmp/openssl-0.9.7a/crypto/asn1/a_strex.c     Tue Nov 12 14:21:22 
2002
+++ crypto/asn1/a_strex.c       Wed Mar 26 21:31:00 2003
@@ -111,11 +111,20 @@
  * character because it could come from 2 or even
  * 4 byte forms.
  */
+#ifdef CHARSET_EBCDIC
+/* The conversion to EBCDIC assumes, that the parameter c is
+ * always an ASCII char. This assumption doesn't hold true
+ * when the calling functions work on a string literal.
+ */
+#endif
 
 static int do_esc_char(unsigned long c, unsigned char flags, char *do_quotes, char_io 
*io_ch, void *arg)
 {
        unsigned char chflgs, chtmp;
        char tmphex[HEX_SIZE(long)+3];
+#ifdef CHARSET_EBCDIC
+      char chtmp_ebcdic;
+#endif
 
        if(c > 0xffffffffL)
                return -1;
@@ -132,15 +141,26 @@
        chtmp = (unsigned char)c;
        if(chtmp > 0x7f) chflgs = flags & ASN1_STRFLGS_ESC_MSB;
        else chflgs = char_type[chtmp] & flags;
+#ifdef CHARSET_EBCDIC
+       chtmp_ebcdic = os_toebcdic[chtmp];
+#endif
        if(chflgs & CHARTYPE_BS_ESC) {
                /* If we don't escape with quotes, signal we need quotes */
                if(chflgs & ASN1_STRFLGS_ESC_QUOTE) {
                        if(do_quotes) *do_quotes = 1;
+#ifdef CHARSET_EBCDIC
+                       if(!io_ch(arg, &chtmp_ebcdic, 1)) return -1;
+#else
                        if(!io_ch(arg, &chtmp, 1)) return -1;
+#endif
                        return 1;
                }
                if(!io_ch(arg, "\\", 1)) return -1;
+#ifdef CHARSET_EBCDIC
+               if(!io_ch(arg, &chtmp_ebcdic, 1)) return -1;
+#else
                if(!io_ch(arg, &chtmp, 1)) return -1;
+#endif
                return 2;
        }
        if(chflgs & (ASN1_STRFLGS_ESC_CTRL|ASN1_STRFLGS_ESC_MSB)) {
@@ -148,7 +168,11 @@
                if(!io_ch(arg, tmphex, 3)) return -1;
                return 3;
        }
+#ifdef CHARSET_EBCDIC
+       if(!io_ch(arg, &chtmp_ebcdic, 1)) return -1;
+#else
        if(!io_ch(arg, &chtmp, 1)) return -1;
+#endif
        return 1;
 }
 

Reply via email to