mirror of
https://github.com/gesellix/Bose-SoundTouch.git
synced 2026-08-18 00:26:29 +00:00
Fix: encode IP addresses as raw octets in Subject Alternative Names (#116)
- Update `GenerateCertificate` to correctly identify IP addresses and add them to `IPAddresses` instead of `DNSNames`. - Update `GetServerTLSConfig` to verify both `DNSNames` and `IPAddresses` when checking certificate validity. - Add `TestCertificateManagerIPAddress` to `certmanager_test.go` to ensure correct encoding and prevent regressions. - Ensure compliance with RFC 5280 by using binary encoding for IP addresses in certificates.
This commit is contained in:
@@ -9,6 +9,7 @@ import (
|
||||
"crypto/x509/pkix"
|
||||
"encoding/pem"
|
||||
"math/big"
|
||||
"net"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"time"
|
||||
@@ -80,6 +81,10 @@ func (cm *CertificateManager) GetServerTLSConfig(domains []string) (*tls.Config,
|
||||
domainMap[d] = true
|
||||
}
|
||||
|
||||
for _, ip := range cert.IPAddresses {
|
||||
domainMap[ip.String()] = true
|
||||
}
|
||||
|
||||
for _, d := range domains {
|
||||
if !domainMap[d] {
|
||||
generate = true
|
||||
@@ -237,6 +242,19 @@ func (cm *CertificateManager) GenerateCertificate(domains []string) ([]byte, []b
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
var (
|
||||
dnsNames []string
|
||||
ipAddresses []net.IP
|
||||
)
|
||||
|
||||
for _, domain := range domains {
|
||||
if ip := net.ParseIP(domain); ip != nil {
|
||||
ipAddresses = append(ipAddresses, ip)
|
||||
} else {
|
||||
dnsNames = append(dnsNames, domain)
|
||||
}
|
||||
}
|
||||
|
||||
template := x509.Certificate{
|
||||
SerialNumber: serialNumber,
|
||||
Subject: pkix.Name{
|
||||
@@ -247,7 +265,8 @@ func (cm *CertificateManager) GenerateCertificate(domains []string) ([]byte, []b
|
||||
NotAfter: notAfter,
|
||||
KeyUsage: x509.KeyUsageDigitalSignature | x509.KeyUsageKeyEncipherment,
|
||||
ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
|
||||
DNSNames: domains,
|
||||
DNSNames: dnsNames,
|
||||
IPAddresses: ipAddresses,
|
||||
}
|
||||
|
||||
derBytes, err := x509.CreateCertificate(rand.Reader, &template, caCert, &priv.PublicKey, caKey)
|
||||
|
||||
@@ -126,3 +126,47 @@ func TestCertificateManager(t *testing.T) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestCertificateManagerIPAddress(t *testing.T) {
|
||||
tempDir, err := os.MkdirTemp("", "crypto-ip-test")
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to create temp dir: %v", err)
|
||||
}
|
||||
defer os.RemoveAll(tempDir)
|
||||
|
||||
cm := NewCertificateManager(filepath.Join(tempDir, "certs"))
|
||||
|
||||
// Test certificate generation with an IP address
|
||||
domains := []string{"192.168.1.100", "localhost"}
|
||||
certPEM, _, err := cm.GenerateCertificate(domains)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to generate certificate: %v", err)
|
||||
}
|
||||
|
||||
// Verify generated certificate
|
||||
block, _ := pem.Decode(certPEM)
|
||||
cert, err := x509.ParseCertificate(block.Bytes)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to parse certificate: %v", err)
|
||||
}
|
||||
|
||||
// Check IP addresses
|
||||
foundIP := false
|
||||
for _, ip := range cert.IPAddresses {
|
||||
if ip.String() == "192.168.1.100" {
|
||||
foundIP = true
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if !foundIP {
|
||||
t.Errorf("Expected IP address 192.168.1.100 in IPAddresses, but it was not found")
|
||||
}
|
||||
|
||||
// Check if it was mistakenly added to DNSNames
|
||||
for _, dns := range cert.DNSNames {
|
||||
if dns == "192.168.1.100" {
|
||||
t.Errorf("IP address 192.168.1.100 should NOT be in DNSNames")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user