Subject: [hybi] on applicability of AES

From: "Pat McManus @Mozilla" <[email-masked]>
Date: Tue, 11 Jan 2011 15:06:36 -0500

Hi all - awesome to see -04 out. Bedside reading tonight!

Mozilla sponsored some time for me to speak with a lawyer versed in
legal cryptography issues so I could ask him what he thought of AES as a
mask. He is a lawyer, but IANAL and I'm the one writing this email - so
please consider it just layman's background information.

Broadly speaking - in the USA normal use of AES in an exported
implementation would be subject to some registration rules that would
probably require legal help but are not that big of a deal, the details
of which depend on just how the implementation is done. As I understand
it, Open source implementations can more or less fall under a blanket
existing provision and don't need to go through explicit registration.

Also broadly speaking, and I don't have any more insight into this
sentence than what I am writing, his opinion was that a number of other
jurisdictions (UK, France, etc..) have similar regulations.

However, as pointed out here, the proposed masking use of AES is not a
normal crypto use. There is a no secret - all keys are transported in
plain text. The lawyer thought it was fair to consider whether or not
this use of the algorithm constituted cryptography - if it did not, then
the concerns about export regulations would not apply.

I hope to seek (and share) an official opinion on that question if AES
continues to be seriously considered, but the wheels of lawyers and the
government don't always churn as fast as we would like. As far as I'm
concerned, its an open question right now.

The discussion did not touch on non AES approaches.

My inclination at this point in time is that AES certainly carries some
baggage and while it might in the end be workable, we should avoid
exclusive use of it in favor of other workable schemes. I suppose we
could allow a negotiation between hmac-sha1 vs aes (with hmac-sha1 a
required LCD, as neither would be insecure) so implementors could trade
off between speed and regulations - but my gut says that's just
un-necessary complication of websockets.

-- 
http://www.getfirefox.com/

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 12:25:57 -0800

> un-necessary complication of websockets.

I'm not sure how this conclusion follows from your previous statements. It seems as if the lawyer's comments say:

A) If regulatory registration is required, it's not a big deal.
B) Registration might not even be required at all for this use.

Thus, it seems like crypto regulations are not an argument against using AES-CTR.

Regards,
Maciej

---

From: "Pat McManus @Mozilla" <[email-masked]>
Date: Tue, 11 Jan 2011 15:38:01 -0500

> A) If regulatory registration is required, it's not a big deal.

a better way I should have expressed it:
s/not a big deal/require specific regulatory knowledge (presumably a
lawyer) but is not insurmountable/

> Thus, it seems like crypto regulations are not an argument against using AES-CTR.

I guess that depends on what your pain threshold for this kind of
complication is for a mandatory provision in an open standard on an open
web. I think it should be implementable by both large and small parties
who may or may not even have legal counsel unless there is a very
compelling marginal good.

your mileage may reasonably vary.

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 12:48:12 -0800

> your mileage may reasonably vary.

Other network protocols that use crypto are in practice available everywhere from a wide variety of vendors. This includes TLS, DNSSec and IPSec. If we get that kind of mileage, I'll be completely satisfied.

And the tradeoff is not only security but also better performance. AES-CTR is more than twice as fast as computing a SHA1 HMAC and XORing, at least for small messages. So while you may be right that export regulations create extra hassle, I don't think they are a good reason to avoid the use of crypto in protocol design. I think it's fair to list the export regulations as a con, but I don't think they are a showstopper.

Regards,
Maciej

---

From: Willy Tarreau <[email-masked]>
Date: Tue, 11 Jan 2011 21:55:45 +0100

Hi Maciej,

> And the tradeoff is not only security but also better performance. AES-CTR is more than twice as fast as computing a SHA1 HMAC and XORing, at least for small messages. So while you may be right tha…

We just keep in mind that while implementing crypto in a protocol can look
appealing, nothing has yet justified its use in WebSocket.

I'd even add that the concerns about export regulation are more serious
than the one about the vulnerabilities that this crypto should avoid !

Regards,
Willy

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 13:35:14 -0800

> than the one about the vulnerabilities that this crypto should avoid !

I don't think anyone has demonstrated that export regulations are a practical problem in any way. Do software implementations of other IETF protocols that use crypto get restricted in practice? Is there any software product that has been unable to ship? Any number of commercial vendors and open source projects ship strong crypto all over the world, so I simply don't believe there is a real problem here. Can you cite any instance where it has created a real problem?

Regards,
Maciej

---

From: Eric Rescorla <[email-masked]>
Date: Tue, 11 Jan 2011 22:00:25 +0000

> appealing, nothing has yet justified its use in WebSocket.

This is at best a matter of opinion.

-Ekr

---

From: Bruce Atherton <[email-masked]>
Date: Tue, 11 Jan 2011 14:21:26 -0800

> This is at best a matter of opinion.

I'm willing to consider changing my opinion if only someone will explain 
why. I've asked you directly, Eric, and gotten no answer. I've started a 
thread on the subject and gotten no explanations about the benefits of 
this approach. I'm at a loss as to how to get someone to give some real 
reasons why this is in any way justified.

For secure web sockets, all of this security makes perfect sense. For 
ordinary websockets, where the tradeoff is intended to largely be 
simplicity over security, I can't understand what justifies it. I want 
to, but until somebody helps me out this requirement is from Mars.

At this point, when the vote on the masking algorithm comes I'll be 
voting for randomly generated frame keys that are transmitted on the 
wire and used as the mask.

---

From: Scott Ferguson <[email-masked]>
Date: Tue, 11 Jan 2011 14:36:46 -0800

> This is at best a matter of opinion.

No, Eric, a missing justification is not a matter of opinion.

-- Scott

---

From: Eric Rescorla <[email-masked]>
Date: Tue, 11 Jan 2011 22:37:08 +0000

On Tue, Jan 11, 2011 at 10:21 PM, Bruce Atherton <[email-masked]> wrote:
> why. I've asked you directly, Eric, and gotten no answer.

I'm sorry you feel that way, but I don't agree with that interpretation. I think
I've been fairly clear on why I think this is an improvement. I appreciate that
you're not convinced, but that's exactly the point I was making to Willy;
this is a matter of opinion.

> ordinary websockets, where the tradeoff is intended to largely be simplicity
> over security, I can't understand what justifies it.

I don't really see the relevance of secure (wss:) versus insecure (ws:) here.
That question is a matter of the security properties provided to legitimate
clients and legitimate servers. The question here is about the side effects when
a client visits malicious servers.

> I want to, but until
> somebody helps me out this requirement is from Mars.

... in your opinion.

-Ekr

> At this point, when the vote on the masking algorithm comes I'll be voting
> for randomly generated frame keys that are transmitted on the wire and used
> as the mask.
>
> _______________________________________________
> hybi mailing list
> [email-masked]
> https://www.ietf.org/mailman/listinfo/hybi
>

---

From: Eric Rescorla <[email-masked]>
Date: Tue, 11 Jan 2011 22:37:55 +0000

On Tue, Jan 11, 2011 at 10:36 PM, Scott Ferguson <[email-masked]> wrote:
>>>> And the tradeoff is not only security but also better performance.
>>>> AES-CTR is more than twice as fast as computing a SHA1 HMAC and XORing, at
>>>> least for small messages. So while you may be right that export regulations
>>>> create extra hassle, I don't think they are a good reason to avoid the use
>>>> of crypto in protocol design. I think it's fair to list the export
>>>> regulations as a con, but I don't think they are a showstopper.
>>>>
>>>

As I said to Bruce, I'm sorry you feel that I haven't justified this.
Obviously, others
feel differently, as do I, and I don't really see a point in repeating myself.

-Ekr

---

From: Scott Ferguson <[email-masked]>
Date: Tue, 11 Jan 2011 14:55:00 -0800

From your earlier response:

> >> My objective is to make the bits that appear on the wire indistinguishable
> >> from random from the attacker's perspective. I think it's clear that this is the
> >> strongest form of masking available, and the method I proposed does that.

This is not the problem that needs to be solved for websockets, and 
there's no justification in that response for switching to your new 
objective.

-- Scott

---

From: Adam Barth <[email-masked]>
Date: Tue, 11 Jan 2011 15:40:28 -0800

On Tue, Jan 11, 2011 at 2:55 PM, Scott Ferguson <[email-masked]> wrote:
> This is not the problem that needs to be solved for websockets, and there's
> no justification in that response for switching to your new objective.

One way to think about the justification is what kinds of assumptions
we need to make about the world in order to convince ourselves that
the protocol meets its security objectives.  In this case, having the
on-the-wire bytes appears to be distributed uniformly at random makes
it easier for us to convince ourselves that the protocol meets its
security objectives.

This is a very common technique in designing secure protocols.

Adam

---

From: Bruce Atherton <[email-masked]>
Date: Tue, 11 Jan 2011 16:30:15 -0800

> it easier for us to convince ourselves that the protocol meets its

That is fair. But there are other design considerations that have been 
identified as desirable with Websockets than security. Simplicity of 
implementation is one. Efficiency is another. Minimizing inconvenience 
to users yet another.

When two goals come into conflict, one has to find a balance between 
them. If Websockets were the only protocol on the Internet, it could be 
arguable that security should come before all other goals. Even if 
Websockets were the only way to create a Javascript-controlled 
connection from the browser it may make sense to argue that.

But there is already the ability to create HTTP connections via 
XMLHttpRequest. Once Websockets is more secure than that, the benefit to 
making it more secure dwindles. At that point, other design goals should 
be given a much more equal weight.

I had thought that you had a reason that I wasn't understanding for 
wanting the added security. If your only reason is that it is more 
secure in the abstract, then personally I'm going to give preference to 
those other more concrete design considerations.

---

From: Scott Ferguson <[email-masked]>
Date: Tue, 11 Jan 2011 17:07:21 -0800

> This is a very common technique in designing secure protocols.

Looking under the streetlight for your keys because it's well lit there 
is not an effective technique.

It's important to solve the actual problem, not a different problem that 
you're more comfortable with which happens to be well-lit. You need to 
justify changing the problem. In this case, there has been no 
justification that Eric's streetlight is the same problem as websockets.

Eric is making the implicit claim (without defense) for the following 
sequence:

  C1: GET /websocket HTTP/1.1
  C1: Upgrade: websocket
  C1: ...

  S2: HTTP/1.1 101 ...
  S2: ...

  C3: %x8F <cnonce-3> <m-bytes of garbage>
       ...
  Cn: <cnonce-n> <reverse-masked content producing: "GET ...">

Claims:

  1. That an intermediate proxy will skip the garbage bytes between C3 
and Cn and execute the "GET" request (as Willy has repeatedly pointed 
out, because of framing, a proxy cannot behave like this.)

  2. That a reverse-masked Cn can even be produced.

Since no-one has attempted to justify claim #1, instead handwaving over 
it, and skipping over to more comfortable discussion of cryptography, it 
looks to me like Willy's points about #1 aren't even understood by the 
people arguing for strong crypto.

Making the garbage bytes look even more garbage-like doesn't actually 
make the protocol more secure; it's just political theater.

-- Scott

---

From: Adam Barth <[email-masked]>
Date: Tue, 11 Jan 2011 17:17:22 -0800

On Tue, Jan 11, 2011 at 5:07 PM, Scott Ferguson <[email-masked]> wrote:
>>> there's
> Looking under the streetlight for your keys because it's well lit there is
> not an effective technique.
>
> justify changing the problem. In this case, there has been no justification
> that Eric's streetlight is the same problem as websockets.
>
>  1. That an intermediate proxy will skip the garbage bytes between C3 and Cn
> and execute the "GET" request (as Willy has repeatedly pointed out, because
> of framing, a proxy cannot behave like this.)
>
> Since no-one has attempted to justify claim #1, instead handwaving over it,
> and skipping over to more comfortable discussion of cryptography, it looks
> to me like Willy's points about #1 aren't even understood by the people
> arguing for strong crypto.

I understand Willy's points, however they require me to make more
assumptions about the world in order to conclude that the protocol is
secure.  Those additional assumptions could either be correct or
incorrect, and we could invest in figuring that out, or we could just
use an approach that doesn't require us to make those assumptions in
the first place.

> Making the garbage bytes look even more garbage-like doesn't actually make
> the protocol more secure; it's just political theater.

I respectfully disagree.  It's much easier to reason about the
security of pure randomness.  That doesn't mean I have an attack on
Willy's design.  That means we have more reason to believe the
AES-128-CTR design is secure.  This is how security works.

Adam

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 17:18:12 -0800

On Jan 11, 2011, at 4:30 PM, Bruce Atherton wrote:

> That is fair. But there are other design considerations that have been identified as desirable with Websockets than security. Simplicity of implementation is one. Efficiency is another. Minimizing inconvenience to users yet another.

AES-CTR is performant, widely available, and easy to use through popular libraries. It's also more performant than the more secure XOR approach..

> 
> When two goals come into conflict, one has to find a balance between them. If Websockets were the only protocol on the Internet, it could be arguable that security should come before all other goals. Even if Websockets were the only way to create a Javascript-controlled connection from the browser it may make sense to argue that.
> 
> But there is already the ability to create HTTP connections via XMLHttpRequest. Once Websockets is more secure than that, the benefit to making it more secure dwindles. At that point, other design goals should be given a much more equal weight.

There is no way (other than WebSocket) to use browser APIs to make a full duplex connection. Browser implementors have a goal of not increasing security attack surface, even if the vulnerabilities might be in some theoretical sense someone else's fault. Since WebSocket has capabilities that HTTP does not, it needs greater restrictions than HTTP. HTTP also has legacy constraints that WebSocket does not. When designing security for WebSocket, we can get it right in the first place, and not be saddled with a problematic legacy design later.

Regards,
Maciej

---

From: Bruce Atherton <[email-masked]>
Date: Tue, 11 Jan 2011 18:59:20 -0800

> AES-CTR is performant, widely available, and easy to use through popular libraries. It's also more performant than the more secure XOR approach..

Sorry, but even a little concrete complexity in implementation for 
totally abstract security benefits that might, some day in some way no 
one can figure out, be beneficial seems like a bad deal to me. It 
strikes me as a huge assumption that there will be AES-CTR libraries on 
all the platforms that people want to deploy Websocket clients and 
servers to, as well.

Leaving aside whether plain XOR of random frame-key based masking is 
more efficient, there is also the efficiency issue of intermediaries 
being forced to unmask and remask when they otherwise wouldn't have to.

As for inconvenience, it doesn't strike me as worth a single hour of a 
single user's time in a government or lawyer's office, let alone giving 
up the ability to efficiently analyze decoded streams.

Eric is right, though, that is just my opinion. If you think the vague 
possibility it may be beneficial someday is worth making others suffer 
like that, so be it.

> There is no way (other than WebSocket) to use browser APIs to make a full duplex connection.

People misuse HTTP to do it all the time.

>   Browser implementors have a goal of not increasing security attack surface, even if the vulnerabilities might be in some theoretical sense someone else's fault.

Yes, I get this. I have argued the point myself on several occasions. 
And browser implementors are an important constituency. They are not the 
only constituency, though. If only their issues are taken into 
consideration in the design, then Websockets will well and truly suck as 
a protocol for those who use it.

I don't understand how this issue affects browser implementors, though. 
The difference between Websockets and long polled HTTP connections is 
that Websockets is by design a bidirectional protocol, rather than a 
hack to achieve the same behaviour on a request/response protocol. How 
exactly does that change the security attack surface in any way that can 
justify the costs?

>   Since WebSocket has capabilities that HTTP does not, it needs greater restrictions than HTTP.

Which capabilities are you referring to that are relevant to this issue?

>   HTTP also has legacy constraints that WebSocket does not. When designing security for WebSocket, we can get it right in the first place, and not be saddled with a problematic legacy design later.

Sorry, but you are saddled with legacy design. HTTP isn't going 
anywhere. XMLHttpRequest isn't going anywhere.

Making Websockets the gold standard in secure protocols while you toss 
all the other requirements out the window is useless because HTTP will 
always provide an attack surface. Websockets doesn't have to outrun the 
bear, it only has to outrun its friend HTTP.

---

From: Bruce Atherton <[email-masked]>
Date: Tue, 11 Jan 2011 20:05:33 -0800

On 11/01/2011 6:59 PM, Bruce Atherton wrote:
>
> I don't understand how this issue affects browser implementors, 
> though. The difference between Websockets and long polled HTTP 
> connections is that Websockets is by design a bidirectional protocol, 
> rather than a hack to achieve the same behaviour on a request/response 
> protocol. How exactly does that change the security attack surface in 
> any way that can justify the costs?

Let me retract this portion of my statement. I am not a browser 
implementor or a specialist on security. If you tell me that it affects 
the attack surface, I believe you.

But given that the enhanced cryptography does not address even a 
hypothetical attack, nor is there any indication it would have any 
bearing on these new types of attacks that Websockets might expose, I 
still don't believe they are worth giving up even one concrete benefit.

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 20:38:14 -0800

On Jan 11, 2011, at 6:59 PM, Bruce Atherton wrote:

> Sorry, but even a little concrete complexity in implementation for totally abstract security benefits that might, some day in some way no one can figure out, be beneficial seems like a bad deal to me. It strikes me as a huge assumption that there will be AES-CTR libraries on all the platforms that people want to deploy Websocket clients and servers to, as well.

The additional complexity is essentially 0. AES-CTR is implemented in libcrypto, which is part of OpenSSL, which is available everywhere. It came out of the box on my OS and took me all of 10 minutes to figure out.

> 
> Leaving aside whether plain XOR of random frame-key based masking is more efficient, there is also the efficiency issue of intermediaries being forced to unmask and remask when they otherwise wouldn't have to.

Not a difference between XOR and AES.

> 
> As for inconvenience, it doesn't strike me as worth a single hour of a single user's time in a government or lawyer's office, let alone giving up the ability to efficiently analyze decoded streams.

Also not a difference between XOR and AES.

> 
> Eric is right, though, that is just my opinion. If you think the vague possibility it may be beneficial someday is worth making others suffer like that, so be it.

Your objections seem to be baed on false assumptions

> People misuse HTTP to do it all the time.

There's no way you can use any HTTP API in the browser to create an actual full duplex connection.

> Yes, I get this. I have argued the point myself on several occasions. And browser implementors are an important constituency. They are not the only constituency, though. If only their issues are taken into consideration in the design, then Websockets will well and truly suck as a protocol for those who use it.

I'm not asking you to take only those concerns into consideration. I'm asking you not to reject them just because they are not as important to you personally.

> 
> I don't understand how this issue affects browser implementors, though. The difference between Websockets and long polled HTTP connections is that Websockets is by design a bidirectional protocol, rather than a hack to achieve the same behaviour on a request/response protocol. How exactly does that change the security attack surface in any way that can justify the costs?

See Adam and Eric's paper for one example of how it makes a difference.

> Which capabilities are you referring to that are relevant to this issue?

Two would be:
- Full duplex messaging.
- Ability to connect to non-same-origin servers without the same restrictions as HTTP.

If WebSocket didn't have any new capabilities, there would be no point to doing it.

> Sorry, but you are saddled with legacy design. HTTP isn't going anywhere. XMLHttpRequest isn't going anywhere.
> 
> Making Websockets the gold standard in secure protocols while you toss all the other requirements out the window is useless because HTTP will always provide an attack surface. Websockets doesn't have to outrun the bear, it only has to outrun its friend HTTP.

Past mistakes are no excuse for shoddy design.

Regards,
Maciej

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 20:50:23 -0800

On Jan 11, 2011, at 8:05 PM, Bruce Atherton wrote:

> Let me retract this portion of my statement. I am not a browser implementor or a specialist on security. If you tell me that it affects the attack surface, I believe you.
> 
> But given that the enhanced cryptography does not address even a hypothetical attack, nor is there any indication it would have any bearing on these new types of attacks that Websockets might expose, I still don't believe they are worth giving up even one concrete benefit.

We really have three options being considered, not two. Here are the pros and cons:

1) XOR using a mask entirely in the frame.

Pro:
- Fastest option.
- No per-connection state.
- Trivial to implement by hand.

Con:
- Does not provide protection in the "use HTTP to attack a WebSocket server" scenario.
- Creates obvious correlations between bytes in messages. This makes security analysis weaker.

2) XOR using a mask computed using HMAC from server and client nonces and a per-frame key

Pro:
- Provides protection in the "use HTTP to attack a WebSocket server" scenario.
- Widely available in popular libraries (but you have to implement the XOR part yourself).

Con:
- Slowest option.
- Requires a small amount of per-connection state to decode.
- Creates somewhat less obvious correlations between bytes in messages. This makes security analysis weaker.

3) AES-CTR, using a key computed using HMAC from client and server nonces and random counter per frame

Pro:
- Makes output indistinguishable from random. This has the best provable security properties.
- Provides protection in the "use HTTP to attack a WebSocket server" scenario.
- Second-fastest option.
- Widely available in popular libraries.

Con:
- Requires a small amount of per-connection state to decode.
- Uses a crypto algorithm, though for non-crypto purposes; may be subject to export regulations.

I consider #1 a nonstarter, because it does not defend against all the threat models that masking can help with. Between 2 and 3, 3 is clearly technically superior. The only argument against it, relative to #2, is the non-technical argument from export regulations.

The recently published -04 draft includes a variant on #2 (except that it uses plain SHA1 instead of HMAC to compute the mask for some reason).

Regards,
Maciej

---

From: "Thomson, Martin" <[email-masked]>
Date: Wed, 12 Jan 2011 13:24:51 +0800

I'm not sure that you've been clear enough in defining how 2 works.  Otherwise, a good summary.

> 1) XOR using a mask entirely in the frame.

I assume that you mean something like:

   for (int i = 0; i < frame.length; ++i) {
      data += read() ^ frame.mask[i % MASK_LENGTH];
   }

> 2) XOR using a mask computed using HMAC from server and client nonces

Is this the method that I saw that generates a pseudorandom sequence using HMAC? 

A)  sessionKey = HMAC-SHA1(uid, client-nonce || server-nonce);
   ...
   for (int blockStart = 0; blockStart < remainingLength; blockStart += 20) {
      mask = HMAC-SHA1(sessionKey, per-frame-key || blockStart);
      for (int i = 0; i < 20 && blockStart + i < remainingLength; ++i) {
         remainingPayload[blockStart + i] ^= mask[i];
      }
   }

Or the cut-down version of the same that is closer to option 1 in performance (computational overhead is the same):

B) sessionKey = HMAC(uid, client-nonce || server-nonce);
   ...
   mask = HMAC(sessionKey, per-frame-key);
   for (int i = 0; i < length; ++i) {
      payload[i % HMAC_LEN] ^= mask[i % HMAC_LEN];
   }

I couldn't work this out because you seem to be claiming the drawbacks of both (computational overhead and correlation problems).  The first has the computational cost, the second has the correlation problems.

> nonces and random counter per frame

...using a key generated by HMAC of client and server nonces and a random _IV_ on each frame.

The state that 2 and 3 maintain are a session key.  They also maintain the AES or HMAC state while they are receiving a message, but that's pitifully small in comparison to the other stuff they have to hold, like a typical receive buffer.

--Martin

---

From: John Tamplin <[email-masked]>
Date: Wed, 12 Jan 2011 00:47:07 -0500

> The state that 2 and 3 maintain are a session key.  They also maintain the AES or HMAC state while they are receiving a message, but that's pitifully small in comparison to the other stuff they hav…

To do it fast, I think in at least the HMAC case you want to hold the
HMAC state after having applied the client/server nonces to make it
faster.

-- 
John A. Tamplin
Software Engineer (GWT), Google

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 12 Jan 2011 07:23:19 +0100

On Tue, Jan 11, 2011 at 01:35:14PM -0800, Maciej Stachowiak wrote:
> I don't think anyone has demonstrated that export regulations are a practical problem in any way. Do software implementations of other IETF protocols that use crypto get restricted in practice? Is there any software product that has been unable to ship?

I have no idea however I think that the simple fact we're discussing it here
indicates that some implementers will also raise the concern when it becomes
their turn.

> Any number of commercial vendors and open source projects ship strong crypto all over the world,

That's a gratuitous statement, you don't necessarily know what products are
shipped where and with what options. It is possible that in some countries,
such products are required to have a check box to turn the crypto off.

> so I simply don't believe there is a real problem here. Can you cite any instance where it has created a real problem?

I can't, but I'm basing my reasoning on what's written :
  - there are regulations related to crypto exportation, eventhough we believe
    they can be relaxed in some situations or for some usages such as ours ;

  - we have absolutely no need for crypto, we're adding that in order to ensure
    that someone who's able to make a browser emit tens of thousands of
    connections and many megabytes of data will not be caught sending
    something that looks like an HTTP request nobody cares about. Instead,
    with crypto we'd like it to only be able to send that request after a
    few gigabytes of data.

Also, can you cite an example where a data posted after some garbage has created
a problem with an HTTP intermediary ?

Willy

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 12 Jan 2011 07:35:55 +0100

Hi Adam,

> AES-128-CTR design is secure.  This is how security works.

In order for AES-128-CTR to be more secure, we'd need to show that
intermediaries that are vulnerable to the simpler XOR-based masking
aren't vulnerable to the AES-128-CTR based masking.

I've shown that by sending tens ouf thousands of connections and a
few megabytes of data, we could make one 32-bit pattern looking like
and HTTP request for a known proxy (Apache). I've shown that we can
get the same pattern with AES-128-CTR without knowing the key after
a few gigabytes of data on a single connection.

I see no justification as to why if some proxy is vulnerable to the
first one, it's not to the second one.

However, if a proxy is not vulnerable to the first one, it's not to
the second one either. No proxies are known to be vulnerable to the
first one at all (and specs would make that very difficult).

So we have all elements to think that both are equally safe with
regards to the issue raised since the attacker does not control
the emitted stream. So unless someone can demonstrate the case
above, I'd really like that we stay on the simpler and less
expensive 32-bit key XOR-based masking, acceptably a changing
key if that makes one feel more comfortable.

Thanks,
Willy

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 12 Jan 2011 07:45:59 +0100

> - Does not provide protection in the "use HTTP to attack a WebSocket server" scenario.

This one is not related at all. If you can manipulate your crypto API to send
the Sec-* headers and manipulate the stream, then you have all is needed to
build a valid WS client and nothing blocks you from using the other algos as
well.

Also, the Sec-* headers were used for that purpose, so if you think they're
useless here, it should be raised as a separate concern, maybe we should get
rid of them then (though I think they're cheap).

> - Provides protection in the "use HTTP to attack a WebSocket server" scenario.

I disagree (see above)

> - Provides protection in the "use HTTP to attack a WebSocket server" scenario.

I disagree (see above)

> - Uses a crypto algorithm, though for non-crypto purposes; may be subject to export regulations.

- quite CPU-intensive for simple stream facing components which will have to
  handle multiple streams.

Willy

---

From: Bjoern Hoehrmann <[email-masked]>
Date: Wed, 12 Jan 2011 07:54:53 +0100

>- Provides protection in the "use HTTP to attack a WebSocket server" scenario.

You are assuming an attacker has enough control over a HTTP client to
convince the server it actually is a Websocket client, and send data
after the server agreed to switch protocols, but not enough control to
set the client nonce and read out the server nonce.

The server needs the client nonce in order to complete the handshake
during normal operation; you might say it's buggy and defaults to zero
if there is no client nonce, but that can happen either way. So it seems
the attacker would know or could infer or find out the client nonce.

So mix the frame key with something derived from the server nonce and
all your three options are the same as far as this point is concerned.
-- 
Björn Höhrmann · mailto:[email-masked] · http://bjoern.hoehrmann.de
Am Badedeich 7 · Telefon: +49(0)160/4415681 · http://www.bjoernsworld.de
25899 Dagebüll · PGP Pub. KeyID: 0xA4357E78 · http://www.websitedev.de/

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 23:29:20 -0800

> all your three options are the same as far as this point is concerned.

I agree that mixing the frame key with something derived from the server nonce is sufficient. I can see how to apply this to options 2 and 3, but in option 1 it doesn't happen, by definition. Perhaps someone cares to make a proposal that uses a different algorithm for mixing.

Regards,
Maciej

---

From: Maciej Stachowiak <[email-masked]>
Date: Tue, 11 Jan 2011 23:45:25 -0800

>      data += read() ^ frame.mask[i % MASK_LENGTH];

Something like that.

> I couldn't work this out because you seem to be claiming the drawbacks of both (computational overhead and correlation problems).  The first has the computational cost, the second has the correlati…

I meant (B). It does have measurably more computational overhead than the others, as shown by the testing various people did. Computing one HMAC per frame is pretty expensive when you have many small frames. (A) would have more overhead for large frames, but indeed, would not have the correlation problem. I didn't think that had been proposed.

> The state that 2 and 3 maintain are a session key.  They also maintain the AES or HMAC state while they are receiving a message, but that's pitifully small in comparison to the other stuff they hav…

Indeed.

Regards,
Maciej

---

From: Dave Cridland <[email-masked]>
Date: Wed, 12 Jan 2011 10:31:47 +0000

On Tue Jan 11 21:35:14 2011, Maciej Stachowiak wrote:
> I don't think anyone has demonstrated that export regulations are a  
> practical problem in any way. Do software implementations of other  
> IETF protocols that use crypto get restricted in practice? 

Those protocols actually require crypto for more than just politics,  
but yes, we need to restrict them (or restrict their export). They  
count as Dual-Use items, and are under export controls for any EU  
member state, including the UK, as I understand things.

So we can (and do) ship TLS anywhere, but we must (and do) restrict  
it. Similarly for other cryptographic protocols, like X.500, SASL,  
etc.

> Is there any software product that has been unable to ship?

We certainly have to ship with a licensing system which allows us to  
ship without strong cryptography (including AES) enabled, and it must  
be disabled by default, and we are unable to ship a license which  
isn't node-locked and has high-grade cryptography on, as I understand  
things. I think most of these decisions were made for the avoidance  
of doubt, mind - but in any case, we are unable to ship the licenses  
enabling "high grade cryptography" everywhere.

Now, whether this particular case consistutes cryptography, and  
whether we could convince the ECO that this case is exempt, is  
another matter.

I'd note that the actual regulation that covers the EU says this (in  
its definitions of dual-use technology and software, this is  
5A002.a.1 of Council Regulation 1334/2000):

"""
1. designed or modified to use ‘cryptography’ employing
digital techniques performing any cryptographic
function other than authentication or digital signature
having any of the following:

Technical notes:

1. Authentication and digital signature functions
include their associated key management function.

2. Authentication includes all aspects of access control
where there is no encryption of files or text except
as directly related to the protection of passwords,
Personal Identification Numbers (PINs) or similar
data to prevent unauthorised access.

3. ‘Cryptography’ does not include ‘fixed’ data
compression or coding techniques.

[...]

a. a ‘symmetric algorithm’ employing a key length
      in excess of 56 bits; or

[...]
"""

Now the point (3) in the technical note might apply - the rest  
certainly don't - because 'Fixed' is defined as:

"""
‘Fixed’ (5) means that the coding or compression algorithm cannot  
accept
externally supplied parameters (e.g., cryptographic or key variables)  
and cannot
be modified by the user.
"""

But the keying *can* be influenced by the user, by, from our  
perspective, controlling the browser's nonce selection. From the  
browser implementor's viewpoint, the server's nonce can modify the  
key. In addition, the plaintext (as I understand things) would also  
influence the keying.

It seems reasonable, to me, to suppose that this means we could could  
use AES-CTR based masking, but only if the keying were in some way  
fixed, which rather disables the point. Arguably, we can't actually  
use any symmetric algorithm (including XOR) with a key length greater  
than 56 bits. Stating the bleeding obvious, that's 7 octets mask  
length. This suggests that if we have to have masking - and I remain  
in much doubt that this is the best solution - then a 32-bit XOR is a  
more sensible choice - especially given Willy's argument that this is  
sufficient.

Of course, it goes without saying that I'm no lawyer - in fact, I'd  
much rather this weren't the case, and we could ship crypto  
everywhere without constraint (it'd reduce my support load  
substantially). Neither am I willing to risk the export license my  
employer has, however, so I'm cautious in my reading of this.

Dave.
-- 
Dave Cridland - mailto:[email-masked] - xmpp:[email-masked]
  - acap://acap.dave.cridland.net/byowner/user/dwd/bookmarks/
  - http://dave.cridland.net/
Infotrope Polymer - ACAP, IMAP, ESMTP, and Lemonade

---

From: Dave Cridland <[email-masked]>
Date: Wed, 12 Jan 2011 10:50:36 +0000

> a problem with an HTTP intermediary ?

You're not in the spirit of this, you know.

The intermediaries the working group has apparently chosen to protect  
from the naughty browsers are more broken than any we can conceive  
of. Since, when reading these words, we know and understand them, it  
follows that such an intermediary must either exist in reality *and*  
our understanding, or else it exists solely in our understanding -  
yet to be more broken than that which we can conceive it must exist  
in reality, since otherwise we could conceive of something more  
broken. Therefore, the broken intermediaries exist.

I'm surprised you even question such watertight logic.

Dave.

---

From: Bjoern Hoehrmann <[email-masked]>
Date: Wed, 12 Jan 2011 11:57:42 +0100

* Maciej Stachowiak wrote:
>I agree that mixing the frame key with something derived from the server
>nonce is sufficient. I can see how to apply this to options 2 and 3, but
>in option 1 it doesn't happen, by definition. Perhaps someone cares to
>make a proposal that uses a different algorithm for mixing.

If you think your hypothetical setup is something that must be addressed
then you should propose a requirement to that end. We can then find some
consensus around the proposed requirements and design a protocol that
addresses them. With protecting intermediaries we've gone from "Surely
that would be a bug in the proxy" to "let's do this trivial thing to
maybe throw off proxies" to "let's do this more elaborate thing to throw
off proxies" to "let's prevent the attacker from controlling the bytes"
to "but that doesn't make the protocol look like entirely random noise!"
so making proposal after proposal does not seem like a good way to make
progress.

Your scenario assumes that some of the components involved have bugs. I
could now say use this algorithm to reduce the server nonce to the size
of the frame key and this other algorithm to mix the two for each frame.
Then someone will point out the nonce X will compute to something that
makes the mixing have no effect, so servers will use that to avoid the
overhead. And then someone will propose browser's reject X as nonce, or 
propose different algorithms where the odds of someone finding X are
worse, and then someone might respond, if other X values are found they
could just be added in browser updates, and so on. Without an agreement
that the initial setup is something we should worry about to begin with.
-- 
Björn Höhrmann · mailto:[email-masked] · http://bjoern.hoehrmann.de
Am Badedeich 7 · Telefon: +49(0)160/4415681 · http://www.bjoernsworld.de
25899 Dagebüll · PGP Pub. KeyID: 0xA4357E78 · http://www.websitedev.de/

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 12 Jan 2011 11:59:11 +0100

> broken. Therefore, the broken intermediaries exist.

Then care to explain me why we agree they are vulnerable to several
megs of garbage but not to one gig of garbage ?

What drives me nuts is that we first choose a crypto algo then find
what type of imaginary intermediary might be vulnerable to something
just below our level of protection but not above.

If we identify a vulnerability, then we must offer real protection
even if we don't like it (eg: base64 encoding), but not something
slightly better but far more complex.

I'm clearly not for using base64 because I'm certain the supposed
vulnerability does not exist at all. For the same reason, I'm much
convinced that your proposed workaround with the CONNECT at the
beggining is far more than enough. But if we decide the vulnerability
exists, then we must address it to the level we imagine it. That
means : no CR/LF in the stream. Period.

Regards,
Willy

---

From: Patrick McManus <[email-masked]>
Date: Wed, 12 Jan 2011 10:24:33 -0500

>  one 32-bit pattern looking like
> and HTTP request for a known proxy (Apache).

I don't understand why "GET\n" is interesting in a proxy scenario.
Without a host header exactly what host is the server going to be able
to spoof in the cache? The paper that this is all based on discusses
mismatches between host headers and ip addresses of the connection.

The only thing I can figure is you are saying that a "GET\n" might
translate into "GET / HTTP/1.0\r\nhost: previous-request" but that would
require inserting the previous request as well.

what am I missing?

---

From: Dave Cridland <[email-masked]>
Date: Wed, 12 Jan 2011 15:29:58 +0000

> mismatches between host headers and ip addresses of the connection.
That's not the reasoning for the masking, though. The masking is  
proposed as a panacea for any attack based on a proxy interpreting  
the data as HTTP traffic.

Merely stopping these can be achieved by the means described (and  
tested) in the paper.

Dave.

---

From: Willy Tarreau <[email-masked]>
Date: Wed, 12 Jan 2011 17:10:03 +0100

On Wed, Jan 12, 2011 at 10:24:33AM -0500, Patrick McManus wrote:
> to spoof in the cache?

The proxy's default host. For example, the hosting provider's site
or default site. Since it worked on my Apache reverse proxy, I don't
see why we should dismiss it as a valid case. What Apache does is
rewrite the request as a complete one with a real Host header.

> The paper that this is all based on discusses

No, it sets "GET / HTTP/1.1\r\nHost: <default-host>\r\n\r\n".

Regards,
Willy

---

From: Bruce Atherton <[email-masked]>
Date: Wed, 12 Jan 2011 09:52:19 -0800

> - Creates obvious correlations between bytes in messages. This makes security analysis weaker.

As I said in another thread, the con about protecting against an HTTP 
attack requires the feature that the mask is influenced by the server 
nonce. But that can be done by generating the mask of the first frame 
based on the server nonce. Or, if you prefer, to combine the client 
nonce and the server nonce. Make it a requirement in the spec that the 
server check the frame key of the first frame to ensure it is so influenced.

The downside to this approach is that you lose the ability to force the 
server to check that the mask is influenced by the server nonce. You 
could use another method to force that check if it was truly needed, but 
doing so would introduce a bit more complexity so if it could be avoided 
altogether it would be best. The upside is that people can decode 
streams without having to be capturing them from the beginning. To me, 
that is a huge benefit that outweighs the small but real cost.

Yes, you do lose a bit on the abstract security guarantees. But as I 
said, I'll take a concrete benefit over an abstract cost every time.

> - Creates somewhat less obvious correlations between bytes in messages. This makes security analysis weaker.

It is not the amount of state that it is the problem, it is the timing 
of it. Since the state is only transmitted at the beginning of the 
connection, you lose the ability to capture anything once the connection 
is created. This is a pain point.

> - Uses a crypto algorithm, though for non-crypto purposes; may be subject to export regulations.

I think you forgot the con - "Not universally available in all languages 
in a library". To me, that is pretty big one. It is going to slow 
adoption of Websockets if the barrier to entry is having a fully 
functional AES-CTR implementation available.

> I consider #1 a nonstarter, because it does not defend against all the threat models that masking can help with. Between 2 and 3, 3 is clearly technically superior. The only argument against it, re…

I think it is wrong to rule out a requirement on the basis that it is 
non-technical. Lots of requirements are non-technical. The issue of 
export regulations falls under the rubric of the requirement to keep 
barriers to adoption of Websockets as low as possible. Export 
regulations can impinge on that requirement.

Imagine if export regulations in all countries required that every 
company pay hundreds of thousands of dollars to export any AES-CTR 
application. Would you still claim that it was a "non-technical argument"?

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 11:28:47 -0800

On Jan 12, 2011, at 9:52 AM, Bruce Atherton wrote:

> As I said in another thread, the con about protecting against an HTTP attack requires the feature that the mask is influenced by the server nonce. But that can be done by generating the mask of the first frame based on the server nonce. Or, if you prefer, to combine the client nonce and the server nonce. Make it a requirement in the spec that the server check the frame key of the first frame to ensure it is so influenced.

How are you supposed to check that the client nonce was "influenced" by the server nonce, when the client nonce is random and mixed with the server nonce using a one-way hash, when you only get the output and not the client nonce? Your suggestion is mathematically impossible.

> 
> The downside to this approach is that you lose the ability to force the server to check that the mask is influenced by the server nonce. You could use another method to force that check if it was truly needed, but doing so would introduce a bit more complexity so if it could be avoided altogether it would be best. The upside is that people can decode streams without having to be capturing them from the beginning. To me, that is a huge benefit that outweighs the small but real cost.
> 
> Yes, you do lose a bit on the abstract security guarantees. But as I said, I'll take a concrete benefit over an abstract cost every time.

I think your suggestion removes all the benefit from using the server nonce as part of the masking key. You need to send the raw per-frame nonce but mask using a mix that includes the server key, to see any improvement.

> It is not the amount of state that it is the problem, it is the timing of it. Since the state is only transmitted at the beginning of the connection, you lose the ability to capture anything once the connection is created. This is a pain point.

Sure, I understand that per-connection state is a downside even if there is not much of it. That is why I listed it as a "con".

> I think you forgot the con - "Not universally available in all languages in a library". To me, that is pretty big one. It is going to slow adoption of Websockets if the barrier to entry is having a fully functional AES-CTR implementation available.

I think it's widely available enough that this is not a serious disadvantage, certainly not compared to HMAC.

> I think it is wrong to rule out a requirement on the basis that it is non-technical. Lots of requirements are non-technical. The issue of export regulations falls under the rubric of the requirement to keep barriers to adoption of Websockets as low as possible. Export regulations can impinge on that requirement.
> 
> Imagine if export regulations in all countries required that every company pay hundreds of thousands of dollars to export any AES-CTR application. Would you still claim that it was a "non-technical argument"?

I didn't claim that non-technical arguments are ruled out. I'm just pointing out that the technical arguments all go the other way. I think it would not be in line with IETF best practices to make a technically inferior choice based on the restrictive legal regimes in some countries. But you are right that at some point policy issues could outweigh technical issues.

Regards,
Maciej

---

From: John Tamplin <[email-masked]>
Date: Wed, 12 Jan 2011 14:39:40 -0500

On Wed, Jan 12, 2011 at 2:28 PM, Maciej Stachowiak <[email-masked]> wrote:

> How are you supposed to check that the client nonce was "influenced" by the
> server nonce, when the client nonce is random and mixed with the server
> nonce using a one-way hash, when you only get the output and not the client
> nonce? Your suggestion is mathematically impossible.
>

You could check that the server-nonce was used by the client only during the
handshake, such as in a Hello frame.  Wouldn't that still address your
concern, since pre-canned attack frames could only be used once a connection
was successfully established?

---

From: Bruce Atherton <[email-masked]>
Date: Wed, 12 Jan 2011 11:44:11 -0800

> build a valid WS client and nothing blocks you from using the other algos as

I agree, and being unable to send valid Sec- headers from a 
browser-based Javascript implementation of Websockets seems more secure 
to me than relying on masking.

It is true that in Maciej's HTTP attack, my understanding is that the 
server nonce cannot be retrieved directly from the response according to 
http://dev.w3.org/2006/waf/access-control/#simple-response-header. But 
assuming it can't be obtained in some other way seems far riskier than 
simply stopping required headers in the request from being present.

OTOH, I don't think that allowing the server nonce to influence the mask 
is that much of a hardship, so long as the mask is still the frame key.

> rid of them then (though I think they're cheap).

I have to admit, I wonder about that too. What is insecure about denying 
the ability to use Sec-* headers in the request? What should we be 
concerned about?

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 12:05:36 -0800

On Jan 12, 2011, at 11:39 AM, John Tamplin wrote:

> You could check that the server-nonce was used by the client only during the handshake, such as in a Hello frame.  Wouldn't that still address your concern, since pre-canned attack frames could only be used once a connection was successfully established?

Your description doesn't have enough detail for me to evaluate it. In what way would the server nonce be used during the handshake, and in what way do you check it?

Regards,
Maciej

---

From: Joel Martin <[email-masked]>
Date: Wed, 12 Jan 2011 14:20:20 -0600

>
> Bruce Atherton wrote:
> I think you forgot the con - "Not universally available in all languages in
> a library". To me, that is pretty big one. It is going to slow adoption of
> Websockets if the barrier to entry is having a fully functional AES-CTR
> implementation available.
>

+1

As a maintainer of both client (web-socket-js:
https://github.com/gimite/web-socket-js) and server (wsproxy:
https://github.com/kanaka/noVNC/tree/master/utils) Websockets
implementations, AES-CTR will certainly be a hassle both technically and due
to the legal uncertainty it adds. I think AES-CTR needs to be compelling for
the friction it will add.

Joel Martin

---

From: John Tamplin <[email-masked]>
Date: Wed, 12 Jan 2011 16:02:18 -0500

On Wed, Jan 12, 2011 at 3:05 PM, Maciej Stachowiak <[email-masked]> wrote:

> Your description doesn't have enough detail for me to evaluate it. In what
> way would the server nonce be used during the handshake, and in what way do
> you check it?
>

If we were to have Hello frames as have been suggested, in the client's
Hello frame it includes a value computed from the server's nonce.  The
server verifies that value to verify that the client processed it.

Granted, a lazy server implementor could skip that step.  But, we discarded
the amateur programmer requirement long ago, and you could equally say that
a lazy client could just use the same masking key every time, which would be
more damaging to secure operations.

---

From: Bruce Atherton <[email-masked]>
Date: Wed, 12 Jan 2011 13:46:05 -0800

> How are you supposed to check that the client nonce was "influenced" by the server nonce, when the client nonce is random and mixed with the server nonce using a one-way hash, when you only get the…

Sorry, I think we are talking about different things. Either that or I 
am completely missing the point you are raising.

What I said was that the server nonce could influence the mask, or, if 
you really needed the client nonce to also influence the mask (which 
last time I checked was the SHA1/HMAC behaviour) you could combine the 
server nonce and the client nonce in someway.

So if you just needed the server nonce to influence the mask, one of the 
simplest things you could do would be to just take the first 32 bits of 
it and use that as the first frame key from the client. If that wasn't 
random enough for you, you could hash the nonce in a known way, so that 
the server could check that the hash matched with the frame key it received.

If you wanted to add the client nonce into the mix, you could XOR the 
server nonce with the client nonce and take the first 32 bits, or hash 
the two of them together, and the server could do the same thing at the 
other end and verify that the results matched the frame key.

I don't really see the point of having the client nonce influence the 
mask, but it was part of the previous design so I mentioned it. I also 
don't care how the mask is influenced by the server nonce so long as it 
is repeatable by the server and the mask checked against the server 
result. Assuming you want to avoid this "HTTP emulating a Websocket 
client in Javascript" attack by using masking.

> I think your suggestion removes all the benefit from using the server nonce as part of the masking key. You need to send the raw per-frame nonce but mask using a mix that includes the server key, t…

Sorry, you've completely lost me here.

> I think it's widely available enough that this is not a serious disadvantage, certainly not compared to HMAC.

Fair enough, you are entitled to your opinion. It should still be listed 
as a con, though, if only so you can argue against its importance.

Obviously I do think this is a serious disadvantage. Think about how 
ubiquitous HTTP classes and functions are in standard libraries of 
languages all over the place. I think it would be desirable to have 
Websockets be as ubiquitous, but I think it will be much harder if 
accepting AES-CTR as a standard part of the language is a prerequisite.

As far as HMAC goes, I don't understand why this is necessary either. 
Any standard hashing function that generates a 32 bit key seems like 
plenty, if you don't want to use the raw bits.

> I didn't claim that non-technical arguments are ruled out. I'm just pointing out that the technical arguments all go the other way. I think it would not be in line with IETF best practices to make…

No, I think you misunderstand me.

I agree that when discussing how to design solutions, technical 
arguments should typically be given priority over nontechnical ones.

But when it comes to requirements, whether the requirements themselves 
are technical or not is of no importance. They are not all equal, of 
course, and sometimes the balance has to sway towards one requirement 
over another. But whether that requirement is based on a technical issue 
is not the reason to decide which requirement gets priority.

Let me give an example. When discussing framing, it was decided to use a 
63 bit length because Java didn't support 64 bit numbers easily. This 
wasn't technical, as Java could in fact support it with BigDecimal and 
the like. But it would be awkward. What is more, Java represents a 
significant market share of the types of people it would be hoped would 
use Websockets. So this decision about how to design a length field was 
primarily a non-technical one. If there had been a serious technical 
issue to prefer 64 bits over 63 bits, it would have been blown out of 
the water. But there wasn't, so it was allowed.

But when talking about Browser Vendors having to take responsibility for 
issues that are not their fault, minimizing the effect of that is a 
requirement. The fact that it is not a "technical" requirement (whatever 
that means) but is more political does not in any way undermine its 
importance.

I have a hard time differentiating requirements as technical or 
non-technical, btw. I've written a lot of legal software, and legal 
concerns seem pretty technical to me.

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 14:27:27 -0800

On Jan 12, 2011, at 1:02 PM, John Tamplin wrote:

> If we were to have Hello frames as have been suggested, in the client's Hello frame it includes a value computed from the server's nonce.  The server verifies that value to verify that the client processed it.
> 
> Granted, a lazy server implementor could skip that step.  But, we discarded the amateur programmer requirement long ago, and you could equally say that a lazy client could just use the same masking key every time, which would be more damaging to secure operations.

OK. The problem with this approach is the same as with other server checks that have no effect on normal operation. If the server's check is buggy, missing, or overly lenient, this won't be noticed in normal operation. Masking can provide better protection than that - if you don't compute the mask correctly, then you will fail in the normal non-attack case. Since there is one and only one way to compute the correct mask, there's no possibility of accidentally being too lenient but still working in the normal case. I think this is a robust design. If we are to use masking anyway, then I think the marginal cost to providing this robustness is low.

Regards,
Maciej

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 14:43:39 -0800

On Jan 12, 2011, at 1:46 PM, Bruce Atherton wrote:

> Sorry, I think we are talking about different things. Either that or I am completely missing the point you are raising.
> 
> What I said was that the server nonce could influence the mask, or, if you really needed the client nonce to also influence the mask (which last time I checked was the SHA1/HMAC behaviour) you could combine the server nonce and the client nonce in someway.
> 
> So if you just needed the server nonce to influence the mask, one of the simplest things you could do would be to just take the first 32 bits of it and use that as the first frame key from the client.

That would fail to protect against the intermediary attack - the server (assumed untrusted) can control the client's first mask, so it can choose the plaintext of the first frame.

> If that wasn't random enough for you, you could hash the nonce in a known way, so that the server could check that the hash matched with the frame key it received.

Just hashing the nonce still lets the attacher control the plaintext. They know what the server nonce will hash too.

> 
> If you wanted to add the client nonce into the mix, you could XOR the server nonce with the client nonce and take the first 32 bits,

This is still vulnerable in the case of the intermediary attack. The server can choose its nonce to neutralize the client nonce.

> or hash the two of them together, and the server could do the same thing at the other end and verify that the results matched the frame key.

This is also vulnerable in the case of the intermediary attack. The server can tell client script what the hash of the server and client nonce is, before the client sends its first frame. Then the client knows how to invert the masking to send chosen plaintext.

> 
> I don't really see the point of having the client nonce influence the mask, but it was part of the previous design so I mentioned it. I also don't care how the mask is influenced by the server nonce so long as it is repeatable by the server and the mask checked against the server result. Assuming you want to avoid this "HTTP emulating a Websocket client in Javascript" attack by using masking.

All your proposals end up with a situation where the per-frame nonce doesn't influence the mask for the first frame, thus reintroducing the intermediary vulnerability. 

You need to involve both the server nonce and a per-frame nonce to protect against both the intermediary attack and the HTTP precomputed frame attack. And you need to send the per-frame nonce raw, not combined with the server nonce, so the server can independently redo the computation.

Regards,
Maciej

---

From: John Tamplin <[email-masked]>
Date: Wed, 12 Jan 2011 17:44:53 -0500

On Wed, Jan 12, 2011 at 5:27 PM, Maciej Stachowiak <[email-masked]> wrote:

> OK. The problem with this approach is the same as with other server checks
> that have no effect on normal operation. If the server's check is buggy,
> missing, or overly lenient, this won't be noticed in normal operation.
> Masking can provide better protection than that - if you don't compute the
> mask correctly, then you will fail in the normal non-attack case. Since
> there is one and only one way to compute the correct mask, there's no
> possibility of accidentally being too lenient but still working in the
> normal case. I think this is a robust design. If we are to use masking
> anyway, then I think the marginal cost to providing this robustness is low.
>

Others don't agree, as it means you can't interpret a frame without state
from the handshake, and introduces a much higher cost.

If we are worrying about poorly written servers, should we be worried about
poorly written clients that will just use a constant or incrementing counter
for the frame key?  What if the server doesn't actually verify the Origin
(which seems like a much bigger issue to me) -- we aren't doing anything
about that.

It still seems like we can get the property you want during the handshake
and using a less expensive mechanism on every frame.  For example, what if
we have Hello frames and they are encoded as you propose for every frame --
a server that doesn't use the values properly won't be able to issue a Hello
response, and the connection never gets initialized so the attack you are
worried about can never take place.

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 14:55:30 -0800

On Jan 12, 2011, at 2:44 PM, John Tamplin wrote:

> Others don't agree, as it means you can't interpret a frame without state from the handshake, and introduces a much higher cost.

I get that they don't agree. I disagree with their priorities. I'm just clearly stating my position. 

> 
> If we are worrying about poorly written servers, should we be worried about poorly written clients that will just use a constant or incrementing counter for the frame key?  What if the server doesn't actually verify the Origin (which seems like a much bigger issue to me) -- we aren't doing anything about that.

There is a small single-digit number of client implementations that will be exposed to the Web, and historically updating them has been much faster than updating all servers. This is why, for example, browsers try to defend against DNS rebinding even though it could be completely defeated by updating all Web servers to check the Host header. So in the long run, robustness against buggy servers is more important. That being said, I believe my preferred options are more robust against client-side programming errors as well.

> 
> It still seems like we can get the property you want during the handshake and using a less expensive mechanism on every frame.  For example, what if we have Hello frames and they are encoded as you propose for every frame -- a server that doesn't use the values properly won't be able to issue a Hello response, and the connection never gets initialized so the attack you are worried about can never take place.

It sounds like this would require an extra round trip to be effective, since only the client hello frame could present the proof that you are talking to a real WebSocket client. The client hello frame would also need to be variable length so the server can't just skip the first N bytes. I'd have to think more about whether this has other problems, in the meantime I have responded to the poll based on the proposals already on the table.

Regards,
Maciej

---

From: Bruce Atherton <[email-masked]>
Date: Wed, 12 Jan 2011 16:02:08 -0800

> That would fail to protect against the intermediary attack - the server (assumed untrusted) can control the client's first mask, so it can choose the plaintext of the first frame.

Ahh, now I understand what you are getting at. You are right. Because we 
are trying to do two different things with masking, the simplest 
solutions pull in two different directions. The intermediary attack 
needs random bits, and the cross site scripting attack is most easily 
dealt with using a mask generated from the server nonce.

Well, you could split the difference - half the bits from the server 
nonce and half random. I suspect you wouldn't like what that did to the 
increase in usefulness of brute-force attacks on the intermediary, 
though. The other thing you could do is to pull the verifiable 
server-nonce info into some other part of the data sent by the client, 
as John suggests with the HELLO frame. There are many other ways to do 
that, including using a Sec- header. Hmmm. Haven't we come full circle?

---

From: Bruce Atherton <[email-masked]>
Date: Wed, 12 Jan 2011 16:11:38 -0800

On 12/01/2011 2:55 PM, Maciej Stachowiak wrote:
>
> There is a small single-digit number of client implementations that 
> will be exposed to the Web, and historically updating them has been 
> much faster than updating all servers.

Whoa, where did this assumption come from?

There are a huge number of HTTP clients on the web. That is because it 
is so easy to create them using standard libraries in most languages. It 
is true that if Websockets requires the kind of overhead you are 
suggesting it is unlikely there will be that many clients around, but if 
we can keep it lightweight there is no reason to think people won't be 
generating Websocket clients quite regularly, although probably not as 
many as there are HTTP clients.

If it ends up just being single digit number of clients (namely just the 
major browsers), I would see that as a fail for Websockets.

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 17:04:00 -0800

On Jan 12, 2011, at 4:02 PM, Bruce Atherton wrote:

> Ahh, now I understand what you are getting at. You are right. Because we are trying to do two different things with masking, the simplest solutions pull in two different directions. The intermediary attack needs random bits, and the cross site scripting attack is most easily dealt with using a mask generated from the server nonce.
> 
> Well, you could split the difference - half the bits from the server nonce and half random. I suspect you wouldn't like what that did to the increase in usefulness of brute-force attacks on the intermediary, though.

That's effectively what the HMAC+XOR and AES-CTR proposals do, although they mix the bits in a cryptographically strong way, so it doesn't reduce the resistance to brute-force attacks in either direction.

> The other thing you could do is to pull the verifiable server-nonce info into some other part of the data sent by the client, as John suggests with the HELLO frame. There are many other ways to do that, including using a Sec- header. Hmmm. Haven't we come full circle?

I've explained why I don't think this is as robust as incorporating the server nonce into the mask. I think folks can make their own determination of whether this robustness is worthwhile.

Regards,
Maciej

---

From: Maciej Stachowiak <[email-masked]>
Date: Wed, 12 Jan 2011 17:05:39 -0800

On Jan 12, 2011, at 4:11 PM, Bruce Atherton wrote:

>> There is a small single-digit number of client implementations that will be exposed to the Web, and historically updating them has been much faster than updating all servers.
> 
> There are a huge number of HTTP clients on the web.

The vast majority them can't effectively be used for a "drive by" browsing attack, since users aren't using them to browse the Web. You are right that HTTP has non-browsing uses, but that's a completely different threat profile, because you can't force a victim user's system to act as the HTTP client.

Regards,
Maciej

---

From: Bruce Atherton <[email-masked]>
Date: Thu, 13 Jan 2011 09:18:42 -0800

> I agree that mixing the frame key with something derived from the server nonce is sufficient. I can see how to apply this to options 2 and 3, but in option 1 it doesn't happen, by definition. Perha…

Maciej, I thought I understood how your attack worked, but now I'm not 
so sure.

You are concerned that an attacker will be able to successfully open a 
Websocket connection and are worried that they can do their own masking 
to send whatever they want. So you want to use the server nonce, which 
is a secret that the attacker's javascript code doesn't know about, to 
generate the mask. Is that correct?

But in order to create the connection in the first place the attacker 
will have to provide a client nonce. And the server nonce is generated 
from the client nonce and a known GUID. So the attacker in fact will 
know the server nonce.

This means that masking offers no protection for this particular attack. 
Use random keys or AES-CTR, once the attacker knows the server nonce it 
is all over.

Can this be right? What am I missing?

---

From: John Tamplin <[email-masked]>
Date: Thu, 13 Jan 2011 12:31:05 -0500

On Thu, Jan 13, 2011 at 12:18 PM, Bruce Atherton <[email-masked]>wrote:

> But in order to create the connection in the first place the attacker will
> have to provide a client nonce. And the server nonce is generated from the
> client nonce and a known GUID. So the attacker in fact will know the server
> nonce.
>

As I understand it, the server nonce is random and the server acceptance is
based on the client nonce, server nonce, and a known GUID.  So a JS-only
attacker does not know the server nonce.

---

From: Willy Tarreau <[email-masked]>
Date: Thu, 13 Jan 2011 18:32:26 +0100

> Can this be right? What am I missing?

It seems so to me too. However, if the masking relied on a nonce emitted
by the server's hello frame, then that would probably be OK assuming that
the JS code can't get the return traffic.

Otherwise if we accept that the JS code controls sent traffic and return
traffic, then it simply becomes a complete WS client.

Willy

---

From: Maciej Stachowiak <[email-masked]>
Date: Thu, 13 Jan 2011 09:42:15 -0800

On Jan 13, 2011, at 9:31 AM, John Tamplin wrote:

> On Thu, Jan 13, 2011 at 12:18 PM, Bruce Atherton <[email-masked]> wrote:
> But in order to create the connection in the first place the attacker will have to provide a client nonce. And the server nonce is generated from the client nonce and a known GUID. So the attacker in fact will know the server nonce.
> 
> As I understand it, the server nonce is random and the server acceptance is based on the client nonce, server nonce, and a known GUID.  So a JS-only attacker does not know the server nonce.

That's correct. The server nonce is random, and therefore unknown to an attacker using HTTP APIs in the browser. The attacker cannot know the server nonce before sending the HTTP request (including its body), so if it is involved in masking, then it is impossible to precompute valid frames and stuff them in an HTTP body.

Regards,
Maciej

---

From: Bruce Atherton <[email-masked]>
Date: Thu, 13 Jan 2011 10:06:03 -0800

My mistake. I was reading the non-normative version of the handshake, 
and the only thing that looked like a server nonce was the Accept-Key.

Section 5.2.2 makes it clear that both a random nonce and the accept key 
are sent by the server.

On 13/01/2011 9:42 AM, Maciej Stachowiak wrote:
>> On Thu, Jan 13, 2011 at 12:18 PM, Bruce Atherton <[email-masked] 
>> <mailto:[email-masked]>> wrote:
>>
>>     But in order to create the connection in the first place the
>>     attacker will have to provide a client nonce. And the server
>>     nonce is generated from the client nonce and a known GUID. So the
>>     attacker in fact will know the server nonce.
>>
>>
>> As I understand it, the server nonce is random and the server 
>> acceptance is based on the client nonce, server nonce, and a known 
>> GUID.  So a JS-only attacker does not know the server nonce.
>
> That's correct. The server nonce is random, and therefore unknown to 
> an attacker using HTTP APIs in the browser. The attacker cannot know 
> the server nonce before sending the HTTP request (including its body), 
> so if it is involved in masking, then it is impossible to precompute 
> valid frames and stuff them in an HTTP body.
>
> Regards,
> Maciej
>

---

From: Greg Wilkins <[email-masked]>
Date: Fri, 14 Jan 2011 08:41:10 +1100

On 12 January 2011 08:35, Maciej Stachowiak <[email-masked]> wrote:
> I don't think anyone has demonstrated that export regulations are a practical problem in any way.

I don't think anyone has demonstrated that export regulations are an
insurmountable problem, but they are definitely a practical one.

> Do software implementations of other IETF protocols that use crypto get restricted in practice?

You have obviously never had to pay personally to jump (albeit low)
hurdles required for this.     As somebody that has worked in the past
for cash strapped startup I can definitely say that crypto export
requirements have caused considerable pain to me in the past.   Note
also that it is my experience that even just calling crypto APIs in
the JVM is enough to trigger the spooks to call the lawyers to make
you explain to your lawyers what you are doing.

It's not impossible - just painful and somewhat expensive (for
starving self funded startups at least ).
If there was a good reason for it, then the pain would be worth it.

---

From: Jamie Lokier <[email-masked]>
Date: Fri, 14 Jan 2011 03:53:44 +0000

> - Makes output indistinguishable from random. This has the best provable security properties.

No, it *doesn't* have the best provable security properties in all the
relevant ways that have been brought up.

I gather one of the objectives motivating AES-CTR is to prevent lax
intermediaries and HTTP servers from dubiously recognising HTTP
requests among a stream of random bytes on many connections?

Case-insensitive 'GET ' followed by an arbitrary string and a newline
occurs rather often in random bytes.  (Every 2^29 or so - it's really
quite poor if you have millions of active user connections.)

Case-insensitive anything-that-looks-like-it-might-be-a-HTTP-method
followed by whitespace, and a short
URL-not-fussy-if-it-contains-8bit-character and a newline occurs *way*
more often.

Often enough to hit at the start of the data in a predictable place if
you have a bit of JavaScript opening connections at the maximum rate
in multiple WebWorkers, unknown to the browser's user (who leaves the
page open all day).

Even Base64 is technically superior in *this* regard - and it blocks JS
browser attacks as well doesn't it?

Same goes for escaping newline characters and other variations on that
theme.

Not that I'm advocating Base64 or newline-escaping - just reminding,
that in this context what is good for encryption (it looks random) is
*not* necessarily best security in this context.

-- Jamie

---

From: Greg Wilkins <[email-masked]>
Date: Fri, 14 Jan 2011 18:20:54 +1100

Note also that with something like AES-CTR it will always be possible
for any non-evil payload to be masked into a legal HTTP request.

With a repeated XOR mask, the original data would need to have a
particular structure in it before it would end up looking like a
request.   Thus is probably far less likely to turn a non-evil payload
into an accidentally evil masked payload.

Off course all these evil and non-evil HTTP requests would still need
the intermediary to be accepting of bad HTTP responses and skip over
bad framing looking for a suitable match, so I don't think we have
much to worry about.

cheers

---

From: Jamie Lokier <[email-masked]>
Date: Fri, 14 Jan 2011 07:31:45 +0000

> bad framing looking for a suitable match, so I don't think we have

Indeed.  Though see the mail I just posted (different thread; same
list) discussing the feasabilitity of using large numbers of
connections, from large (but realistic) numbers of users, to cause an
evil request to appear at a known position near the beginning on one
of those connections.

If the masking occurs from the very first octets following the
HTTP-like handshake, and uses a key which can take all values
uniformly, the attacker doesn't even have to control the messages sent
by the client.  Just the fact that the first octets vary due to the
key is enough, with enough connections.

-- Jamie

---

From: Bjoern Hoehrmann <[email-masked]>
Date: Sun, 16 Jan 2011 02:26:02 +0100

>requests among a stream of random bytes on many connections?

As I understand it, the only attack against any of the schemes proposed
works equally well against all the proposals. The more elborate schemes
are being proposed because a couple of people think "maybe they help",
at a tremendous cost that people entirely unaffacted by the underlying
"problem" are not willing to pay for based on a few people's feelings.

Personally I share the "bad feeling" and assume the most simple masking
scheme is much weaker than the length of the per-frame key might
suggest, and I assume that there are far more, orders of magnitude more,
intermediaries that are vulnerable to attack than the paper by Adam et
al. suggests (based on my own reasoning, I've not seen the proponents of
more elaborate schemes offer much reasoning).

But so what? Even if you could prove exceedingly convincingly that an
attack that'd require 2 TB of traffic with the AES scheme would require
only 2 MB of traffic with the most simple scheme, why would that make me
think using some AES scheme for masking is the best protocol design? We
would still have no evidence or argument that it would make a difference
in practise, and we would still have other options at our disposal.
-- 
Björn Höhrmann · mailto:[email-masked] · http://bjoern.hoehrmann.de
Am Badedeich 7 · Telefon: +49(0)160/4415681 · http://www.bjoernsworld.de
25899 Dagebüll · PGP Pub. KeyID: 0xA4357E78 · http://www.websitedev.de/