Commit 7edc3b8363283ca77d3e879388ff18ef9bf43cc7

Authored by Wiebe Cazemier
1 parent 0d676dc9

CONNECT with protocol 3.1, mostly

client.cpp
... ... @@ -102,11 +102,12 @@ bool Client::bufferToMqttPackets(std::vector<MqttPacket> &packetQueueIn)
102 102 // TODO: reset buffer to normal size after a while of not needing it, or not needing the extra space.
103 103 }
104 104  
105   -void Client::setClientProperties(const std::string &clientId, const std::string username, bool connectPacketSeen)
  105 +void Client::setClientProperties(const std::string &clientId, const std::string username, bool connectPacketSeen, uint16_t keepalive)
106 106 {
107 107 this->clientid = clientId;
108 108 this->username = username;
109 109 this->connectPacketSeen = connectPacketSeen;
  110 + this->keepalive = keepalive;
110 111 }
111 112  
112 113  
... ...
client.h
... ... @@ -30,6 +30,7 @@ class Client
30 30 bool connectPacketSeen = false;
31 31 std::string clientid;
32 32 std::string username;
  33 + uint16_t keepalive = 0;
33 34  
34 35 ThreadData_p threadData;
35 36  
... ... @@ -58,7 +59,7 @@ public:
58 59 int getFd() { return fd;}
59 60 bool readFdIntoBuffer();
60 61 bool bufferToMqttPackets(std::vector<MqttPacket> &packetQueueIn);
61   - void setClientProperties(const std::string &clientId, const std::string username, bool connectPacketSeen);
  62 + void setClientProperties(const std::string &clientId, const std::string username, bool connectPacketSeen, uint16_t keepalive);
62 63 void setAuthenticated(bool value) { authenticated = value;}
63 64 bool getAuthenticated() { return authenticated; }
64 65 bool hasConnectPacketSeen() { return connectPacketSeen; }
... ...
mqttpacket.cpp
... ... @@ -27,7 +27,7 @@ void MqttPacket::handleConnect()
27 27 // TODO: Do all packets have a variable header?
28 28 variable_header_length = readTwoBytesToUInt16();
29 29  
30   - if (variable_header_length == 4)
  30 + if (variable_header_length == 4 || variable_header_length == 6)
31 31 {
32 32 char *c = readBytes(variable_header_length);
33 33 std::string magic_marker(c, variable_header_length);
... ... @@ -37,54 +37,61 @@ void MqttPacket::handleConnect()
37 37 if (magic_marker == "MQTT" && protocol_level == 0x04)
38 38 {
39 39 protocolVersion = ProtocolVersion::Mqtt311;
  40 + }
  41 + else if (magic_marker == "MQIsdp" && protocol_level == 0x03)
  42 + {
  43 + protocolVersion = ProtocolVersion::Mqtt31;
  44 + }
  45 + else
  46 + {
  47 + throw ProtocolError("Only MQTT 3.1 and 3.1.1 supported.");
  48 + }
40 49  
41   - char flagByte = readByte();
42   - bool reserved = !!(flagByte & 0b00000001);
  50 + char flagByte = readByte();
  51 + bool reserved = !!(flagByte & 0b00000001);
43 52  
44   - if (reserved)
45   - throw ProtocolError("Protocol demands reserved flag in CONNECT is 0");
  53 + if (reserved)
  54 + throw ProtocolError("Protocol demands reserved flag in CONNECT is 0");
46 55  
47 56  
48   - bool user_name_flag = !!(flagByte & 0b10000000);
49   - bool password_flag = !!(flagByte & 0b01000000);
50   - bool will_retain = !!(flagByte & 0b00100000);
51   - char will_qos = (flagByte & 0b00011000) >> 3;
52   - bool will_flag = !!(flagByte & 0b00000100);
53   - bool clean_session = !!(flagByte & 0b00000010);
  57 + bool user_name_flag = !!(flagByte & 0b10000000);
  58 + bool password_flag = !!(flagByte & 0b01000000);
  59 + bool will_retain = !!(flagByte & 0b00100000);
  60 + char will_qos = (flagByte & 0b00011000) >> 3;
  61 + bool will_flag = !!(flagByte & 0b00000100);
  62 + bool clean_session = !!(flagByte & 0b00000010);
54 63  
55   - uint16_t keep_alive = readTwoBytesToUInt16();
  64 + uint16_t keep_alive = readTwoBytesToUInt16();
56 65  
57   - uint16_t client_id_length = readTwoBytesToUInt16();
58   - std::string client_id(readBytes(client_id_length), client_id_length);
  66 + uint16_t client_id_length = readTwoBytesToUInt16();
  67 + std::string client_id(readBytes(client_id_length), client_id_length);
59 68  
60   - std::string username;
61   - std::string password;
  69 + std::string username;
  70 + std::string password;
62 71  
63   - if (will_flag)
64   - {
  72 + if (will_flag)
  73 + {
65 74  
66   - }
67   - if (user_name_flag)
68   - {
69   - uint16_t user_name_length = readTwoBytesToUInt16();
70   - username = std::string(readBytes(user_name_length), user_name_length);
71   - }
72   - if (password_flag)
73   - {
74   - uint16_t password_length = readTwoBytesToUInt16();
75   - password = std::string(readBytes(password_length), password_length);
76   - }
  75 + }
  76 + if (user_name_flag)
  77 + {
  78 + uint16_t user_name_length = readTwoBytesToUInt16();
  79 + username = std::string(readBytes(user_name_length), user_name_length);
  80 + }
  81 + if (password_flag)
  82 + {
  83 + uint16_t password_length = readTwoBytesToUInt16();
  84 + password = std::string(readBytes(password_length), password_length);
  85 + }
77 86  
78   - sender->setClientProperties(clientid, username, true);
  87 + // TODO: validate UTF8 encoded username/password.
79 88  
80   - }
  89 + sender->setClientProperties(clientid, username, true, keep_alive);
81 90 }
82   - else if (variable_header_length == 6)
  91 + else
83 92 {
84   - throw ProtocolError("Only MQTT 3.1.1 implemented.");
  93 + throw ProtocolError("Invalid variable header length. Garbage?");
85 94 }
86   -
87   - throw ProtocolError("Unprogrammed sequence in CONNECT.");
88 95 }
89 96  
90 97 char *MqttPacket::readBytes(size_t length)
... ...