[AFS3-std] Finishing the core rxgk document

Benjamin Kaduk kaduk@MIT.EDU
Thu, 17 Oct 2013 23:08:18 -0400 (EDT)


Hey list: Nico reviewed the rxgk document, his comments are in the quoted 
text.

The biggest (not super-big, but a little big) question I want feedback on 
is whether we should axe the complete description of the GSS negotiation 
loop and just make use of references to other examples/descriptions.

Most of the changes are minor and I've taken them (or a similar version) 
without comment.  A rendered version is up at 
http://web.mit.edu/kaduk/Public/draft-wilkinson-afs3-rxgk.txt (I didn't 
see the need to submit a new I-D until the negotiation loop description 
question is answered); the XML source is still at 
https://github.com/kaduk/openafs/commits/prot

The I-D submission cutoff is on monday, I'd like to get a new revision in 
before then.

[more inline]

On Mon, 14 Oct 2013, Nico Williams wrote:

> On Fri, Sep 20, 2013 at 12:42:12PM -0400, Benjamin Kaduk wrote:
>> Is there any chance you could look it over and give your comments?
>> It's section 6 of
>> http://tools.ietf.org/html/draft-wilkinson-afs3-rxgk-07 , and
>> ideally comments would go to the afs3-standardization@openafs.org
>> list.
>
> - Section 4, authentication only also does not protect against
>   eavesdroppers.  I know, obvious.
>
> - rxkad is mentioned (first in Section 4) without definition nor
>   references.

It's a bit awkward, since we're sort of bootstrapping the standardization 
of AFS, and there's no real reference for rxkad.  I talked about it a 
little in the introduction, at least.

> - Section 4, the paragraph following the list is redundant.
>
> - Section 5, is there any latency expectation regarding how long it
>   takes to identify a client user from a token?

I don't think there are any particularly concrete expectations.
The client does have some timeouts at the connection level, but those will 
be seconds at least.  (I don't know the concrete values offhand.)

> - Section 5, maybe the notional *minimal* contents (decrypted or
>   looked-up) of the token should be described with an XDR struct?  See
>   comment below about K0; it'd help to state that the root session key
>   is part of the token.

I think I could picture a scenario when only the session key is needed, 
amusingly enough.  (The negotiation service only issues tokens to 
authorized users, all users have full permissions, and no one cares about 
expiry.)  The companion document draft-wilkinson-afs3-rxgk-afs does have 
an explicit token format for the use with the AFS protocol.

> - Section 6, what language is used for the data description?  It's not
>   XDR proper...  If it's a superset of XDR, maybe we can express the
>   input and output parameters of the GSSNegotiate() RPC as structs,
>   just as... ONC RPC does.  Then you get the benefit of being able to
>   use rpcgen(1), if nothing else to validate the spec.

It's written so as to be compatible with rxgen(1), our fork of rpcgen(1); 
the language itself is called "RPC-L" which is basically XDR for 
structures plus a syntax for writing RPC prototypes and their names.

> - page 6:
>
>   What is:
>
>       package RXGK_
>
>   ?  Is it unfinished?

This is part of the syntax used by rxgen, basically placing everything 
that follows into the RXGK namespace...

>   Later this operation is referred to as RXGK_GSSNegotiate, then later
>   again as GSSNegotiate, so I suspect there is a formatting error here.
>   If nothing else it's confusing.

...so the routine that clients will call from the C code is 
RXGK_GSSNegotiate().  But, it's probably easiest to continue referring to 
the RPC as just GSSNegotiate() in the document, there was only one 
instance with the RXGK_ prefix, so I removed the prefix in that instance.

> - Section 6, the gss_minor/major_status values need to be explicitly
>   described as entirely optional and informative -- of no normative
>   value, even in error conditions, EXCEPT that the major status is of
>   normative value IFF the no output_token_buffer field is absent, and
>   the gss_major_status value is present.
>
>   Please RECOMMEND that error tokens be sent (as output_token_buffer).
>
>   No need to say anything about whether to bother sending
>   gss_major/minor_status.  UNLESS successfully established security
>   contexts can be rejected by the server, though even then, no
>   gss_major/minor_status code could be of use in conveying such
>   authorization decisions.  (Ah, but I see that successful sec ctx
>   establishment is not sufficient, and that subsequent non-GSS errors
>   can be communicated via the errorcode of the RXGK_ClientInfo.
>
>   Is gss_major_status strictly optional?  Is it possible for rxgk_info
>   to be present but gss_major_status to be absent?  I think it's
>   important to be clear on this point.  Actual implementation behavior
>   for existing implementations may be relevant.

Unfortunately, we are using gss_major_status as an indicator for whether 
the contents of rxgk_info are valid.  This is not a great situation to be 
in, given that the abstract GSS-API does not seem do indicate that 
GSS_S_COMPLETE has value 0 (as jhutz has actually pointed months ago on 
this list, which I noticed as I was reviewing the old threads just now).
I added some text calling out GSS_S_COMPLETE as 0, and noting that any 
distinction between different non-zero values is purely informational, but 
this setup is kind of ugly.  I think the protocol as currently set up does 
need an external indicator that the rxgk_info has valid contents, though 
(that is, that the server is GSS_S_COMPLETE and has produced a token), and 
this field is probably the best place to do so.

> - Section 6, bytelife is described as informative, not normative, but
>   similar detail is not provided for lifetime.
>
> - Section 6, but maybe client_nonce shouldn't be too large...  Dual_EC
>   DRBG comes to mind!

I mentioned that it SHOULD NOT be longer than the actual key it's 
producing, but from the DUAL_EC_DBRG standpoint, even the 160 bits we give 
as a minimum may be too much...

> - Section 6.2, first paragraph, I think we should describe the context
>   token exchange as much as possible in terms that reference RFCs 2743
>   and 2744.  My suggestion:
>
> OLD:
>
> 6.2.  GSS Negotiation Loop
>
>   The client proceeds through a GSS security context initialization
>   loop, with alternating calls to GSS_Init_sec_context() and the
>   GSSNegotiate() RPC, until an error or success condition is reached.
>   Each call to GSSNegotiate will return an output token from
>   GSS_Accept_sec_context() and/or an output opaque to be used as an
>   input for a subsequent call to GSSNegotiate, if such a subsequent
>   call is necessary.
>
> NEW:
>
> 6.2.  GSS Negotiation Loop
>
>   The client runs a standard loop over GSS_Init_sec_context() [RFC2743]
>   (see also C example in [RFC2744]).  Security context tokens output by
>   GSS_Init_sec_context() are sent in a GSSNegotiate() RPC, and security
>   context tokens output by GSS_Accept_sec_context() on the server side
>   are sent as results of this RPC.
>
>   The server calls GSS_Accept_sec_context() to process security context
>   tokens sent as the input_token_buffer input parameter of the
>   GSSNegotiate() RPC.  The server sends the response token, as well as
>   an opaque context identifier, in the output_token_buffer and
>   opaque_out output parameters of the GSSNegotiate() RPC result,
>   respectively.
>
>   This is repeated until the security context token exchange is
>   complete (i.e., GSS_Init_sec_context() or GSS_Accept_sec_context()
>   return GSS_S_COMPLETE) or an error results (GSS_Init_sec_context() or
>   GSS_Accept_sec_context() return any major status other than
>   GSS_S_COMPLETE or GSS_S_CONTINUE_NEEDED).  The opaque_out result of
>   any GSSNegotiate() RPC is sent as the opaque_in input of the next
>   GSSNEgotiate() call, if any.

I took this, with a few tweaks.

> - Section 6.2, third paragraph:
>
> OLD:
>
>   Different GSS mechanisms will require a different number of full (or
>   half) round trips.  ...
>
> NEW:
>
>   GSS security context token exchanges are synchronous and may involve
>   any number of context tokens larger than or equal to one.
>   Implementations MUST NOT assume any number of context tokens for any
>   one mechanism, but implementations MAY set an upper bound no less
>   than six (6).

I'm not sure where the number six is coming from, so I haven't taken this 
part yet.  The rest of the wording is probably okay to take, though.

>   ...
>
> - Section 6.2, structure of loop.  I think this is a bit odd and
>   redundant.  The structure of the loop is quite standard; repeating it
>   is useful when the reader doesn't know anything about the GSS-API,
>   but otherwise it could be a source of bugs and confusion.
>
>   It'd be better to describe the req_flags that MUST/SHOULD and/or MUST
>   NOT/SHOULD NOT be set, the ret_flags that MUST/SHOULD or MUST NOT/
>   SHOULD NOT be set on success.  Include a RECOMMENDation to send any
>   context tokens when GSS_Init/Accept_sec_context() return an error.
>
>   Less text, mo' better.
>
>   For example, I think there's no need to discuss non-sensical GSS
>   results, like GSS_S_CONTINUE_NEEDED w/ no output sec context token.
>
> - I.e., remove all of the items 1..4 in section 6.2 and replace them a)
>   with the above text, and b) with text explaining what to do when
>   GSS_Init/Accept_sec_context() returns GSS_S_COMPLETE.  E.g., when
>   GSS_Init_sec_context() returns GSS_S_COMPLETE *and* an output token
>   then the client MUST send it in a GSSNegotiate() RPC... the client is
>   not done until the server returns an rxgk_info... if the context is
>   fully-established but there's no rxgk_info then the client must close
>   the connection and delete the security context token...

This hunk is the biggest question remaining.
I think Simon at one point (when the text was pretty broken) said that he 
would prefer nothing at all to the (then-) current text, but I'd like to 
hear from others, particularly jhutz, before committing to that route.
I do agree that there's nothing particularly special about what we're 
doing here and that if an implementor knows how to do a GSS negotiation 
loop in general, they should be fine implementing rxgk.  The question (to 
me) is more of whether we want to assume that level of expertise on the 
reader, and whether we think that we can give references/examples to 
enough good sources that an inexperienced reader could produce a correct 
implementation.

> - Section 6.3, first para, first sentence, replace "rxgk_info
>   contains..." with "rxgk_info contains GSS wrap token (as output by
>   GSS_Wrap() with the established security context on the server side)
>   taken over the XDR encoding of an RXGK_ClientInfo structure.  If
>   confidentiality protection is available (i.e., conf_ret_flag was
>   set), then conf_flag MUST be set to true in the call to GSS_Wrap())."
>
> - Section 6.3, first para, third sentence: I'm confused.  Is it ever
>   OK to not use conf prot?  The first sentence seems to imply "yes" (if
>   the mech does not support conf prot).

I went back and looked at the history for why that bit was added. 
Basically, a lack of confidentiality is a failure, but it's a failure that 
we report in the errorcode of the RXGK_ClientInfo.  Since we need to 
return the ClientInfo inside a GSS_Wrap token, we have to allow 
non-confidential wrapping in that case, but the idea is to only allow it 
in that case.  I hope the updated text is more clear on this matter.

> - Section 6.3, what is 'K0'?  Maybe it should be defined first?  Or
>   maybe it should be named later?
>
> - Section 6.3, s/K, the desired output length/The required output
>   length (here denoted as K)/

That didn't quite match up with the structure of the list, with the item 
being described appearing first.

>   Although I'd want this to be K_len or something more indicative of
>   its meaning (K tends to denote "key" to me).
>
> - Section 6.3, reference RFC4401 where GSS_Pseudo_random() is first
>   mentioned?
>
> - Section 7, hmmm, so KRB5-FX-CF2 takes two peppers as arguments, but
>   in its description they are labelled just octet strings.  It's not
>   clear that those strings are the peppers referenced afterwards in
>   RFC6113.  No big deal.

Yeah, not much we can do on our end, here.

> - Security considerations: should we now note that nonces present an
>   opportunity for a) exploiting backdoored RNGs, b) a covert way to
>   sneak out session key data?

I'm not really convinced that we're doing anything special enough to merit 
mentioning this.  Yes, it is a theoretical issue, and it's getting some 
coverage elsewhere at present, but I don't really want to do much more 
than (potentially) refer to some other description of the issue.

> That's it for now.  I'll review section 8 some other time.

[I got a note on IRC that there were no comments about section 8]

> Feel free to share this with Simon or anyone else.

The list is "anyone else", yay.

Thanks again for the review.

-Ben