|
-
July 24th, 2006, 05:18 PM
#1
another compiler bug?
i got the folowing code:
Code:
unsigned int val1;
void* ptr1 = (void*)val1;
void* ptr2;
ptr1 += ptr2;
then i get the errors:
'+=' : illegal, right operand has type 'void *'
'+=' : pointer on left; needs integral value on right
1. pointers ARE integers.
2. ptr + ptr works why doesnt ptr += ptr?
is the compiler confused because of the int to ptr? (wich i had to type cast, even though pointers are integral)
Last edited by Mitsukai; July 24th, 2006 at 05:29 PM.
-
July 24th, 2006, 05:29 PM
#2
Re: another compiler bug?
1) False, pointers are not integral.
2) ptr + ptr does not work. (error C2110)
3) You can not perform arithmatic on void pointers anyways
-
July 24th, 2006, 05:30 PM
#3
Re: another compiler bug?
pointers are integral. they store the adress of a function or variable
-
July 24th, 2006, 05:32 PM
#4
Re: another compiler bug?
i geuss its not a compiler bug but rather a bug in the standards.
they dont see the need for an int to ptr and ptr+ptr
but i just had had a situation that i needed to.
forcing to type casting is a bit ugly
-
July 24th, 2006, 05:33 PM
#5
Re: another compiler bug?
>> 1. pointers ARE integers.
Chars are integers too, in the end.
>> 2. ptr + ptr works why doesnt ptr += ptr?
ptr + ptr works?
What is the sence of adding 2 pointers?
-
July 24th, 2006, 05:53 PM
#6
Re: another compiler bug?
 Originally Posted by Dmitry Zemskov
What is the sence of adding 2 pointers?
i will give you a simple example.
Code:
struct SA
{
int size;
int* data;
};
void FA(const struct SA& PA, const int new_size)
{
int* tmp_data = new int[new_size];
memcpy(tmp_data, PA.data, (PA.size > new_size) ? new_size : PA.size * sizeof(int));
delete[] data;
PA.data = tmp_data;
PA.size = new_size;
}
int main(void)
{
SA LA;
LA.data = new int[LA.size = 1234];
int* LB = LA.size;
FA(LA, 4321);
LB += LA.data; // we now have position of the added space
delete[] LA.data;
}
-
July 24th, 2006, 06:34 PM
#7
Re: another compiler bug?
Man, that's an int, not an int * Plus
Code:
"ComeauTest.c", line 15: error: identifier "data" is undefined
delete[] data;
^
"ComeauTest.c", line 16: error: expression must be a modifiable lvalue
PA.data = tmp_data;
^
"ComeauTest.c", line 17: error: expression must be a modifiable lvalue
PA.size = new_size;
^
"ComeauTest.c", line 24: error: a value of type "int" cannot be used to initialize
an entity of type "int *"
int* LB = LA.size;
^
"ComeauTest.c", line 26: error: expression must have integral or enum type
LB += LA.data; // we now have position of the added space
-
July 24th, 2006, 08:04 PM
#8
Re: another compiler bug?
 Originally Posted by Mitsukai
i geuss its not a compiler bug but rather a bug in the standards.
I'm sure it standarized that way for a purpose.
 Originally Posted by Mitsukai
they dont see the need for an int to ptr
That you can do with a reinterpret_cast.
 Originally Posted by Mitsukai
and ptr+ptr
How would that work? Currently you can add an integer to a pointer (not a void one) and it is evaluated somewhat like this:
Code:
int* ptr = reinterpret_cast<int*>(0x1000);
int n = 5;
// ptr += n;
ptr = reinterpret_cast<int*>(reinterpret_cast<size_t>(ptr) + sizeof(int) * n);
That is, if you add 5 to the an int*, then the value of int* is increased by sizeof(int) * 5. In other words the pointer will point to the 5. integer following its original value. How would you apply this simple rule when adding two pointers? It's called pointer arithmetic and I'm sure it has been discussed since pre-c++.
You can however subtract two pointers (of same type) from eachother. The rusult, a ptrdiff_t, gives the numbers of elements between the two pointers:
Code:
int arr[10];
int* ptrA = &arr[1];
int* ptrB = &arr[5];
ptrdiff_t diff = ptrB - ptrA; // results in 4
Both pointers should be pointing to the same array (but not necessarily within the bound of that array). Why? Because otherwise would have strange effects on your code:
Code:
int* ptrA = reinterpret_cast<int*>(0x100);
int* ptrB = reinterpret_cast<int*>(0x102); // different, but not by a complete sizeof(int)
if (ptrA == ptrB)
{
// they're equal (this won't happen)
}
if ((ptrA - ptrB) == 0)
{
// they're equal, strange... this will happen
}
 Originally Posted by Mitsukai
but i just had had a situation that i needed to.
forcing to type casting is a bit ugly
From what Calculator posted, type casting isn't the worst that could happen to that code...
- petter
-
July 24th, 2006, 08:19 PM
#9
Re: another compiler bug?
i geuss thats true. i forgot about pointer arithmetic.
but i do not understand this.
it does accept a ptr+=int but not a ptr=int?
maybe i should use an integer and cast it to a pointer than other wise..
-
July 24th, 2006, 08:57 PM
#10
Re: another compiler bug?
ptr += int makes sense. ptr points to a location in memory. adding to the pointer makes it point to a different place in memory. wildfrog explained how the expression ptr += int will increment the pointer by the sizeof *ptr * int. But the problem is that an int is not a pointer, it is not meant to address memory, even if it has the ability to. The C FAQ explains what I was just about to try to explain very well 10.2 Pointers and Arrays; Pointer Arithmetic
-
July 24th, 2006, 09:24 PM
#11
Re: another compiler bug?
 Originally Posted by Mitsukai
i will give you a simple example.
Code:
struct SA
{
int size;
int* data;
};
void FA(struct SA& PA, const int new_size)
{
int* tmp_data = new int[new_size];
memcpy(tmp_data, PA.data, (PA.size > new_size) ? new_size : PA.size * sizeof(int));
delete[] PA.data;
PA.data = tmp_data;
PA.size = new_size;
}
int main(void)
{
SA LA;
LA.data = new int[LA.size = 1234];
int LB = LA.size * sizeof(int); //int* LB = LA.size;
FA(LA, 4321);
LB += (int)LA.data; // LB += LA.data;
delete[] LA.data;
}
i edited my code (it was just a quick example out of hand)
Last edited by Mitsukai; July 24th, 2006 at 09:38 PM.
-
July 24th, 2006, 09:34 PM
#12
Re: another compiler bug?
btw i know how ptrs work =]
the reason behind my dumb post is time, it is 4:43 am heh
-
July 24th, 2006, 09:41 PM
#13
Re: another compiler bug?
Yup, it's late (again).
Code:
LB += (int)LA.data; // LB += LA.data;
int isn't necessarily large enough to hold a pointer. You should use intptr_t.
- petter
-
July 25th, 2006, 01:31 AM
#14
Re: another compiler bug?
 Originally Posted by Mitsukai
it does accept a ptr+=int but not a ptr=int?
In my opinion the only int accepted in "ptr = int" is zero, meaning "null pointer":
Usually it is defined as NULL:
Code:
#define NULL 0 // (from WinDef.h)
. . .
ptr = NULL;
-
July 25th, 2006, 05:50 AM
#15
Re: another compiler bug?
 Originally Posted by Mitsukai
Code:
struct SA
{
int size;
int* data;
};
void FA(const struct SA& PA, const int new_size)
{
int* tmp_data = new int[new_size];
memcpy(tmp_data, PA.data, (PA.size > new_size) ? new_size : PA.size * sizeof(int));
delete[] data;
PA.data = tmp_data;
PA.size = new_size;
}
int main(void)
{
SA LA;
LA.data = new int[LA.size = 1234];
int* LB = LA.size;
FA(LA, 4321);
LB += LA.data; // we now have position of the added space
delete[] LA.data;
}
It makse no sense
 Originally Posted by Mitsukai
1. pointers ARE integers.
NO.
Pointers can be represented by integers on all platforms, transforming a non flat memory space in a flat memory space, but the process can be very very SLOW.
You want to impose a particular representation for pointers.
Just think about far pointers on x86-16 platforms.
First, pointers usually have a different size from integers.
It can be greater, or it can be smaller.
You piece of code... How would you expect it to work...
Assuming a x86-32 architecture without sizeof(int)==sizeof(void*), and a FLAT addressing space:
In fact, the only thing I see with your code, is that you are not able to use a typed language.
There exists untyped language, such as B.
BUT.
- They are very inefficient (or impossible to implement) on platforms having a non-flat addressing mode (such as x86-16)
- They are *still* very inefficient on platforms with a flat memory model.
- It's a real problem for such languages to choose a "word" size... Which must be the same for pointers & integers.
That's very problematic on many platforms. - Accessing other things than words (such as individual chars or floating point values) is very inefficent or incredibely error prone or incredibely verbose.
Non-typed language, in a general sense, are incredibely error prone.
Plus, it is very hard for the compiler to optimize things.
Even early C compilers were less weakly typed that what you want.
What's wrong with
Code:
int main(void)
{
SA LA;
LA.data = new int[LA.size = 1234];
int LA_old_size = LA.size;
FA(LA, 4321);
int* LB =LA.data + LA_old_size;
delete[] LA.data;
}
Last edited by SuperKoko; July 25th, 2006 at 05:53 AM.
"inherit to be reused by code that uses the base class, not to reuse base class code", Sutter and Alexandrescu, C++ Coding Standards.
Club of lovers of the C++ typecasts cute syntax: Only recorded member.
Out of memory happens! Handle it properly!
Say no to g_new()!
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|