aheinecke@21: #include "certificate.h" aheinecke@82: #include andre@186: #include aheinecke@21: #include aheinecke@21: aheinecke@338: #include "certhelp.h" aheinecke@94: aheinecke@338: /* Qt wrapper around certhelp functions. */ aheinecke@338: QString getX509Value(x509_name *namebuf, unsigned char *oid) { aheinecke@338: QString retval; aheinecke@338: char * buf = get_oid_valstr(namebuf, oid); aheinecke@338: if (buf == NULL) { aheinecke@338: return retval; aheinecke@338: } aheinecke@338: retval = QString::fromUtf8(buf, -1); aheinecke@338: free(buf); aheinecke@338: return retval; aheinecke@338: } aheinecke@338: aheinecke@338: void Certificate::parseDetails(const QByteArray& cert) { aheinecke@338: x509_crt chain; aheinecke@338: aheinecke@338: x509_crt_init(&chain); aheinecke@338: if (x509_crt_parse_der(&chain, (const unsigned char *)cert.data(), aheinecke@338: cert.size()) != 0) { aheinecke@338: qDebug() << "Failed to parse cert.."; aheinecke@338: return; aheinecke@338: } aheinecke@338: aheinecke@338: mValidFrom = QDateTime(QDate(chain.valid_from.year, aheinecke@338: chain.valid_from.mon, aheinecke@338: chain.valid_from.day), aheinecke@338: QTime(chain.valid_from.hour, aheinecke@338: chain.valid_from.min, aheinecke@338: chain.valid_from.sec)); aheinecke@338: aheinecke@338: mValidTo = QDateTime(QDate(chain.valid_to.year, aheinecke@338: chain.valid_to.mon, aheinecke@338: chain.valid_to.day), aheinecke@338: QTime(chain.valid_to.hour, aheinecke@338: chain.valid_to.min, aheinecke@338: chain.valid_to.sec)); aheinecke@338: aheinecke@338: mSubjectCN = getX509Value(&(chain.subject), CERT_OID_CN); aheinecke@338: mSubjectOU = getX509Value(&(chain.subject), CERT_OID_OU); aheinecke@338: mSubjectO = getX509Value(&(chain.subject), CERT_OID_O); aheinecke@338: mSubjectSN = getX509Value(&(chain.subject), CERT_OID_SN); aheinecke@338: x509_crt_free(&chain); aheinecke@338: aheinecke@338: mDetails = QObject::tr("Certificate:\n" aheinecke@338: " %1\n" aheinecke@338: " %2, %3\n\n" aheinecke@338: "Serial number:\n" aheinecke@338: "%4\n" aheinecke@338: "Valid from: %5 to %6\n\n" aheinecke@338: "Issued by: ..") aheinecke@338: .arg(mSubjectCN) aheinecke@338: .arg(mSubjectO) aheinecke@338: .arg(mSubjectOU) aheinecke@338: .arg(mSubjectSN) aheinecke@338: .arg(QLocale::system().toString(mValidFrom)) aheinecke@338: .arg(QLocale::system().toString(mValidTo)); aheinecke@338: } andre@186: aheinecke@83: Certificate::Certificate(const QString& b64Line) : andre@186: mValid(false) aheinecke@81: { andre@204: if (b64Line.isEmpty()) { andre@204: return; andre@204: } andre@204: aheinecke@83: /* Cut of the first two chars (e.g. I: and decode) */ aheinecke@83: QByteArray asn1data = QByteArray::fromBase64( aheinecke@83: b64Line.right(b64Line.size() - 2).toLatin1()); aheinecke@83: aheinecke@338: parseDetails(asn1data); andre@186: aheinecke@338: /* If the subject CN is set then at least one x509parse aheinecke@338: * in polarssl was successfull. And a root certificate aheinecke@338: * always needs to have a subject CN */ aheinecke@338: mValid = !mSubjectCN.isEmpty(); aheinecke@83: aheinecke@83: mBaseLine = b64Line; aheinecke@81: } andre@186: aheinecke@338: QString Certificate::shortDescription() const { aheinecke@338: if (!isValid()) { aheinecke@338: return QObject::tr("Failed to parse certificate"); aheinecke@338: } aheinecke@338: aheinecke@338: QString ret = mSubjectCN; /* Necessary by definition */ aheinecke@338: if (!mSubjectO.isEmpty()) { aheinecke@338: ret += " - " + mSubjectO; aheinecke@338: } aheinecke@338: if (!mSubjectOU.isEmpty()) { aheinecke@338: ret += ", " + mSubjectOU; aheinecke@338: } aheinecke@338: return ret; andre@186: } rrenkert@352: rrenkert@352: void Certificate::setInstallCert(bool install) rrenkert@352: { rrenkert@352: if (install && mBaseLine.startsWith("R:")) { rrenkert@352: mBaseLine.replace(0, 1, "I"); rrenkert@352: } rrenkert@352: else if (!install && mBaseLine.startsWith("I:")) { rrenkert@352: mBaseLine.replace(0, 1, "R"); rrenkert@352: } rrenkert@352: }