@@ -1855,6 +1855,7 @@ static int BrokerRetained_Store(MqttBroker* broker, const char* topic,
18551855#else
18561856 {
18571857 byte is_new = 0 ;
1858+ byte * new_payload = NULL ;
18581859 BrokerRetainedMsg * cur = broker -> retained ;
18591860 while (cur ) {
18601861 if (cur -> topic != NULL && XSTRCMP (cur -> topic , topic ) == 0 ) {
@@ -1863,16 +1864,8 @@ static int BrokerRetained_Store(MqttBroker* broker, const char* topic,
18631864 }
18641865 cur = cur -> next ;
18651866 }
1866- if (msg != NULL ) {
1867- /* Replace existing: free old payload */
1868- if (msg -> payload ) {
1869- WOLFMQTT_FREE (msg -> payload );
1870- msg -> payload = NULL ;
1871- }
1872- msg -> payload_len = 0 ;
1873- }
1874- else {
1875- /* Allocate new */
1867+ if (msg == NULL ) {
1868+ /* Allocate new node + topic */
18761869 int tlen = (int )XSTRLEN (topic );
18771870 msg = (BrokerRetainedMsg * )WOLFMQTT_MALLOC (
18781871 sizeof (BrokerRetainedMsg ));
@@ -1894,16 +1887,22 @@ static int BrokerRetained_Store(MqttBroker* broker, const char* topic,
18941887 is_new = 1 ;
18951888 }
18961889 }
1890+ /* Stage new payload in a temp; only touch the stored message after
1891+ * all allocations succeed, so an OOM cannot destroy the prior one. */
18971892 if (rc == MQTT_CODE_SUCCESS && payload_len > 0 && payload != NULL ) {
1898- msg -> payload = (byte * )WOLFMQTT_MALLOC (payload_len );
1899- if (msg -> payload == NULL ) {
1893+ new_payload = (byte * )WOLFMQTT_MALLOC (payload_len );
1894+ if (new_payload == NULL ) {
19001895 rc = MQTT_CODE_ERROR_MEMORY ;
19011896 }
19021897 else {
1903- XMEMCPY (msg -> payload , payload , payload_len );
1898+ XMEMCPY (new_payload , payload , payload_len );
19041899 }
19051900 }
19061901 if (rc == MQTT_CODE_SUCCESS ) {
1902+ if (!is_new && msg -> payload != NULL ) {
1903+ WOLFMQTT_FREE (msg -> payload );
1904+ }
1905+ msg -> payload = new_payload ;
19071906 msg -> payload_len = payload_len ;
19081907 if (is_new ) {
19091908 msg -> next = broker -> retained ;
0 commit comments