Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads have no legal conversion for 'this' pointer

589 views
Skip to first unread message

Bob

unread,
Nov 14, 2008, 4:21:23 PM11/14/08
to
Ive only done a little compiling in VS 2003 with wxWidgets. Im trying
to compile
source code that was developed under VS6.0 under VS 2003 and Im
getting the
following error:

error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads
have no legal conversion for 'this' pointer
with
[
BaseType=TCHAR
]

from this line:

ReadLog(logFiles.GetAt(0).GetBuffer(0));

where logFiles is a CStringArray

Can anyone help me fix this properly and get it to compile properly?
I looked at it but cant figure it out.

Thanks in advance

Doug Harrison [MVP]

unread,
Nov 14, 2008, 4:47:39 PM11/14/08
to

I don't see any reason it should fail, unless GetAt(0) is returning a const
CString or const CString&. What happens if you write it like this:

CString s = logFiles.GetAt(0);
ReadLog(s.GetBuffer(0));

BTW, is that GetBuffer(0) correct, and are you sure you're not subject to
buffer overruns?

--
Doug Harrison
Visual C++ MVP

Joseph M. Newcomer

unread,
Nov 14, 2008, 5:14:40 PM11/14/08
to
See below...

On Fri, 14 Nov 2008 15:47:39 -0600, "Doug Harrison [MVP]" <d...@mvps.org> wrote:

>On Fri, 14 Nov 2008 13:21:23 -0800 (PST), Bob <je...@rahul.net> wrote:
>
>>Ive only done a little compiling in VS 2003 with wxWidgets. Im trying
>>to compile
>>source code that was developed under VS6.0 under VS 2003 and Im
>>getting the
>>following error:
>>
>>error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads
>>have no legal conversion for 'this' pointer
>> with
>> [
>> BaseType=TCHAR
>> ]
>>
>>from this line:
>>
>>ReadLog(logFiles.GetAt(0).GetBuffer(0));
>>
>>where logFiles is a CStringArray
>>
>>Can anyone help me fix this properly and get it to compile properly?
>>I looked at it but cant figure it out.
>
>I don't see any reason it should fail, unless GetAt(0) is returning a const
>CString or const CString&. What happens if you write it like this:
>
> CString s = logFiles.GetAt(0);
> ReadLog(s.GetBuffer(0));

***
This would make a copy of the CString in location 0 of the array. The meaning of
ReadLog() is unspecified; if it is
ReadLog(LPTSTR p);
then this would damage random memory, because GetBuffer(0) would return a buffer of 0
length.

This looks like a poor implementation of a way to read the lines of a log into an array.
It reads into the 0th element of the array (so why is there an array at all?) and gets a
buffer of length 0 into which to put it.

Among other things, it looks like someone asking how to get bad code to work to solve an
unspecified problem. Perhaps a specification of the problem might lead to a reasonable
solution. For example, why does ReadLog apparently want an LPTSTR when a CString & would
have been a better choice?
joe
****


>
>BTW, is that GetBuffer(0) correct, and are you sure you're not subject to
>buffer overruns?

Joseph M. Newcomer [MVP]
email: newc...@flounder.com
Web: http://www.flounder.com
MVP Tips: http://www.flounder.com/mvp_tips.htm

Bob

unread,
Nov 14, 2008, 6:06:39 PM11/14/08
to
On Nov 14, 3:14 pm, Joseph M. Newcomer <newco...@flounder.com> wrote:
> See below...
> On Fri, 14 Nov 2008 15:47:39 -0600, "Doug Harrison [MVP]" <d...@mvps.org> wrote:
>
>
>
> >On Fri, 14 Nov 2008 13:21:23 -0800 (PST), Bob <j...@rahul.net> wrote:
>
> >>Ive only done a little compiling in VS 2003 with wxWidgets.  Im trying
> >>to compile
> >>source code that was developed under VS6.0 under VS 2003 and Im
> >>getting the
> >>following error:
>
> >>error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads
> >>have no legal conversion for 'this' pointer
> >>        with
> >>        [
> >>            BaseType=TCHAR
> >>        ]
>
> >>from this line:
>
> >>ReadLog(logFiles.GetAt(0).GetBuffer(0));
>
> >>where logFiles is a CStringArray
>
> >>Can anyone help me fix this properly and get it to compile properly?
> >>I looked at it but cant figure it out.
>
> >I don't see any reason it should fail, unless GetAt(0) is returning a const
> >CString or const CString&. What happens if you write it like this:
>
> >   CString s = logFiles.GetAt(0);
> >   ReadLog(s.GetBuffer(0));
>

That fixed it. Thank you! I didnt write this code, a client wants
me to modify it to do some extra stuff, so someone else wrote some
poor code apparently. The client bought the source from some company.

Thanks again

Doug Harrison [MVP]

unread,
Nov 14, 2008, 11:43:44 PM11/14/08
to
On Fri, 14 Nov 2008 15:06:39 -0800 (PST), Bob <je...@rahul.net> wrote:

>> >I don't see any reason it should fail, unless GetAt(0) is returning a const
>> >CString or const CString&. What happens if you write it like this:
>>
>> >   CString s = logFiles.GetAt(0);
>> >   ReadLog(s.GetBuffer(0));
>>
>
>That fixed it. Thank you! I didnt write this code, a client wants
>me to modify it to do some extra stuff, so someone else wrote some
>poor code apparently. The client bought the source from some company.
>
>Thanks again

At this point, I was just trying to understand why it wasn't compiling.
Your result would seem to confirm that GetAt(0) is returning a const
CString or const CString&, and you should be able to verify that by looking
at the CStringArray class, comparing VC6 to VC.NET 2003. The original code
apparently was intended to update the CStringArray, and this altered code
does not; it merely updates the copy of the string returned by GetAt(0)
stored in the local variable "s". So I would think you've got some more
work to do.

Doug Harrison [MVP]

unread,
Nov 14, 2008, 11:58:21 PM11/14/08
to
On Fri, 14 Nov 2008 17:14:40 -0500, Joseph M. Newcomer
<newc...@flounder.com> wrote:

>See below...
>On Fri, 14 Nov 2008 15:47:39 -0600, "Doug Harrison [MVP]" <d...@mvps.org> wrote:
>
>>On Fri, 14 Nov 2008 13:21:23 -0800 (PST), Bob <je...@rahul.net> wrote:
>>
>>>Ive only done a little compiling in VS 2003 with wxWidgets. Im trying
>>>to compile
>>>source code that was developed under VS6.0 under VS 2003 and Im
>>>getting the
>>>following error:
>>>
>>>error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads
>>>have no legal conversion for 'this' pointer
>>> with
>>> [
>>> BaseType=TCHAR
>>> ]
>>>
>>>from this line:
>>>
>>>ReadLog(logFiles.GetAt(0).GetBuffer(0));
>>>
>>>where logFiles is a CStringArray
>>>
>>>Can anyone help me fix this properly and get it to compile properly?
>>>I looked at it but cant figure it out.
>>
>>I don't see any reason it should fail, unless GetAt(0) is returning a const
>>CString or const CString&. What happens if you write it like this:
>>
>> CString s = logFiles.GetAt(0);
>> ReadLog(s.GetBuffer(0));

NB: I suggested that code not as a solution but to test the hypothesis that
preceded it. Sorry if that wasn't clear, and see my reply to the OP for
additional follow-up.

>This would make a copy of the CString in location 0 of the array. The meaning of
>ReadLog() is unspecified; if it is
> ReadLog(LPTSTR p);
>then this would damage random memory, because GetBuffer(0) would return a buffer of 0
>length.

Right, which is why I immediately followed the above with:

>>BTW, is that GetBuffer(0) correct, and are you sure you're not subject to
>>buffer overruns?

It could be expected to work right only if the string had a preset length
greater than any that could be retrieved by ReadLog, which seems very risky
and strange to me. (AFAIK, GetBuffer(n) for n < the CString's current
capacity won't shrink the capacity.)

>This looks like a poor implementation of a way to read the lines of a log into an array.
>It reads into the 0th element of the array (so why is there an array at all?) and gets a
>buffer of length 0 into which to put it.
>
>Among other things, it looks like someone asking how to get bad code to work to solve an
>unspecified problem. Perhaps a specification of the problem might lead to a reasonable
>solution. For example, why does ReadLog apparently want an LPTSTR when a CString & would
>have been a better choice?
> joe

Good questions all, but the guy was trying to get his existing code which
apparently worked before to work once again, and the newer compiler
refusing the existing code may indicate a flaw in the existing code. If we
can figure out why the newer compiler isn't liking the code, a design flaw
or two might become apparent.

Giovanni Dicanio

unread,
Nov 15, 2008, 4:52:10 AM11/15/08
to

"Bob" <je...@rahul.net> ha scritto nel messaggio
news:cfafb4cd-c278-4621...@i20g2000prf.googlegroups.com...

> Im trying
> to compile
> source code that was developed under VS6.0 under VS 2003 and Im
> getting the
> following error:
>
> error C2663: 'ATL::CSimpleStringT<BaseType>::GetBuffer' : 2 overloads
> have no legal conversion for 'this' pointer

>[...]


> from this line:
>
> ReadLog(logFiles.GetAt(0).GetBuffer(0));
>
> where logFiles is a CStringArray

CStringArray::GetAt() of VC6 is different from CStringArray::GetAt() of
VS2008 (a.k.a. VC9). I verified that opening afxcoll.h file in both versions
(<afxcoll.h> is where CStringArray class is defined).
I don't have VS.NET 2003 (VC7.1) installed on this PC, but I think that
VC7.1 definition is the same of VS2008.

So, in good old VC6 CStringArray::GetAt() is declared like this:

CString GetAt(int nIndex) const;

This means that GetAt() returns a "deep" copy of the string (not just a
reference), so GetAt() can be qualified as const, and the caller can modify
the string returned by GetAt() (because the modifications to the returned
string do not impact the string stored in the collection).

Instead, in more modern VCs, the prototype of GetAt() is this:

const CString& GetAt(INT_PTR nIndex) const;

This means that GetAt() returns a *const reference* to the string at nIndex
position. So, you *can't* modify that string, because it is a const
reference.

But if you write code like this - like Doug posted:

CString s = logFiles.GetAt(0);

then a deep copy is created from the const reference returned from GetAt(),
and you can modify 's' (you are *not* touching the string in the
collection).

If you want to modify the string in the collection at given position, you
may want to use ElementAt(), which has this prototype:

CString& ElementAt(int nIndex);

So, it returns a non-const reference to string at given index, and you can
modify the content of that string.

HTH,
Giovanni


Giovanni Dicanio

unread,
Nov 15, 2008, 5:01:58 AM11/15/08
to

"Doug Harrison [MVP]" <d...@mvps.org> ha scritto nel messaggio
news:ueksh4l4c3h97bei2...@4ax.com...

> At this point, I was just trying to understand why it wasn't compiling.
> Your result would seem to confirm that GetAt(0) is returning a const
> CString or const CString&, and you should be able to verify that by
> looking
> at the CStringArray class, comparing VC6 to VC.NET 2003. The original code
> apparently was intended to update the CStringArray, and this altered code
> does not; it merely updates the copy of the string returned by GetAt(0)
> stored in the local variable "s". So I would think you've got some more
> work to do.

I verified that the prototype of CStringArray::GetAt() in VC6 is

CString GetAt(int nIndex) const;

so also in VC6 he is modifying a copy of the string (not the string in the
collection).

In modern version of VS the prototype returns a const reference to CString
(const CString &), and the compiler correctly complains (because the OP
can't modify a const CString &).

Maybe there is a bug in the original code, and it showed now after upgrading
to more modern VS? :)

If the OP wants to modify the string in the collection, I think he should
use ElementAt(), which returns a CString &.

(BTW: CStringArray interface is kind of confusing - another reason for me to
prefer std::vector< CString > or vector< wstring >).

Giovanni

Doug Harrison [MVP]

unread,
Nov 15, 2008, 3:24:45 PM11/15/08
to
On Sat, 15 Nov 2008 11:01:58 +0100, "Giovanni Dicanio"
<giovanniD...@REMOVEMEgmail.com> wrote:

>I verified that the prototype of CStringArray::GetAt() in VC6 is
>
> CString GetAt(int nIndex) const;
>
>so also in VC6 he is modifying a copy of the string (not the string in the
>collection).
>
>In modern version of VS the prototype returns a const reference to CString
>(const CString &), and the compiler correctly complains (because the OP
>can't modify a const CString &).

Ah, that explains it then.

>Maybe there is a bug in the original code, and it showed now after upgrading
>to more modern VS? :)

The question is, which original code was more at fault? :) The OP's code
was wrong, but it compiled only due to a design flaw in the VC6
CStringArray.

>If the OP wants to modify the string in the collection, I think he should
>use ElementAt(), which returns a CString &.
>
>(BTW: CStringArray interface is kind of confusing - another reason for me to
>prefer std::vector< CString > or vector< wstring >).

I've never used CStringArray, but I guess ElementAt must also have been
available in VC6. It is indeed very confusing to have the two functions
GetAt and ElementAt. Only the latter is essential, and there is no concept
of "GetAt" for arrays anyway. That is, either the array is an array of
const or it is not, and it is that which determines the type of element you
get when you access the array, not the means of accessing it.

0 new messages