Skip to content

Commit

Permalink
Merge pull request #272 from projectdiscovery/cert-parsing
Browse files Browse the repository at this point in the history
Improving certificate parsing
  • Loading branch information
Ice3man543 authored May 22, 2021
2 parents 08955fd + 934e104 commit 51da009
Showing 1 changed file with 66 additions and 13 deletions.
79 changes: 66 additions & 13 deletions common/httpx/tls.go
Original file line number Diff line number Diff line change
@@ -1,32 +1,85 @@
package httpx

import (
"bytes"
"crypto/sha256"
"encoding/hex"
"errors"
"fmt"
"net/http"
)

// TLSData contains the relevant Transport Layer Security information
type TLSData struct {
DNSNames []string `json:"dns_names,omitempty"`
Emails []string `json:"emails,omitempty"`
CommonName []string `json:"common_name,omitempty"`
Organization []string `json:"organization,omitempty"`
IssuerCommonName []string `json:"issuer_common_name,omitempty"`
IssuerOrg []string `json:"issuer_organization,omitempty"`
TLSVersion string `json:"tls_version,omitempty"`
ExtensionServerName string `json:"extension_server_name,omitempty"`
DNSNames []string `json:"dns_names,omitempty"`
Emails []string `json:"emails,omitempty"`
CommonName []string `json:"common_name,omitempty"`
Organization []string `json:"organization,omitempty"`
IssuerCommonName []string `json:"issuer_common_name,omitempty"`
IssuerOrg []string `json:"issuer_organization,omitempty"`
FingerprintSHA256 string `json:"fingerprint_sha256,omitempty"`
FingerprintSHA256OpenSSL string `json:"fingerprint_sha256_openssl,omitempty"`
}

// TLSGrab fills the TLSData
func (h *HTTPX) TLSGrab(r *http.Response) *TLSData {
if r.TLS != nil {
var tlsdata TLSData
for _, certificate := range r.TLS.PeerCertificates {
tlsdata.DNSNames = append(tlsdata.DNSNames, certificate.DNSNames...)
tlsdata.Emails = append(tlsdata.Emails, certificate.EmailAddresses...)
tlsdata.CommonName = append(tlsdata.CommonName, certificate.Subject.CommonName)
tlsdata.Organization = append(tlsdata.Organization, certificate.Subject.Organization...)
tlsdata.IssuerOrg = append(tlsdata.IssuerOrg, certificate.Issuer.Organization...)
tlsdata.IssuerCommonName = append(tlsdata.IssuerCommonName, certificate.Issuer.CommonName)
// Only PeerCertificates[0] contains useful information
cert := r.TLS.PeerCertificates[0]
tlsdata.DNSNames = append(tlsdata.DNSNames, cert.DNSNames...)
tlsdata.Emails = append(tlsdata.Emails, cert.EmailAddresses...)
tlsdata.CommonName = append(tlsdata.CommonName, cert.Subject.CommonName)
tlsdata.Organization = append(tlsdata.Organization, cert.Subject.Organization...)
tlsdata.IssuerOrg = append(tlsdata.IssuerOrg, cert.Issuer.Organization...)
tlsdata.IssuerCommonName = append(tlsdata.IssuerCommonName, cert.Issuer.CommonName)
tlsdata.ExtensionServerName = r.TLS.ServerName
if v, ok := tlsVersionStringMap[r.TLS.Version]; ok {
tlsdata.TLSVersion = v
}

if fingerprintSHA256, err := calculateFingerprints(r); err == nil {
tlsdata.FingerprintSHA256 = asHex(fingerprintSHA256)
tlsdata.FingerprintSHA256OpenSSL = asOpenSSL(fingerprintSHA256)
}
return &tlsdata
}
return nil
}

var tlsVersionStringMap = map[uint16]string{
0x0300: "SSL30",
0x0301: "TLS10",
0x0302: "TLS11",
0x0303: "TLS12",
0x0304: "TLS13",
}

func calculateFingerprints(r *http.Response) (fingerprintSHA256 []byte, err error) {
if len(r.TLS.PeerCertificates) == 0 {
err = errors.New("no certificates found")
return
}

cert := r.TLS.PeerCertificates[0]
dataSHA256 := sha256.Sum256(cert.Raw)
fingerprintSHA256 = dataSHA256[:]
return
}

func asOpenSSL(b []byte) string {
var buf bytes.Buffer
for i, f := range b {
if i > 0 {
fmt.Fprintf(&buf, ":")
}
fmt.Fprintf(&buf, "%02X", f)
}
return buf.String()
}

func asHex(b []byte) string {
return hex.EncodeToString(b)
}

0 comments on commit 51da009

Please sign in to comment.