tech-kern archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: kmem API to allocate arrays



On 30.07.2017 15:45, Taylor R Campbell wrote:
>> Date: Sun, 30 Jul 2017 10:22:11 +0200
>> From: Kamil Rytarowski <n54%gmx.com@localhost>
>>
>> I think we should go for kmem_reallocarr(). It has been designed for
>> overflows like realocarray(3) with an option to be capable to resize a
>> table fron 1 to N elements and back from N to 0 including freeing.
> 
> Initially I was reluctant to do that because (a) we don't even have a
> kmem_realloc, perhaps for some particular reason, and (b) it requires
> an extra parameter for the old size.  But I don't know any particular
> reason in (a), and perhaps (b) not so bad after all.  Here's a draft:
> 
> int
> kmem_reallocarr(void *ptrp, size_t size, size_t ocnt, size_t ncnt, int flags)
> {
> 	void *optr, *nptr;
> 
> 	KASSERT(size != 0);
> 	if (__predict_false((size|ncnt) >= SQRT_SIZE_MAX &&
> 		ncnt > SIZE_MAX/size))
> 		return ENOMEM;
> 
> 	memcpy(&optr, ptrp, sizeof(void *));
> 	KASSERT((ocnt == 0) == (optr == NULL));
> 	if (ncnt == 0) {
> 		nptr = NULL;
> 	} else {
> 		nptr = kmem_alloc(size*ncnt, flags);
> 		KASSERT(nptr != NULL || flags == KM_NOSLEEP);
> 		if (nptr == NULL)
> 			return ENOMEM;
> 	}
> 	KASSERT((ncnt == 0) == (nptr == NULL));
> 	if (ocnt & ncnt)
> 		memcpy(nptr, optr, size*MIN(ocnt, ncnt));
> 	if (ocnt != 0)
> 		kmem_free(optr, size*ocnt);
> 	memcpy(ptrp, &nptr, sizeof(void *));
> 
> 	return 0;
> }
> 

I would allow size to be 0, like with the original reallocarr(3). It
might be less pretty, but more compatible with the original model and
less vulnerable to accidental panics for no good reason.

Attachment: signature.asc
Description: OpenPGP digital signature



Home | Main Index | Thread Index | Old Index