[OpenAFS-devel] Re: 1.3.77 on Linux 2.6.10 (Fedora Core 3 test): patches for partial success
chas williams - CONTRACTOR
chas@cmf.nrl.navy.mil
Tue, 11 Jan 2005 14:41:16 -0500
In message <20050107042308.GA24277@jadzia.bu.edu>,Matthew Miller writes:
>Unable to handle kernel paging request at virtual address 0008008e
> printing eip:
>c0131d35
>*pde = 12d54067
>Oops: 0000 [#1]
>DEBUG_PAGEALLOC
>Modules linked in: libafs(U) radeon parport_pc lp parport autofs4 sunrpc iptable_filter ip_tables video button battery ac md5 ipv6 usbled ohci1394 ieee1394 uhci_hcd ehci_hcd i2c_viapro i2c_core snd_via82xx snd_ac97_codec snd_pcm_oss snd_mixer_oss snd_pcm snd_timer snd_page_alloc gameport snd_mpu401_uart snd_rawmidi snd_seq_device snd soundcore sk98lin floppy dm_snapshot dm_zero dm_mirror ext3 jbd dm_mod sata_promise sata_via libata sd_mod scsi_mod
>CPU: 0
>EIP: 0060:[<c0131d35>] Tainted: P VLI
>EFLAGS: 00010216 (2.6.10-1.727_FC3)
>EIP is at bit_waitqueue+0x2f/0x42
>eax: b9b92403 ebx: 0007ff56 ecx: 00000020 edx: 00000003
>esi: e118a120 edi: e11860e4 ebp: e0ce1680 esp: d35c9c7c
>ds: 007b es: 007b ss: 0068
>Process ls (pid: 5462, threadinfo=d35c9000 task=d1837aa0)
>Stack: 00000003 c0131cfb e1189f84 e0f413d0 c017a832 e1189f84 e134cbe8 c017aad6
> e1189f84 e0f1be5b e1189f84 e0f21969 00000202 00000000 00000000 c964e120
> 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
>Call Trace:
> [<c0131cfb>] wake_up_bit+0xb/0x16
> [<e0f413d0>] afs_delete_inode+0x0/0x10 [libafs]
> [<c017a832>] generic_delete_inode+0x20a/0x224
> [<c017aad6>] iput+0x5f/0x61
> [<e0f1be5b>] afs_PutVCache+0x4c/0x93 [libafs]
> [<e0f21969>] afs_DoBulkStat+0x5f8/0x144a [libafs]
> [<e08c4b3a>] __ext3_journal_stop+0x19/0x34 [ext3]
> [<e0f0f3bc>] afs_dir_GetBlob+0xb/0x1e [libafs]
> [<e0f0f45a>] FindItem+0x5c/0xde [libafs]
> [<e0f0f20d>] afs_dir_LookupOffset+0x4c/0x53 [libafs]
> [<e0f230c6>] afs_lookup+0x90b/0xf79 [libafs]
i took a little look at this problem this morning. its back to 'where
does afs get its inodes'. the wake_up_bit() mechanism has replaced
'per object' wait queues (atleast when testing for single bit changes).
the actual wait queue to use is determined using a hash on page->flags
(which encodes the zone table in the lower 8 bits). afs inodes come from
a vmalloc() since afs gets all the inodes in one go. vmalloc()'d memory
apparently doesnt get mapped to any particular zone. so when an afs
inode uses wake_up_bit() they index off the end of the zone_page table.
i verified this by forcing afs_osi_Alloc() to always use kmalloc() and
starting afsd with suitably smallish parameters. works fine.
a real fix? two options i guess, dont get all the inodes in one go.
its a linked list in memory, so just get them one at a time to make sure
we use kmalloc(). or, and likely a better solution in the long term,
just get inodes the 'normal' way from the kernel (i had some code to
do this at one point and lost it, i have seen some code from a suse
developer as well to do the same thing).