Porpoise
3439dd86e3
[PATCH] When CONFIG_BASE_SMALL=1, cascade() may enter an infinite loop
When CONFIG_BASE_SAMLL=1, cascade() in may enter the infinite loop.
Because of CONFIG_BASE_SMALL=1(TVR_BITS=6 and TVN_BITS=4), the list
base->tv5 may cascade into base->tv5. So, the kernel enters the infinite
loop in the function cascade().
I created a test module to verify this bug, and a patch to fix it.
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/timer.h>
#if 0
#include <linux/kdb.h>
#else
#define kdb_printf printk
#endif
#define TVN_BITS (CONFIG_BASE_SMALL ? 4 : 6)
#define TVR_BITS (CONFIG_BASE_SMALL ? 6 : 8)
#define TVN_SIZE (1 << TVN_BITS)
#define TVR_SIZE (1 << TVR_BITS)
#define TVN_MASK (TVN_SIZE - 1)
#define TVR_MASK (TVR_SIZE - 1)
#define TV_SIZE(N) (N*TVN_BITS + TVR_BITS)
struct timer_list timer0;
struct timer_list dummy_timer1;
struct timer_list dummy_timer2;
void dummy_timer_fun(unsigned long data) {
}
unsigned long j=0;
void check_timer_base(unsigned long data)
{
kdb_printf("check_timer_base %08x\n",jiffies);
mod_timer(&timer0,(jiffies & (~0xFFF)) + 0x1FFF);
}
int init_module(void)
{
init_timer(&timer0);
timer0.data = (unsigned long)0;
timer0.function = check_timer_base;
mod_timer(&timer0,jiffies+1);
init_timer(&dummy_timer1);
dummy_timer1.data = (unsigned long)0;
dummy_timer1.function = dummy_timer_fun;
init_timer(&dummy_timer2);
dummy_timer2.data = (unsigned long)0;
dummy_timer2.function = dummy_timer_fun;
j=jiffies;
j&=(~((1<<TV_SIZE(3))-1));
j+=(1<<TV_SIZE(3));
j+=(1<<TV_SIZE(4));
kdb_printf("mod_timer %08x\n",j);
mod_timer(&dummy_timer1, j );
mod_timer(&dummy_timer2, j );
return 0;
}
void cleanup_module()
{
del_timer_sync(&timer0);
del_timer_sync(&dummy_timer1);
del_timer_sync(&dummy_timer2);
}
(Cleanups from Oleg)
[oleg@tv-sign.ru: use list_replace_init()]
Cc: Oleg Nesterov <oleg@tv-sign.ru>
Cc: Matt Mackall <mpm@selenic.com>
Signed-off-by: Oleg Nesterov <oleg@tv-sign.ru>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
2006-06-23 07:43:08 -07:00
..
2006-06-23 07:43:05 -07:00
2006-06-23 07:43:00 -07:00
2006-01-03 11:35:26 +01:00
2006-06-23 07:42:45 -07:00
2006-06-20 05:25:28 -04:00
2006-06-20 05:25:28 -04:00
2006-06-20 05:25:28 -04:00
2006-06-23 07:43:07 -07:00
2006-03-25 08:22:56 -08:00
2006-06-23 07:42:53 -07:00
2006-01-03 13:37:51 +01:00
2006-03-27 08:44:50 -08:00
2006-06-23 07:42:54 -07:00
2005-04-16 15:20:36 -07:00
2006-03-24 07:33:30 -08:00
2006-06-17 10:52:13 -07:00
2006-05-15 11:20:55 -07:00
2006-06-23 07:43:04 -07:00
2006-03-31 12:18:59 -08:00
2006-06-23 07:42:45 -07:00
2006-06-20 14:51:22 -07:00
2006-03-26 08:57:03 -08:00
2005-10-30 17:37:32 -08:00
2005-06-23 09:45:10 -07:00
2005-06-25 16:24:45 -07:00
2006-06-23 07:43:02 -07:00
2005-10-08 15:00:57 -07:00
2006-03-28 18:36:41 -08:00
2006-04-20 07:54:03 -07:00
2006-06-23 07:43:02 -07:00
2006-03-25 08:22:57 -08:00
2006-05-08 22:40:05 +01:00
2006-05-15 11:20:55 -07:00
2006-01-11 08:14:16 -08:00
2006-01-09 15:59:20 -08:00
2006-01-10 14:27:59 -08:00
2006-01-09 15:59:19 -08:00
2006-04-11 06:18:40 -07:00
2006-03-28 09:16:03 -08:00
2006-03-31 12:19:00 -08:00
2006-06-17 10:52:13 -07:00
2006-03-26 08:57:03 -08:00
2006-06-19 18:16:01 -07:00
2006-04-26 08:30:03 -07:00
2006-05-11 11:08:49 -07:00
2006-06-23 07:43:07 -07:00
2006-03-28 09:16:05 -08:00
2006-03-23 19:58:45 +01:00
2006-01-10 08:02:02 -08:00
2006-06-23 07:43:04 -07:00
2005-04-16 15:20:36 -07:00
2006-06-20 05:25:21 -04:00
2006-04-26 08:30:03 -07:00
2006-04-26 08:30:03 -07:00
2006-03-23 07:38:16 -08:00
2006-01-10 08:01:25 -08:00
2006-06-23 07:42:53 -07:00
2006-06-23 07:43:07 -07:00
2006-06-23 07:43:06 -07:00
2006-04-01 01:41:22 +02:00
2006-06-23 07:43:08 -07:00
2006-04-19 16:27:18 -07:00
2006-06-22 15:05:55 -07:00
2005-04-16 15:20:36 -07:00
2006-06-23 07:43:07 -07:00