I use new to allocate a buffer, as follows:
BYTE *p;
p = new BYTE[20];
If I do NOT store the size of the allocated buffer, how to determine the buffer size via p only?
Thanks
Printable View
I use new to allocate a buffer, as follows:
BYTE *p;
p = new BYTE[20];
If I do NOT store the size of the allocated buffer, how to determine the buffer size via p only?
Thanks
As far as I know, there is no way to do that given just p. Store the size separately (or bundled together in a container, e.g., std::vector).
You do have _msize but not sure if it works for new ??
http://msdn.microsoft.com/en-us/library/z2s077bc.aspx
James
Yes, a test shows _msize() in MS VS does work with new as new by default used the standard memory allocator. However if non-standard memory allocation is used then _msize() won't work. Note that it returns the size of the memory allocated - nor the number of elements allocated. See http://msdn.microsoft.com/en-us/library/z2s077bc.aspx
short answer there is no portable way to do so.
There are ways if you want to go into specific compilers like the _msize() trick which will work in so far as the memory allocator isn't being replaced or a custom operator new hasn't been provided for the datatype.
The above is precicely why you would want to use something like vector instead (which makes it RAII too, so you get that as an added bonus).
true, but.
Maybe that the compiler he uses but still wants a portable solution
Maybe he doesn't use VC and just posted it here because none of the other subforums looked better to him.
And even if VC specific... It is still a non-portable issue even if you stay within a particular brand of compiler. VC2010 may do this entirely differently from VC2013 and this is perfectly fine, because the language doesn't define how to solve the problem of "knowing how many elements an array holds" it is compiler (and even possible version) dependent. So this is what I meant.
if you want this to work with a specific brand AND version... then there are ways...
for VC specific (with subtle changes depending on version).
whenever you allocate memory, the C-runtime overallocates and places a structure at the front of the actual allocated memory, a start marker, then comes your allocated data which is returned as the value from operator new and it ends with a end marker.
The start/end marker are used to identify memory overwrites and is typically only present in debugbuilds, though you can have this enabled in release builds too.
for VC2010.
If the type you are array-allocating has a destructor, the array size is located as DWORD (for 32bit builds) or a UINT64 (for Win64builds) just before the allocated pointer.
Do not assume this is the case for non-array allocates as it isn't.
Do not assume this is the case for overloaded operator new[].
Do not assume this is the case for types that do not have a destructor.
So if the type has a destructor AND you use array-allocate via the normal global operator new[] then:
If there is no destructor, there is no guaranteed way in VC, though you can make "educated guesses" as to the size. The problem is that on allocate, the C-Runtime overallocates and rounds up allocation size. So something like _msize() may be larger than what you allocated.Code:CString* ps = new CString[123];
DWORD size = *(reinterpret_cast<DWORD*>(ps)-1); // size = 123
delete [] ps;