changeset 349:a49766196a7d

Add certificateFromFile method Currently untested
author Andre Heinecke <andre.heinecke@intevation.de>
date Thu, 10 Apr 2014 15:08:54 +0200
parents e6aa82466420
children 8fb815b78742
files ui/certificate.cpp ui/certificate.h
diffstat 2 files changed, 87 insertions(+), 2 deletions(-) [+]
line wrap: on
line diff
--- a/ui/certificate.cpp	Thu Apr 10 14:14:56 2014 +0200
+++ b/ui/certificate.cpp	Thu Apr 10 15:08:54 2014 +0200
@@ -1,9 +1,11 @@
 #include "certificate.h"
 #include <QDebug>
+#include <QFile>
 #include <QStringList>
 #include <QObject>
 
 #include "certhelp.h"
+#include "listutil.h"
 
 /* Qt wrapper around certhelp functions. */
 QString getX509Value(x509_name *namebuf, unsigned char *oid) {
@@ -62,6 +64,20 @@
             .arg(QLocale::system().toString(mValidTo));
 }
 
+Certificate::Certificate(const QByteArray& derData) :
+    mValid(false)
+{
+    if (derData.isEmpty()) {
+        return;
+    }
+
+    parseDetails(derData);
+
+    mValid = !mSubjectCN.isEmpty();
+
+    mBaseLine = derData.toBase64();
+}
+
 Certificate::Certificate(const QString& b64Line) :
     mValid(false)
 {
@@ -70,10 +86,10 @@
     }
 
     /* Cut of the first two chars (e.g. I: and decode) */
-    QByteArray asn1data = QByteArray::fromBase64(
+    QByteArray derData = QByteArray::fromBase64(
             b64Line.right(b64Line.size() - 2).toLatin1());
 
-    parseDetails(asn1data);
+    parseDetails(derData);
 
     /* If the subject CN is set then at least one x509parse
      * in polarssl was successfull. And a root certificate
@@ -97,3 +113,54 @@
     }
     return ret;
 }
+
+QList<Certificate> Certificate::fromFileName(const QString& file_name) {
+    /* We read the file using Qt to avoid filename encoding problems
+     * on Windows */
+
+    /* TODO change qDebug errors into messageboxes */
+    QFile certificateFile(file_name);
+    QByteArray fileContent;
+    QList<Certificate> retval;
+    x509_crt chain;
+    int ret = 0;
+    if (!certificateFile.open(QIODevice::ReadOnly)) {
+        qDebug() << "Failed to read file.";
+        return retval;
+    }
+
+    if (certificateFile.size() > MAX_LINE_LENGTH * MAX_LINES) {
+        qDebug() << "File too large";
+        return retval;
+    }
+
+    fileContent = certificateFile.readAll();
+
+    x509_crt_init(&chain);
+
+    ret = x509_crt_parse(&chain,
+            reinterpret_cast<const unsigned char*>(fileContent.constData()),
+            fileContent.size());
+
+    if (ret < 0) {
+        qDebug() << "Failed to parse certificates.";
+        return retval;
+    }
+
+    if (ret > 0) {
+        qDebug() << "Some certificates could not be parsed.";
+        /* Maybe return here? */
+    }
+
+    x509_crt *iter = &chain;
+
+    while (iter) {
+        QByteArray derData(reinterpret_cast<const char*>(iter->raw.p),
+                static_cast<int>(iter->raw.len));
+        retval << Certificate(derData);
+        iter = iter->next;
+    }
+    x509_crt_free(&chain);
+
+    return retval;
+}
--- a/ui/certificate.h	Thu Apr 10 14:14:56 2014 +0200
+++ b/ui/certificate.h	Thu Apr 10 15:08:54 2014 +0200
@@ -36,6 +36,12 @@
      **/
     Certificate(const QString& b64Line = QString());
 
+    /** @brief construct a certificate from a byte array of DER data
+     *
+     *  @param[in] derData a der encoded certificate.
+     **/
+    Certificate(const QByteArray& derData);
+
     /** @brief check if this certificate could be parsed */
     bool isValid() const {return mValid;}
 
@@ -88,6 +94,18 @@
     /** @brief get the date the certificate expires */
     QDateTime validTo() const {return mValidTo;}
 
+    /** @brief construct certificate objects from a file
+     *
+     *  Constructs a new Certificate Object from a file containing either
+     *  one DER encoded certificate or one or many PEM certificates.
+     *  If no certificate could be parsed from that file an empty list is
+     *  returned.
+     *
+     *  The size restrictions for the certificate list file also apply
+     *  for this file.
+     **/
+    static QList<Certificate> fromFileName (const QString& file_name);
+
 private:
     /** @brief Helper function to parse the details of a certificate **/
     void parseDetails(const QByteArray& cert);

http://wald.intevation.org/projects/trustbridge/