Commit cdd77c7d861f6d0e1b03fd32b5b3599a8b5e235b

Authored by Wiebe Cazemier
1 parent deace493

Parse user property in publish

mqtt5properties.cpp
1 1 #include "mqtt5properties.h"
2 2  
3 3 #include "cstring"
  4 +#include "vector"
4 5  
5 6 #include "exceptions.h"
6 7  
... ... @@ -102,6 +103,11 @@ void Mqtt5PropertyBuilder::writeResponseTopic(const std::string &str)
102 103 writeStr(Mqtt5Properties::ResponseTopic, str);
103 104 }
104 105  
  106 +void Mqtt5PropertyBuilder::writeUserProperty(const std::string &key, const std::string &value)
  107 +{
  108 + write2Str(Mqtt5Properties::UserProperty, key, value);
  109 +}
  110 +
105 111 void Mqtt5PropertyBuilder::writeUint32(Mqtt5Properties prop, const uint32_t x, std::vector<char> &target)
106 112 {
107 113 size_t pos = target.size();
... ... @@ -165,3 +171,33 @@ void Mqtt5PropertyBuilder::writeStr(Mqtt5Properties prop, const std::string &amp;str
165 171 std::memcpy(&genericBytes[pos], str.c_str(), strlen);
166 172 }
167 173  
  174 +void Mqtt5PropertyBuilder::write2Str(Mqtt5Properties prop, const std::string &one, const std::string &two)
  175 +{
  176 + size_t pos = genericBytes.size();
  177 + const size_t newSize = pos + one.length() + two.length() + 5;
  178 + genericBytes.resize(newSize);
  179 +
  180 + genericBytes[pos++] = static_cast<uint8_t>(prop);
  181 +
  182 + std::vector<const std::string*> strings;
  183 + strings.push_back(&one);
  184 + strings.push_back(&two);
  185 +
  186 + for (const std::string *str : strings)
  187 + {
  188 + if (str->length() > 0xFFFF)
  189 + throw ProtocolError("String too long.");
  190 +
  191 + const uint16_t strlen = str->length();
  192 +
  193 + const uint8_t a = static_cast<uint8_t>(strlen >> 8);
  194 + const uint8_t b = static_cast<uint8_t>(strlen);
  195 +
  196 + genericBytes[pos++] = a;
  197 + genericBytes[pos++] = b;
  198 +
  199 + std::memcpy(&genericBytes[pos], str->c_str(), strlen);
  200 + pos += strlen;
  201 + }
  202 +}
  203 +
... ...
mqtt5properties.h
... ... @@ -16,6 +16,7 @@ class Mqtt5PropertyBuilder
16 16 void writeUint16(Mqtt5Properties prop, const uint16_t x);
17 17 void writeUint8(Mqtt5Properties prop, const uint8_t x);
18 18 void writeStr(Mqtt5Properties prop, const std::string &str);
  19 + void write2Str(Mqtt5Properties prop, const std::string &one, const std::string &two);
19 20 public:
20 21 Mqtt5PropertyBuilder();
21 22  
... ... @@ -38,6 +39,7 @@ public:
38 39 void writePayloadFormatIndicator(uint8_t val);
39 40 void writeMessageExpiryInterval(uint32_t val);
40 41 void writeResponseTopic(const std::string &str);
  42 + void writeUserProperty(const std::string &key, const std::string &value);
41 43 };
42 44  
43 45 #endif // MQTT5PROPERTIES_H
... ...
mqttpacket.cpp
... ... @@ -815,7 +815,14 @@ void MqttPacket::handlePublish()
815 815 case Mqtt5Properties::CorrelationData:
816 816 break;
817 817 case Mqtt5Properties::UserProperty:
  818 + {
  819 + const uint16_t lenKey = readTwoBytesToUInt16();
  820 + const std::string userPropKey(readBytes(lenKey), lenKey);
  821 + const uint16_t lenVal = readTwoBytesToUInt16();
  822 + const std::string userPropVal(readBytes(lenVal), lenVal);
  823 + publishData.propertyBuilder->writeUserProperty(userPropKey, userPropVal);
818 824 break;
  825 + }
819 826 case Mqtt5Properties::SubscriptionIdentifier:
820 827 break;
821 828 case Mqtt5Properties::ContentType:
... ...