Skip to content

PerMessageDeflateExtension *_no_context_takeover negotiation is faulty, leading to mismatch #1496

@robert-s-ubi

Description

@robert-s-ubi

Describe the bug
The PerMessageDeflateExtension#getProvidedExtensionAsClient() method unconditionally includes client_no_context_takeover and server_no_context_takeover in the extensions to send to the server, ignoring the clientNoContextTakeover and serverNoContextTakeover configuration variables.

The acceptProvidedExtensionAsServer() on the server will thus ALWAYS set its clientNoContextTakeover variable to true, but the acceptProvidedExtensionAsClient() does NOT update its clientNoContextTakeover configuration variable upon receiving this, leading to a mismatch.

As a result, the second compressed response the client receives from the server yields an exception:

org.java_websocket.exceptions.InvalidDataException: invalid distance too far back
at org.java_websocket.extensions.permessage_deflate.PerMessageDeflateExtension.decodeFrame(PerMessageDeflateExtension.java:193)
at org.java_websocket.drafts.Draft_6455.translateSingleFrame(Draft_6455.java:589)

To Reproduce
Steps to reproduce the behavior:

  1. Set up WebSocketClient and WebSocketServer with the PerMessageDelateExtension
  2. Connect them
  3. Send messages back and forth
  4. The client side will bail out at the second message it receives from the server

Example application to reproduce the issue
https://github.com/ChargeTimeEU/Java-OCA-OCPP was recently enhanced with WebSocket compression support, but it's broken due to this bug.

Expected behavior
Behavior must be as follows:

  1. getProvidedExtensionsAsClient() must add the extensions following the clientNoContextTakeover and serverNoContextTakeover configuration variables (i.e. leave them out if false).
  2. acceptProvidedExtensionsAsServer() must enable the clientNoContextTakeover and/or serverNoContextTakeover if their corresponding extensions are received, effectively ORing them with the locally configured settings.
  3. getProviderExtensionsAsServer() must add the extensions following the (potentially updated) clientNoContextTakeover and serverNoContextTakeover configuration variables (i.e. leave them out if false).
  4. acceptProvidedExtensionsAsClient() must enable the clientNoContextTakeover and/or serverNoContextTakeover if their corresponding extensions are received, effectively ORing them with the locally configured settings.

This ensures these configuration settings are always properly synchronized on both ends, and allows operation with context takeover on both ends (both configuration variables set to false on both ends), which maximizes the compression efficiency.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions