Fixes slab corruption in cbq_destroy
Subsystems (3)
PATCH 1/1 Fixes slab corruption in cbq_destroy
Fixes slab corruption in cbq_destroy. cbq_destroy_filters and qdisc_put_rtab(q->link.R_tab) are already called in cbq_destroy_class. The latter lead to a slab corruption due to repeated freeing of q->link.R_tab because q->link is part of q->classes. Problem introduced in 1.21.
net/sched/sch_cbq.c +0 -6
@@ -1770,10 +1770,6 @@#ifdef CONFIG_NET_CLS_POLICE q->rx_class =NULL ;#endif -for (h =0 ; h <16 ; h++) { -for (cl = q->classes[h]; cl; cl = cl->next) -cbq_destroy_filters (cl); - }for (h =0 ; h <16 ; h++) {struct cbq_class *next;
@@ -1783,8 +1779,6 @@cbq_destroy_class (sch, cl); } } - -qdisc_put_rtab (q->link.R_tab); }static void cbq_put (struct Qdisc *sch,unsigned long arg)
Quoted 7 lines · Thomas Graf
Fixes slab corruption in
cbq_destroy.cbq_destroy_filtersandqdisc_put_rtab(q->link.R_tab)are already called incbq_destroy_class. The latter lead to a slab corruption due to repeated freeing ofq->link.R_tabbecauseq->linkis part ofq->classes. Problem introduced in 1.21.
I don't see how there can be slab corruption. qdisc_put_rtab only calls kfree if the table is found in qdisc_rtab_list, which only happens once. But the patch is still fine as cleanup :)
Regards
Patrick
Quoted 28 lines
Signed-off-by Thomas Graf <[email protected]>net/sched/sch_cbq.c +0
-6@@ -1770,10 +1770,6 @@#ifdef CONFIG_NET_CLS_POLICE q->rx_class =NULL ;#endif -for (h =0 ; h <16 ; h++) { -for (cl = q->classes[h]; cl; cl = cl->next) -cbq_destroy_filters (cl); - }for (h =0 ; h <16 ; h++) {struct cbq_class *next;@@ -1783,8 +1779,6 @@cbq_destroy_class (sch, cl); } } - -qdisc_put_rtab (q->link.R_tab); }static void cbq_put (struct Qdisc *sch,unsigned long arg)
* Patrick McHardy <[email protected]> 2004-09-16 15:47
Quoted 9 lines
Quoted 7 lines · Thomas Graf
Fixes slab corruption in
cbq_destroy.cbq_destroy_filtersandqdisc_put_rtab(q->link.R_tab)are already called incbq_destroy_class. The latter lead to a slab corruption due to repeated freeing ofq->link.R_tabbecauseq->linkis part ofq->classes. Problem introduced in 1.21.
Quoted 3 lines
I don't see how there can be slab corruption.
qdisc_put_rtabonly calls kfree if the table is found inqdisc_rtab_list, which only happens once. But the patch is still fine as cleanup :)
On second call to qdisc_put_rtab with tab pointing to an already freed qdisc_rate_table:
sch_api.c:271: if (!tab || --tab->refcnt)
Sep 16 01:52:51 axs kernel: Slab corruption: start=d8bd4f30, len=2048
Sep 16 01:52:51 axs kernel: Redzone: 0x5a2cf071/0x5a2cf071.
Sep 16 01:52:51 axs kernel: Last user: [<c036c9af>](cbq_destroy_class+0x36/0x60)
Sep 16 01:52:51 axs kernel: 410: 6a 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b 6b
^^
I guess this is the --tab->refcntSep 16 01:52:51 axs kernel: Prev obj: start=d8bd4724, len=2048 Sep 16 01:52:51 axs kernel: Redzone: 0x170fc2a5/0x170fc2a5. Sep 16 01:52:51 axs kernel: Last user: [<c0364594>](qdisc_get_rtab+0x77/0xcd) Sep 16 01:52:51 axs kernel: 000: 04 00 00 00 00 00 40 00 20 bc be 00 05 00 00 00 Sep 16 01:52:51 axs kernel: 010: 05 00 00 00 05 00 00 00 05 00 00 00 05 00 00 00 Sep 16 01:52:51 axs kernel: Next obj: start=d8bd573c, len=2048 Sep 16 01:52:51 axs kernel: Redzone: 0x170fc2a5/0x170fc2a5. Sep 16 01:52:51 axs kernel: Last user: [<c03484ce>](alloc_skb+0x48/0xe1) Sep 16 01:52:51 axs kernel: 000: 6c 04 00 00 28 00 05 06 d5 d5 48 41 00 00 00 00 Sep 16 01:52:51 axs kernel: 010: 00 00 00 00 04 00 00 00 12 00 10 00 00 00 10 00
Quoted 9 lines · Thomas Graf
* Patrick McHardy <[email protected]> 2004-09-16 15:47
Quoted 5 lines
I don't see how there can be slab corruption.
qdisc_put_rtabonly calls kfree if the table is found inqdisc_rtab_list, which only happens once. But the patch is still fine as cleanup :)
Quoted 6 lines
On second call to
qdisc_put_rtabwith tab pointing to an already freedqdisc_rate_table:sch_api.c:271: if (!tab || --tab->refcnt)
You're right, no double free but accessing and modifying of freed memory.
Regards
Patrick
* Patrick McHardy <[email protected]> 2004-09-16 16:58
Quoted 11 lines
Quoted 9 lines · Thomas Graf
* Patrick McHardy <[email protected]> 2004-09-16 15:47
Quoted 5 lines
I don't see how there can be slab corruption.
qdisc_put_rtabonly calls kfree if the table is found inqdisc_rtab_list, which only happens once. But the patch is still fine as cleanup :)
Quoted 7 lines
Quoted 6 lines
On second call to
qdisc_put_rtabwith tab pointing to an already freedqdisc_rate_table:sch_api.c:271: if (!tab || --tab->refcnt)
You're right, no double free but accessing and modifying of freed memory.
My patch description was misleading should have been something like this:
Fixes slab corruption in cbq_destroy. cbq_destroy_filters and qdisc_put_rtab(q->link.R_tab) are already called in cbq_destroy_class. The latter lead to a slab corruption due to use of q->link.R_tab after being freed by previous call to qdisc_put_rtab. Problem introduced in 1.21.
David S. Miller
maintainerQuoted 5 lines · On Thu, 16 Sep 2004 15:28:56 +0200 Thomas Graf <[email protected]> wrote:
Fixes slab corruption in
cbq_destroy.cbq_destroy_filtersandqdisc_put_rtab(q->link.R_tab)are already called incbq_destroy_class. The latter lead to a slab corruption due to repeated freeing ofq->link.R_tabbecauseq->linkis part ofq->classes. Problem introduced in 1.21.
Good catch, applied.