关于证书和TLS支持 - emmansun/gmsm GitHub Wiki

  • 证书支持:smx509
  • http tls支持(tlcp):第三方实现gotlcp,该实现ECC_SM4_GCM_SM3、ECC_SM4_CBC_SM3经过互操作测试,其它ECDHE_SM4_GCM_SM3、ECDHE_SM4_CBC_SM3没有通过互操作测试,目前没有可信的互操作测试目标,规范也描述不清。
  • ShangMi (SM) Cipher Suites for TLS 1.3,实现了和golang 1.19.x类似的ecdh,能融入golang sdk就比较好实现,单独维护成本太大,而且使用范围不广。

smx509实现中的问题:

现有smx509实现中,我们定义了以下结构(非别名),用于覆盖x509中的实现或者添加新方法:

// A Certificate represents an X.509 certificate.
type Certificate x509.Certificate

// CertificateRequest represents a PKCS #10, certificate signature request.
type CertificateRequest x509.CertificateRequest

type RevocationList x509.RevocationList

它的优点是:

  • 新的类型,可以覆盖旧方法、添加新方法;
  • 无需复制x509中相关结构的完整定义和方法;

它的缺点是:

  • 需要显示转换才能在这些类型和x509相应类型之间进行转换。
  • 如果x509中相应类型有私有字段(不管是直接的还是间接的),并且我们的扩展实现必须访问,则会引发可访问性问题
  • 如果有其它类型中定义了该类型的字段,那这个类型必须完整重定义(复制完整实现),代码改动量、维护工作量也比较大。

Golang 在x509.Certificate中引入了新字段(忽略简单字段): image

这种情况下,在sm509中实现相应功能就显得十分困难!

解决方案

方案一

重新定义Certificate,不再是简单的类型定义type Certificate x509.Certificate,而是拷贝x509.Certificate完整结构,或者扩展x509.Certificate结构,这样的话,在两者之间转换成本就偏高。

假设以后Golang在某个版本又新加了新字段,那为了兼容以前的旧版本,在两者转换的时候,还需要通过反射来判断该字段的存在性;或者不转新字段,直到支持的Golang最小版本都支持该字段。

方案二

彻底抛弃原来的实现,放弃支持非国密,这个改动可能成本更高,且有上游的兼容性问题。

这个等有实际case需要support的时候再考虑吧。至于为什么要引入x509.OID,可以参考golang的issue #60665 crypto/x509: introduce new robust OID type & use it for certificate policies.