Commit 4bf112b6d9f450f2ee8eb5665eb4f3f9d4ecbed4

Authored by Wiebe Cazemier
1 parent f262b796

Separate DISCONNECT packet parsing and handling

This is necessary for the test client I have in mind, so I can re-use
this code in that new test client which has no MQTT behavior, but just
returns packets (meaning I have to be able to parse them without
initiating handling).
mqttpacket.cpp
@@ -812,19 +812,23 @@ void MqttPacket::handleExtendedAuth() @@ -812,19 +812,23 @@ void MqttPacket::handleExtendedAuth()
812 } 812 }
813 } 813 }
814 814
815 -void MqttPacket::handleDisconnect() 815 +DisconnectData MqttPacket::parseDisconnectData()
816 { 816 {
  817 + if (this->packetType != PacketType::DISCONNECT)
  818 + throw std::runtime_error("Packet must be disconnect packet.");
  819 +
817 if (first_byte & 0b1111) 820 if (first_byte & 0b1111)
818 throw ProtocolError("Disconnect packet first 4 bits should be 0.", ReasonCodes::MalformedPacket); 821 throw ProtocolError("Disconnect packet first 4 bits should be 0.", ReasonCodes::MalformedPacket);
819 822
820 - ReasonCodes reasonCode = ReasonCodes::Success;  
821 - std::string reasonString; 823 + setPosToDataStart();
  824 +
  825 + DisconnectData result;
822 826
823 if (this->protocolVersion >= ProtocolVersion::Mqtt5) 827 if (this->protocolVersion >= ProtocolVersion::Mqtt5)
824 { 828 {
825 if (!atEnd()) 829 if (!atEnd())
826 { 830 {
827 - reasonCode = static_cast<ReasonCodes>(readByte()); 831 + result.reasonCode = static_cast<ReasonCodes>(readByte());
828 832
829 const size_t proplen = decodeVariableByteIntAtPos(); 833 const size_t proplen = decodeVariableByteIntAtPos();
830 const size_t prop_end_at = pos + proplen; 834 const size_t prop_end_at = pos + proplen;
@@ -839,12 +843,13 @@ void MqttPacket::handleDisconnect() @@ -839,12 +843,13 @@ void MqttPacket::handleDisconnect()
839 { 843 {
840 const Settings *settings = ThreadGlobals::getSettings(); 844 const Settings *settings = ThreadGlobals::getSettings();
841 const uint32_t session_expire = std::min<uint32_t>(readFourBytesToUint32(), settings->getExpireSessionAfterSeconds()); 845 const uint32_t session_expire = std::min<uint32_t>(readFourBytesToUint32(), settings->getExpireSessionAfterSeconds());
842 - sender->getSession()->setSessionExpiryInterval(session_expire); 846 + result.session_expiry_interval = session_expire;
  847 + result.session_expiry_interval_set = true;
843 break; 848 break;
844 } 849 }
845 case Mqtt5Properties::ReasonString: 850 case Mqtt5Properties::ReasonString:
846 { 851 {
847 - reasonString = readBytesToString(); 852 + result.reasonString = readBytesToString();
848 break; 853 break;
849 } 854 }
850 case Mqtt5Properties::ServerReference: 855 case Mqtt5Properties::ServerReference:
@@ -862,15 +867,25 @@ void MqttPacket::handleDisconnect() @@ -862,15 +867,25 @@ void MqttPacket::handleDisconnect()
862 } 867 }
863 } 868 }
864 869
865 - std::string disconnectReason = formatString("MQTT Disconnect received (code %d).", static_cast<uint8_t>(reasonCode)); 870 + return result;
  871 +}
  872 +
  873 +void MqttPacket::handleDisconnect()
  874 +{
  875 + DisconnectData data = parseDisconnectData();
  876 +
  877 + std::string disconnectReason = formatString("MQTT Disconnect received (code %d).", static_cast<uint8_t>(data.reasonCode));
  878 +
  879 + if (!data.reasonString.empty())
  880 + disconnectReason += data.reasonString;
866 881
867 - if (!reasonString.empty())  
868 - disconnectReason += reasonString; 882 + if (data.session_expiry_interval_set)
  883 + sender->getSession()->setSessionExpiryInterval(data.session_expiry_interval);
869 884
870 logger->logf(LOG_NOTICE, "Client '%s' cleanly disconnecting", sender->repr().c_str()); 885 logger->logf(LOG_NOTICE, "Client '%s' cleanly disconnecting", sender->repr().c_str());
871 sender->setDisconnectReason(disconnectReason); 886 sender->setDisconnectReason(disconnectReason);
872 sender->markAsDisconnecting(); 887 sender->markAsDisconnecting();
873 - if (reasonCode == ReasonCodes::Success) 888 + if (data.reasonCode == ReasonCodes::Success)
874 sender->clearWill(); 889 sender->clearWill();
875 ThreadGlobals::getThreadData()->removeClientQueued(sender); 890 ThreadGlobals::getThreadData()->removeClientQueued(sender);
876 } 891 }
mqttpacket.h
@@ -113,6 +113,7 @@ public: @@ -113,6 +113,7 @@ public:
113 ConnectData parseConnectData(); 113 ConnectData parseConnectData();
114 void handleConnect(); 114 void handleConnect();
115 void handleExtendedAuth(); 115 void handleExtendedAuth();
  116 + DisconnectData parseDisconnectData();
116 void handleDisconnect(); 117 void handleDisconnect();
117 void handleSubscribe(); 118 void handleSubscribe();
118 void handleUnsubscribe(); 119 void handleUnsubscribe();
packetdatatypes.h
@@ -38,5 +38,14 @@ struct ConnectData @@ -38,5 +38,14 @@ struct ConnectData
38 ConnectData(); 38 ConnectData();
39 }; 39 };
40 40
  41 +struct DisconnectData
  42 +{
  43 + ReasonCodes reasonCode = ReasonCodes::Success;
  44 + std::string reasonString;
  45 +
  46 + bool session_expiry_interval_set = false;
  47 + uint32_t session_expiry_interval = 0;
  48 +};
  49 +
41 50
42 #endif // PACKETDATATYPES_H 51 #endif // PACKETDATATYPES_H