natt: hand the UPnP reply to the XML document instead of copying it twice

Each of the three UPnP replies (device description, external address,
port mapping) was copied into a NUL-terminated heap buffer, then
copied again by rxml_load_document_string, which keeps its own.  The
buffer is now handed over with rxml_load_document_owned, which keeps it
as the document's or frees it on failure, so the second copy and its
allocation are gone and the caller no longer frees it.

natt_desc_parse_test passes.
This commit is contained in:
LibretroAdmin authored and libretroadmin committed 2026-11-07 06:36:57 +01:00
1 parent 6af9ab068f
commit e8dc09f986
1 file changed
+9 -6
+9 -6
View File
@@ -246,7 +246,9 @@ static void natt_query_device_cb(retro_task_t *task, void *task_data,
xml[data->len] = '\0';
/* Parse the device's description XML. */
document = rxml_load_document_string(xml);
/* The document takes the copy over (and frees it on failure)
* rather than copying it a second time. */
document = rxml_load_document_owned(xml, data->len);
if (document)
{
rxml_node_t *root = rxml_root_node(document);
@@ -256,7 +258,6 @@ static void natt_query_device_cb(retro_task_t *task, void *task_data,
rxml_free_document(document);
}
free(xml);
done:
retro_atomic_store_release_int(&device->busy, 0);
@@ -345,7 +346,9 @@ static void natt_external_address_cb(retro_task_t *task, void *task_data,
xml[data->len] = '\0';
/* Parse the returned external ip address. */
document = rxml_load_document_string(xml);
/* The document takes the copy over (and frees it on failure)
* rather than copying it a second time. */
document = rxml_load_document_owned(xml, data->len);
if (document)
{
rxml_node_t *root = rxml_root_node(document);
@@ -355,7 +358,6 @@ static void natt_external_address_cb(retro_task_t *task, void *task_data,
rxml_free_document(document);
}
free(xml);
done:
retro_atomic_store_release_int(&device->busy, 0);
@@ -433,7 +435,9 @@ static void natt_open_port_cb(retro_task_t *task, void *task_data,
xml[data->len] = '\0';
/* Parse the device's port forwarding response. */
document = rxml_load_document_string(xml);
/* The document takes the copy over (and frees it on failure)
* rather than copying it a second time. */
document = rxml_load_document_owned(xml, data->len);
if (document)
{
rxml_node_t *root = rxml_root_node(document);
@@ -443,7 +447,6 @@ static void natt_open_port_cb(retro_task_t *task, void *task_data,
rxml_free_document(document);
}
free(xml);
done:
retro_atomic_store_release_int(&device->busy, 0);