On Thu, Jun 6, 2013 at 3:09 PM, Pieter Hintjens <[email protected]> wrote:
> As you may know we're drafting a new protocol for tcp://.
>
> The current draft is here: http://rfc.zeromq.org/spec:23, and libzmq
> already implements most of that (NULL and PLAIN mechanisms).
> [...]
I'm also quickly reading through ZMTP specification and below are
my observations (in the order I observe them, not necessarily
priority, etc.)
(A) As mechanism is specified, interleaving `%x0` characters are
allowed in between the other characters, which could be used to try to
trick various implementations. It should be clearly specified that
the `%x0` character is allowed only as padding, not inside the string.
In the "Authentication and Confidentiality" section it already
specified the structure of a valid method name, however doesn't
discuss the syntax over the wire.
(B) From how the `command-size` and `message-more` are specified I
deduce that just by looking at the traffic I can detect when the
connection has changed from "command" mode to "message" mode (the
first byte is unique). This is very good and it should be kept in
future versions, because it would allow one to implement something
like `tcpdump` for TCP.
(C) There is a potential "network bug" in section "Error Handling"
which requires that a peer not to reconnect unless it has succeeded a
security handshake. There are a few problems here:
* if the network packets (either the `FIN` or the actual reply)
are dropped and not retransmitted earlier than the timeout given by
the socket API, then the peer can't deduce which was the case;
* if we assume that TCP is unsecured and can be the target of a
MITM attack, then the attacker could fake the `FIN` (or `RST`) packets
thus obtaining a denial of service;
The same observation can be made for all the cases. Moreover the
reconnection handling seems a little bit fuzzy to me (at a first
glance), some cases allowing reconnect, some not, and in all cases you
can't deduce what has actually happened with the other peer. Maybe
all cases should be handled with an exponential backoff approach.
(D) In the case of an "encrypted" connection, the specification
says that the messages are "wrapped" in commands. This means that an
attacker can identify how many messages, and how large, each peer has
exchanged.
I guess that the reason is the following: once the peer selects a
"mechanism" then both the authentication and the privacy is completely
delegated to that mechanism, thus obtaining an almost "perfect"
decoupling between transport, framing and security.
But I think this should be thoroughly reviewed by a cryptographer...
Maybe the "safest" solution is to require the following:
* completely specify (in the ZMTP specification) a few transport
security mechanisms; (just for example like: use RC4, or use AES 128
in CTR mode, etc.;)
* the security handler should then be able to choose one of the
available mechanisms, and also provide the "arguments" (i.e.
cryptographic material) needed to configure them;
(E.1) I find it odd that the "connection meta-data" is a
by-product of the security, thus reducing the reuse potential of the
ZAP protocol.
Maybe a better approach is to say, that after the security
negotiation, there may be other commands (this time potentially
encrypted), that allow the negotiation of this "meta-data".
(E.2) Shouldn't the "identity" be mandatory?
(F) As an observation, I've once read the specification for SOAP,
and found a very nice feature that I've failed to see in other
"transport" mechanisms: mandatory vs optional envelope elements (I
think "elements" were called?). For example we could say something
like this in ZMTP: all commands have a "mandatory" flag, that if
present the other peer must either understand them or fail; if not
mandatory they can be ignored, but replied back as not-understood.
(G) For the purpose of replying back if a command is not
understood, or for asynchronous parallel commands, wouldn't it be
better if all the commands are identified with a unique identifier
chosen by the sender? For example in case of ZAP this is already
present. (This identifier shouldn't be reused in any circumstance by
the sender, meanwhile the replier can only use it as a reply, not for
new commands.)
Moreover couldn't we allow commands to be interleaved with
messages, thus opening a door to something like flow-control, etc.
(But these features shouldn't be missuses.) :)
(H) In general when it comes to "hard-coded" tokens like socket
types or security mechanisms, I think there should be a prefix that
denotes "experimental" or "private", just like in case of
`X-Something` HTTP or SMTP headers.
As a general remark, I think ZMTP is still balanced in terms of
complexity and what it offers. Good work!
Ciprian.
_______________________________________________
zeromq-dev mailing list
[email protected]
http://lists.zeromq.org/mailman/listinfo/zeromq-dev