Uploaded image for project: 'OASIS Message Queuing Telemetry Transport (MQTT) TC'
  1. OASIS Message Queuing Telemetry Transport (MQTT) TC
  2. MQTT-6

What should a server do if it receives a connect packet with and incorrect protocol name?

    Details

    • Type: Improvement
    • Status: Closed
    • Priority: Major
    • Resolution: Fixed
    • Affects Version/s: 3.1.1
    • Fix Version/s: 3.1.1
    • Component/s: core
    • Labels:
      None
    • Proposal:
      Hide

      If the first data that the server receives is not an MQTT CONNECT packet, including the correct protocol name, then it MAY continue to process it
      as some other protocol, alternatively it MUST disconnect the TCP session without sending a CONNACK. The server MUST NOT continue to process a malformed initial packet in line with this specification.

      Non normative comment.
      A server can support multiple protocols by checking to see if the initial data it receives is a valid CONNECT packet or valid data for some other protocol such as an earlier version of the MQTT specification.

      Show
      If the first data that the server receives is not an MQTT CONNECT packet, including the correct protocol name, then it MAY continue to process it as some other protocol, alternatively it MUST disconnect the TCP session without sending a CONNACK. The server MUST NOT continue to process a malformed initial packet in line with this specification. Non normative comment. A server can support multiple protocols by checking to see if the initial data it receives is a valid CONNECT packet or valid data for some other protocol such as an earlier version of the MQTT specification.
    • Resolution:
      Hide

      Updated in WD08.

      Show
      Updated in WD08.

      Description

      What should a server do if it receives a connect packet with and incorrect protocol name?

      If the server receives a connect packet with no MQIsdp field present ( or its replacement field) The server could.
      1) Disconnect the Clients TCP session
      2) Return CONNACK RC=X01, then disconnect the clients TCP session.
      3) Return CONNACK with some new return code and then disconnect the clients TCP session.

        Attachments

          Activity

          Hide
          knolleary Nick O'Leary (Inactive) added a comment -

          The protocol the client is using is identified in the connect packet by the combination of both the protocol name and protocol version number.

          If either is missing then the packet is not properly encoded and the server should treat it as it would any other badly formed MQTT packet - drop the connection with no feedback sent.

          If both are present, but either one is not recognised or supported, then that is what return code "0x01 - Unacceptable Protocol Version" was intended for. It may call it say 'protocol version' in its name, but I believe the intent was it cover both version and name.

          Show
          knolleary Nick O'Leary (Inactive) added a comment - The protocol the client is using is identified in the connect packet by the combination of both the protocol name and protocol version number. If either is missing then the packet is not properly encoded and the server should treat it as it would any other badly formed MQTT packet - drop the connection with no feedback sent. If both are present, but either one is not recognised or supported, then that is what return code "0x01 - Unacceptable Protocol Version" was intended for. It may call it say 'protocol version' in its name, but I believe the intent was it cover both version and name.
          Hide
          peterniblett Peter Niblett (Inactive) added a comment -

          This issue is connected with MQTT-8 (which talk about malformed connect packets), MQTT-15 (protocol names and version numbers) and MQTT-5 (reserved bits in Connect).

          It seems to me that we have several kinds of "bad" Connect packet:

          i) Something that isn't really an MQTT Connect at all - it's either a packet from a different protocol that arrives because of an innocent configuration error, or it's the result of some kind of malicious DoS attack

          ii) An MQTT Connect from a different version of the protocol (either older or newer)

          iii) An MQTT Connect that identifies itself as being from this version of the protocol, but has some other syntactic problem in it (e.g. reserved flags bit set non-zero, an error in the client ID, a parameter missing from the payload).

          iv) Something that parses correctly as another MQTT command that is received instead of a Connect.

          I think we agreed that we want the server to disconnect the TCP/IP session in case i) without sending any CONNACK. However our requirements on servers to trap this case must not be so stringent that they prevent case ii) - we should let servers handle this case (possibly with an RFC 2119 MAY) accept case ii).

          We might also consider it is helpful to return a negative CONNACK in some instances of case ii), in order to negotiate a level that is acceptable to both client and server.

          There is also the question of whether it's helpful to developers to be able to catch cases iii) and iv) and send a negative CONNACK - this I think is MQTT-8.

          So how does a server distinguish case i) from the others?

          • A valid CONNECT packet for this version of the protocol has to start with the byte 0x10 (this is thanks to MQTT-5). So testing this byte has a reasonable chance of catching case i), though it would also catch iv) and some instances of ii) and iii).
          • The next thing you encounter is the "RemainingLength" field which uses a special integer encoding. There's a 1in 16 chance that a random message will contain an invalid encoding, and a very high chance that when decoded it won't match the actual amount of data in the packet
          • The protocol version is a UTF-8 encoded string (with a 2 byte length prefix). There's a high chance that a random message would not have a valid encoding for this field.

          I suggest rewording Nick's suggestion a bit, and say words to the effect of

          1. A server MUST generate a CONNACK if it receives a syntactically well-formed CONNECT packet. This means a packet in which the first byte is 0x10, the RemainingLength is a valid MultiByte integer (we might want to impose a bound on the value here to catch people who send 256M ), and the protocol and version number are encoded as described in this spec.

          2. A server MAY generate a CONNACK if it receives a packet that meets the requirements of 1, but has a different (though correctly encoded) protocol and version. In this case it MAY also accept the CONNECT even if some of the flag bits in the first byte are non-zero.

          3. In all other cases it MUST close the connection without sending a CONNACK.

          Note that this means that case iv) results in the connection being closed without a CONNACK, but that's reasonable since it wasn't a CONNECT in the first place.

          Show
          peterniblett Peter Niblett (Inactive) added a comment - This issue is connected with MQTT-8 (which talk about malformed connect packets), MQTT-15 (protocol names and version numbers) and MQTT-5 (reserved bits in Connect). It seems to me that we have several kinds of "bad" Connect packet: i) Something that isn't really an MQTT Connect at all - it's either a packet from a different protocol that arrives because of an innocent configuration error, or it's the result of some kind of malicious DoS attack ii) An MQTT Connect from a different version of the protocol (either older or newer) iii) An MQTT Connect that identifies itself as being from this version of the protocol, but has some other syntactic problem in it (e.g. reserved flags bit set non-zero, an error in the client ID, a parameter missing from the payload). iv) Something that parses correctly as another MQTT command that is received instead of a Connect. I think we agreed that we want the server to disconnect the TCP/IP session in case i) without sending any CONNACK. However our requirements on servers to trap this case must not be so stringent that they prevent case ii) - we should let servers handle this case (possibly with an RFC 2119 MAY) accept case ii). We might also consider it is helpful to return a negative CONNACK in some instances of case ii), in order to negotiate a level that is acceptable to both client and server. There is also the question of whether it's helpful to developers to be able to catch cases iii) and iv) and send a negative CONNACK - this I think is MQTT-8 . So how does a server distinguish case i) from the others? A valid CONNECT packet for this version of the protocol has to start with the byte 0x10 (this is thanks to MQTT-5 ). So testing this byte has a reasonable chance of catching case i), though it would also catch iv) and some instances of ii) and iii). The next thing you encounter is the "RemainingLength" field which uses a special integer encoding. There's a 1in 16 chance that a random message will contain an invalid encoding, and a very high chance that when decoded it won't match the actual amount of data in the packet The protocol version is a UTF-8 encoded string (with a 2 byte length prefix). There's a high chance that a random message would not have a valid encoding for this field. I suggest rewording Nick's suggestion a bit, and say words to the effect of 1. A server MUST generate a CONNACK if it receives a syntactically well-formed CONNECT packet. This means a packet in which the first byte is 0x10, the RemainingLength is a valid MultiByte integer (we might want to impose a bound on the value here to catch people who send 256M ), and the protocol and version number are encoded as described in this spec. 2. A server MAY generate a CONNACK if it receives a packet that meets the requirements of 1, but has a different (though correctly encoded) protocol and version. In this case it MAY also accept the CONNECT even if some of the flag bits in the first byte are non-zero. 3. In all other cases it MUST close the connection without sending a CONNACK. Note that this means that case iv) results in the connection being closed without a CONNACK, but that's reasonable since it wasn't a CONNECT in the first place.
          Hide
          coppen Richard Coppen (Inactive) added a comment -

          Discussed on TC call 18.07.2013

          Show
          coppen Richard Coppen (Inactive) added a comment - Discussed on TC call 18.07.2013
          Hide
          coppen Richard Coppen (Inactive) added a comment -

          Proposal agreed on TC call

          Show
          coppen Richard Coppen (Inactive) added a comment - Proposal agreed on TC call
          Hide
          coppen Richard Coppen (Inactive) added a comment -

          Fixed in WD08

          Show
          coppen Richard Coppen (Inactive) added a comment - Fixed in WD08
          Hide
          coppen Richard Coppen (Inactive) added a comment -

          in WD08

          Show
          coppen Richard Coppen (Inactive) added a comment - in WD08

            People

            • Assignee:
              andrew_banks Andrew Banks (Inactive)
              Reporter:
              andrew_banks Andrew Banks (Inactive)
            • Watchers:
              1 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved: