dns_packet_unref() unconditionally unrefs p->more on every call,
even when n_ref > 1. But dns_packet_ref() doesn't ref p->more.
This means if a packet with a ->more chain gets ref'd and unref'd
multiple times, the chain gets freed too early while the parent
still holds a dangling pointer.
Move the p->more unref into the n_ref == 1 block so the chain
only gets cleaned up when the packet is actually being freed.
assert(p->n_ref > 0);
- dns_packet_unref(p->more);
-
- if (p->n_ref == 1)
+ if (p->n_ref == 1) {
+ dns_packet_unref(p->more);
dns_packet_free(p);
- else
+ } else
p->n_ref--;
return NULL;