This site is being rebuilt and some pages are out of date. For current details, write to [email protected]. This notice goes away when the rebuild is done.

No analytics unless you allow it, no tracking. This site keeps in your browser the language you pick, the theme, its colour, which site you chose, the currency on the pricing page and that you closed this notice; signing in adds session cookies. The legal page has the details.

Sign in

Radar · Go · Archive · Week 48 · Nov 24 – 30, 2025

crypto/x509: add ExtKeyUsage.OID

Nice to knowstdlib

What changed
The proposal adds ExtKeyUsage.OID() and OIDFromASN1OID to allow checking an EKU’s ASN.1 object identifier.
Production impact
The source does not say.
Try it
Inspect a certificate’s ExtKeyUsage values and call .OID() on them.
Source
github.com/golang/go/issues/75325

Understand it, then run it

Run it now

Todaygo
// This program demonstrates how to detect an unknown Extended Key Usage (EKU)
// in a certificate using Go 1.27.1, where the standard library does not
// provide ExtKeyUsage.OID(). It parses the EKU extension directly from the
// ASN.1 data to obtain the OID. The output shows the OID that was not
// recognized by the x509 package.

package main

import (
	"crypto/rand"
	"crypto/rsa"
	"crypto/x509"
	"crypto/x509/pkix"
	"encoding/asn1"
	"encoding/pem"
	"fmt"
	"math/big"
	"time"
)

func main() {
	// Create a self‑signed certificate that contains an EKU with an OID
	// that the standard library does not recognize (1.2.3.4.5.6).
	unknownEKU := asn1.ObjectIdentifier{1, 2, 3, 4, 5, 6}

	// Build the EKU extension manually.
	ekuExt, err := asn1.Marshal([]asn1.ObjectIdentifier{unknownEKU})
	if err != nil {
		panic(err)
	}
	ext := pkix.Extension{
		Id:    asn1.ObjectIdentifier{2, 5, 29, 37}, // id-ce-extKeyUsage
		Value: ekuExt,
	}

	// Generate a key for the certificate.
	priv, err := rsa.GenerateKey(rand.Reader, 2048)
	if err != nil {
		panic(err)
	}

	// Create the certificate template.
	template := x509.Certificate{
		SerialNumber: big.NewInt(1),
		Subject: pkix.Name{
			CommonName: "example.com",
		},
		NotBefore:             time.Now(),
		NotAfter:              time.Now().Add(365 * 24 * time.Hour),
		KeyUsage:              x509.KeyUsageDigitalSignature,
		BasicConstraintsValid: true,
		IsCA:                  true,
		// Include the manually built EKU extension.
		ExtraExtensions: []pkix.Extension{ext},
	}

	// Create the DER‑encoded certificate.
	derBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &priv.PublicKey, priv)
	if err != nil {
		panic(err)
	}

	// Encode the certificate as PEM for display.
	pemBlock := pem.EncodeToMemory(&pem.Block{Type: "CERTIFICATE", Bytes: derBytes})
	fmt.Println(string(pemBlock))

	// Parse the certificate with the standard library.
	cert, err := x509.ParseCertificate(derBytes)
	if err != nil {
		panic(err)
	}

	// The unknown EKU will appear in UnknownExtKeyUsage.
	fmt.Println("UnknownExtKeyUsage:", cert.UnknownExtKeyUsage)

	// To check the EKU OID, we must parse the extension ourselves.
	// Find the EKU extension by OID.
	var ekuValue []byte
	for _, e := range cert.Extensions {
		if e.Id.Equal(asn1.ObjectIdentifier{2, 5, 29, 37}) {
			ekuValue = e.Value
			break
		}
	}
	if ekuValue == nil {
		fmt.Println("EKU extension not found")
		return
	}

	// Decode the EKU extension value.
	var oids []asn1.ObjectIdentifier
	if _, err := asn1.Unmarshal(ekuValue, &oids); err != nil {
		fmt.Println("Failed to parse EKU extension:", err)
		return
	}
	fmt.Println("Parsed EKU OIDs:", oids)
}

What it printed when we ran it on Go 1.27.1

-----BEGIN CERTIFICATE-----
MIIC+zCCAeOgAwIBAgIBATANBgkqhkiG9w0BAQsFADAWMRQwEgYDVQQDEwtleGFt
cGxlLmNvbTAeFw0yNjEwMDEwOTIzMzRaFw0yNzEwMDEwOTIzMzRaMBYxFDASBgNV
BAMTC2V4YW1wbGUuY29tMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA
rxtw8YWR/IZhv/ZPBnhiwVtpv0+Fu8c9V8dC9Fdi96c6GUA9L2RBonOPwKvK25mB
RBs+vdqzW7AklUI7AGh8WCXYTKHPDPCTDhO5SjO87yHdkNibrwPK6b9p0+qM0lZg
1fybkBzz3yavUXeJV9mn6IkYUGegZCnKFFyWBcckEkPYGBxV7dz0iTr1lZSHGUam
FNMYwuwwe0Zea+w43F/PoLIusApok+kHcMYypwbJ6Gx2k94J6a7t1BHC1yDWc7M2
gQZT2VjFIOYBZXl+B08e3/MNzKHUa8feVQcUVCQRNMRpTm5hch1YhUoAcn7UuG/b
mNa9E9aRIao6S4O66EVVMQIDAQABo1QwUjAOBgNVHQ8BAf8EBAMCB4AwDwYDVR0T
AQH/BAUwAwEB/zAdBgNVHQ4EFgQUYg2QiyZTZXaw5s/h0827ec03PtIwEAYDVR0l
BAkwBwYFKgMEBQYwDQYJKoZIhvcNAQELBQADggEBAAhDFbkKjbo54++DMWnL4rlO
Eze41CEh6cOA72ep4exfrNFQAlD5JVVmGVzAempqufjrBou4CCCDRKlANr/T0ZOa
OZC0BgmRhT9nsg+nkEwNiIUpWM3ltDuRkSntiuxgNYbJERSM3sOf0gGW6LxVlOAb
GeV5CJ78BOI/nMeQ/Z7+A2mCUdKOuN/L4fGG4TjXDJsqTpJ2BLNkBcwAXblyH9n9
OnxFrcpnN3QOqHx4rVK4YgSBFli1o3NegxJm7A4/AGtnrIox8V+9CGZjB2tRP6Ko
h1TxJqtzzU5ru5MdlxivPWrfZISvMyCohiS127Mpb1D9o+kMsQR7Vc63DEv58zA=
-----END CERTIFICATE-----

UnknownExtKeyUsage: [1.2.3.4.5.6]
Parsed EKU OIDs: [1.2.3.4.5.6]

Run sends this program (for Solidity, the contract and its tests) to our own sandbox, where it is compiled and run once, with no network, and what it printed or the test report comes back here. Nothing is kept. Runs are counted per visitor for the day so everyone gets a turn; the details are on the legal page.

Written by gpt-oss-20b from the linked source · claims checked against the sources · archive, not individually reviewed