x509 certificate MaxPathLen and ASN.1 serialisation

186 views
Skip to first unread message

ky...@gokyle.net

unread,
Apr 11, 2014, 3:44:45 PM4/11/14
to golan...@googlegroups.com
Hello,

I'm trying to build intermediate certificate authority certificates using `crypto/x509`; as part of this, I'd like to explicitly specify a MaxPathLen of 0. I've noticed that due to the way the ASN.1 package handles de-serialisation, a MaxPathLen of 0 is not included in the final DER output.

Specifically, the basic constraints are encoded using

    type basicConstraints struct {
        IsCA       bool `asn1:"optional"`
        MaxPathLen int  `asn1:"optional,default:-1"`
    }

It turns out the ASN.1 package only uses the default value during unmarshaling, and that the zero value is used during marshaling:

        if params.optional && reflect.DeepEqual(v.Interface(), reflect.Zero(v.Type()).Interface()) {
            return
        }

Changing this does have implications, for example, in the way certificates are built now. If this were changed, MaxPathLen would have to be set to -1 to be dropped from the serialised form.

Is there a workaround to this? Would it make sense to patch the ASN.1 package? Am I missing something?

Cheers,
Kyle

Matt Harden

unread,
Apr 12, 2014, 3:52:26 PM4/12/14
to ky...@gokyle.net, golang-nuts
I see no possible workaround that doesn't involve copying parts of crypto/x509 or encoding/asn1.

It definitely makes more sense to me to use the default value to trigger the "optional" behavior. Other marshalers, like JSON, use the zero value (for omitempty) but those don't have a default setting. From what I know about ASN.1 I would be surprised by the current behavior. I also think that marshaling and unmarshaling should be inverses of each other to the greatest extent possible. The current behavior is not documented and in fact the documentation suggests that the default value should be used to make omission decisions.


default:x		sets the default value for optional integer fields

We do have two exceptions in the Go 1 compatibility promise that might be considered to cover this change, despite the fact that it has the potential to break existing programs:
  • Unspecified behavior. The Go specification tries to be explicit about most properties of the language, but there are some aspects that are undefined. Programs that depend on such unspecified behavior may break in future releases.
  • Specification errors. If it becomes necessary to address an inconsistency or incompleteness in the specification, resolving the issue could affect the meaning or legality of existing programs. We reserve the right to address such issues, including updating the implementations. Except for security issues, no incompatible changes to the specification would be made.
Regards,
Matt


--
You received this message because you are subscribed to the Google Groups "golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

agl

unread,
Apr 14, 2014, 2:58:13 PM4/14/14
to golan...@googlegroups.com, ky...@gokyle.net
On Saturday, April 12, 2014 12:52:26 PM UTC-7, Matt Harden wrote:
I see no possible workaround that doesn't involve copying parts of crypto/x509 or encoding/asn1.

Yes, I believe this is a bug.

Please test https://codereview.appspot.com/86960045 and let me know if that fixes it for you.


Cheers

AGL
Reply all
Reply to author
Forward
0 new messages