This is the mail archive of the
libstdc++@gcc.gnu.org
mailing list for the libstdc++ project.
Re: libstdc++/8230: Buggy allocator behaviour
- From: Gabriel Dos Reis <gdr at integrable-solutions dot net>
- To: bkoz at gcc dot gnu dot org
- Cc: gcc-bugs at gcc dot gnu dot org, jkanze at caicheuvreux dot com, gcc-gnats at gcc dot gnu dot org, libstdc++ at gcc dot gnu dot org
- Date: 14 Nov 2002 15:59:43 +0100
- Subject: Re: libstdc++/8230: Buggy allocator behaviour
- Organization: Integrable Solutions
- References: <20021113221911.21632.qmail@sources.redhat.com>
bkoz@gcc.gnu.org writes:
| Synopsis: Buggy allocator behaviour
|
| Responsible-Changed-From-To: unassigned->bkoz
| Responsible-Changed-By: bkoz
| Responsible-Changed-When: Wed Nov 13 14:19:11 2002
| Responsible-Changed-Why:
| Mine.
| State-Changed-From-To: open->feedback
| State-Changed-By: bkoz
| State-Changed-When: Wed Nov 13 14:19:11 2002
| State-Changed-Why:
| I don't think this is an allocator::allocate issue per se. The member function reserve is only in std::vector and std::vector<bool>, and the standard says
Hi Benjamin,
This issue is a conjugation of both std::allocator<> and
std::vector<> ill-behaviour. Fixing std::vector<> fixes a part of
the problem (i.e. the testcase provided will pass), but leaves
completely unfixed the std::allocator<> bits as required by the
standard:
20.4.1.1 allocator members
2/
pointer allocator(size_type n, allocator<void>::const_pointer = 0);
7/
Throws: bad_alloc if the storage cannot be obtained
20.4.1.1/11
size_type max_size() const throw();
returns the largest value N for which the call allocate(N, 0) might
succeed.
Now consider
int main()
{
try {
std::allocator<int> alloc;
const std::allocator<int>::size_type n = alloc.max_size();
int* p = alloc.allocate(n + 1);
p[n] = 2002;
std::cout << p[n] << std::endl;
} catch(const std::bad_alloc& e) {
std::cerr << e.what() << std::endl;
}
}
This coredumps on my machine using current source. The problem here is
that std::allocator<> is not checking the bounds as required and it is
lying.
On fr.comp.lang.c++, I developed a theory to the effect that
std::vector<> may always not check the bounds and still remain
conformant *provided* that the allocator is doing the right thing.
| 23.2.4.2 - vector capacity
|
| -4- Throws: length_error if n > max_size().*
|
| Where allocator::allocate doesn't know what vector::max_size is.
Agreed.
|
| This fix brings the code up to conformance, and is the best fix I think.
It, however, does not address the std::allocator<> ill-behaviour.
I'm also nervous about:
std::vector<int> v;
v.resize(v.max_size());
v[v.max_size() - 1] = 2002;
I didn't test it with your patch.
-- Gaby