On Thu, Nov 06, 2014 at 06:01:41PM +0100, Maxime Villard wrote: > Le 06/11/2014 08:28, Michael van Elst a ?crit : > >petri.laa...@asd.fi (Petri Laakso) writes: > > > > > >>On Fri, 31 Oct 2014, Maxime Villard wrote: > >>>That's KMEM_SIZE. Great. > >>>It means that it caught a memory corruption somewhere. > >>>That being said, I don't think I can help without a trace... > > > >>Here's backtrace and steps how I ended up with panic. This was in > >>single user mode after fresh 7.0_BETA install (sources from last night) > > > >>http://www.asd.fi/~petri/tmp/rpi_bt.jpg > > > >>Petri > > > >malloc considered useful: > > > >allocation in ffs_mountfs: > > bsize = fs->fs_cssize; > > if (fs->fs_contigsumsize > 0) > > bsize += fs->fs_ncg * sizeof(int32_t); > > bsize += fs->fs_ncg * sizeof(*fs->fs_contigdirs); > > allocsbsize = bsize; > > space = kmem_alloc((u_long)allocsbsize, KM_SLEEP); > > fs->fs_csp = space; > > > >deallocation in ffs_unmount: > > bsize = fs->fs_cssize; > > if (fs->fs_contigsumsize > 0) > > bsize += fs->fs_ncg * sizeof(int32_t); > > bsize += fs->fs_ncg * sizeof(*fs->fs_contigdirs); > > kmem_free(fs->fs_csp, bsize); > > > > > >allocsbsize only exists to handle some error paths, but since > >it is not stored globally, the value is recalculated, assuming > >that the underlying values do not change. > > > >Apparently that's not true after the resize of the filesystem. > > Yes. That's similar to the mail I sent some days ago on tech-kern@: > > http://mail-index.netbsd.org/tech-kern/2014/10/27/msg017874.html > > I think we should implement a set of kmem_vXX functions, which > don't need a size argument to free: > void *kmem_valloc(size_t size) > void kmem_vfree(void *ptr) > > Such an allocator would be very useful; not only in ffs, but in > many other places where strange hacks in structures are necessary > to hold the allocated size. > > It is easy to implement, and kmem_valloc(0) wouldn't panic the > system - contrary to kmem_alloc().
You can do that now, using the existing allocation routines, and, at the cost of possible suboptimal "block" alignment, allocate size_t extra bytes at the start to hold the allocated size: void * allocate(size_t size, int type) { uint8_t *p; p = kmem_alloc(size + sizeof(size_t), type); memcpy(p, &size, sizeof(size)); return &p[sizeof(size)]; } void deallocate(void *ptr) { uint8_t *p = (uint8_t *)ptr; size_t size; p -= sizeof(size); memcpy(&size, p, sizeof(size)); kmem_free(p, size); } Regards, Alistair