ref: 272dec2602bfb557af9464d21426d195b8e8e1a5
parent: 13738d2aa200eeb5859525225ec1d7bec7e8134e
author: mkf <mkf@cloud9p.org>
date: Tue Dec 3 07:21:09 EST 2024
der.c: import
--- /dev/null
+++ b/der.c
@@ -1,0 +1,124 @@
+#include <openssl/x509.h>
+#include <openssl/x509v3.h>
+#include <openssl/bn.h>
+#include <openssl/asn1.h>
+#include <openssl/x509.h>
+#include <openssl/x509_vfy.h>
+#include <openssl/pem.h>
+#include <openssl/bio.h>
+#include "common.h"
+
+int
+duplicateCN(u_char *cn, Der *der)
+{
+ for(int i = 0 ; i < der->nCommonName ; i++)
+ {
+ if(!strcmp(cn, der->commonName[i]))
+ return 1;
+ }
+ return 0;
+}
+
+int
+parseDerManual(const u_char *pkt, Der *der)
+{
+ u_char subjectlen;
+ u_char cnlen;
+ u_char *cn;
+
+ // for(u_char *p = PKTHEAD ; p < PKTHEAD + der->len + 5 ; p++)
+ der->nCommonName = 0;
+ for(u_char *p = PKTHEAD ; der->nCommonName < DER_CN_MAX && p != NULL ; p = (u_char*)memchr(p+1, 30, der->len))
+ {
+ p++;
+ subjectlen = *p;
+
+ for(u_char *s = p ; s != NULL && s - p < subjectlen ; s = (u_char*)memchr(s+1, 0x55, der->len))
+ {
+ if(s[0] == 0x55 && s[1] == 0x4 && s[2] == 0x3)
+ {
+ s += 4;
+ cnlen = *p;
+ s += 1;
+ cn = memdup(s, cnlen+1);
+ cn[cnlen] = '\0';
+
+ if(duplicateCN(cn, der))
+ {
+ free(cn);
+ continue;
+ }
+ der->commonName[der->nCommonName] = cn;
+ der->nCommonName++;
+ s += cnlen;
+ }
+ }
+ }
+ pos += der->len;
+ return 1;
+}
+
+
+int
+parseDerOpenSSL(const u_char *pkt, Der *der)
+{
+ const u_char *head = pkt + pos;
+ der->cert = d2i_X509(NULL, &head, der->len);
+ if(!der->cert)
+ {
+ err(0, "parseDer(): failure to parse cert: pos: %d (%#x)", pos, pos);
+ return 0;
+ }
+
+ der->subject = X509_NAME_oneline(X509_get_subject_name(der->cert), NULL, 0);
+ der->issuer = X509_NAME_oneline(X509_get_issuer_name(der->cert), NULL, 0);
+
+ if (X509_check_issued(der->cert, der->cert) == X509_V_OK)
+ der->selfsigned = 1;
+ else
+ der->selfsigned = 0;
+
+ der->commonName[0] = strstr(der->subject, "CN=");
+ der->commonName[0] += 3; // "CN=", skip it.
+ der->nCommonName++;
+
+ pos += der->len;
+ return 1;
+}
+
+int
+parseDer(const u_char *pkt, Der *der)
+{
+ return parseDerOpenSSL(pkt, der);
+}
+
+void
+printDer(Der der)
+{
+ if(debug)
+ {
+ printf("Der:\n"
+ "\t\tsubject: %s\n"
+ "\t\tissuer: %s\n"
+ "\t\tselfsigned: %d\n",
+
+ der.subject, der.issuer, der.selfsigned);
+
+ for(int i = 0 ; i < der.nCommonName ; i++)
+ printf("\t\tCN: %s\n",
+ der.commonName[i]);
+ }
+ else
+ {
+ for(int i = 0 ; i < der.nCommonName ; i++)
+ printf("\t\tCN: %s\n",
+ der.commonName[i]);
+ }
+}
+
+void
+freeDer(Der *der)
+{
+ X509_free(der->cert);
+ free(der);
+}
\ No newline at end of file