473,385 Members | 1,409 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,385 software developers and data experts.

end of array

Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?

Mar 4 '07 #1
21 3748
su**************@yahoo.com, India wrote:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?
It's allowed because certain idiomatic loop constructs are made easier
if it was allowed to end up one past an array. The famous strcpy loop
is an example.

Mar 4 '07 #2
On Mar 4, 12:57 pm, "subramanian10...@yahoo.com, India"
<subramanian10...@yahoo.comwrote:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?
One important facet of C spirit is that "Trust the programmer." C
gives you the power to do _nearly_ whatever you want (Segment fault or
something like that is what the OS gives you, not C). C is designed
for that because it was used to write the Unix kernel originally, this
niche determines C can't be too complex and can't hide something
behide programmers.

You can, of course, use any feature like that freely, but C can't
guarantee that will be right. Making sure that's right is your work.

Mar 4 '07 #3
It's allowed because certain idiomatic loop constructs are
made easier
if it was allowed to end up one past an array. The famous
strcpy loop is an example.
Isn't what you have mentioned, an example of pointer ?

With array, why is it allowed

Mar 4 '07 #4
su**************@yahoo.com, India wrote:
It's allowed because certain idiomatic loop constructs are
made easier
if it was allowed to end up one past an array. The famous
strcpy loop is an example.

Isn't what you have mentioned, an example of pointer ?

With array, why is it allowed
Because most often, pointers are used to point to and iterate through
arrays.

Mar 4 '07 #5
At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?
You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];

p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.
--
Daniel Rudy

Email address has been base64 encoded to reduce spam
Decode email address using b64decode or uudecode -m

Why geeks like computers: look chat date touch grep make unzip
strip view finger mount fcsk more fcsk yes spray umount sleep
Mar 5 '07 #6
Daniel Rudy wrote:
At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?

You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];

p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.
Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.

Mar 5 '07 #7
At about the time of 3/5/2007 7:14 AM, santosh stated the following:
Daniel Rudy wrote:
>At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
>>Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?
You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];

p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.

Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.
Of course. I'm thinking in terms of Unix. I guess that on a windows
system you would get a program error or maybe even a blue-screen. On a
DOS system, it could keep running depending on what was accessed at that
location.

UB = Undefined Behavior = Platform/Implementation specific results.

And the lesson here folks is don't exceed your defined array dimensions.
You can kill your program, your system, or worse.

--
Daniel Rudy

Email address has been base64 encoded to reduce spam
Decode email address using b64decode or uudecode -m

Why geeks like computers: look chat date touch grep make unzip
strip view finger mount fcsk more fcsk yes spray umount sleep
Mar 5 '07 #8
santosh wrote, On 05/03/07 15:14:
Daniel Rudy wrote:
>At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
>>Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?
You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];
No you can't. Or rather you can, but since you are doing pointer
arithmetic that goes more than 1 past the end of the object the pointer
arithmetic invokes undefined behaviour and anything can happen. Note
that the [] operator is defined in terms of pointer arithmetic.
>p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.

Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.
You don't have to attempt to dereference the pointer to invoke undefined
behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.
--
Flash Gordon
Mar 5 '07 #9
At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:
santosh wrote, On 05/03/07 15:14:
>Daniel Rudy wrote:
>>At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?

You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];

No you can't. Or rather you can, but since you are doing pointer
arithmetic that goes more than 1 past the end of the object the pointer
arithmetic invokes undefined behaviour and anything can happen. Note
that the [] operator is defined in terms of pointer arithmetic.
>>p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.
Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.

You don't have to attempt to dereference the pointer to invoke undefined
behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.
Huh?

Just calculating a pointer like that can cause UB? How?

I thought that the compiler was doing something like this:

p = &a[0] + (65536 * sizeof(char));

Am I wrong in this assumption?

--
Daniel Rudy

Email address has been base64 encoded to reduce spam
Decode email address using b64decode or uudecode -m

Why geeks like computers: look chat date touch grep make unzip
strip view finger mount fcsk more fcsk yes spray umount sleep
Mar 5 '07 #10

Daniel Rudy wrote:
At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:
santosh wrote, On 05/03/07 15:14:
Daniel Rudy wrote:
At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
Suppose we have
char array[10];

C allows taking the address of array[10] (ie &array[10] is valid)
though the element array[10] cannot be accessed.

Is this allowed for use in binary search method (as given in K & R
second edition page 137) or is there any other reason ?

You can make a pointer point to anything. As to how useful it is...well
that's up to you.

I can do this:

char a[10], *p;
p = &a[65536];
No you can't. Or rather you can, but since you are doing pointer
arithmetic that goes more than 1 past the end of the object the pointer
arithmetic invokes undefined behaviour and anything can happen. Note
that the [] operator is defined in terms of pointer arithmetic.
>p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.
Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.
You don't have to attempt to dereference the pointer to invoke undefined
behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.

Huh?

Just calculating a pointer like that can cause UB? How?
Yes, since theoretically, an implementation can have different address
spaces for each object. So calculating a value beyond one past the
object, or before it, could trigger a trap.

<snip>

Mar 5 '07 #11
At about the time of 3/5/2007 8:32 AM, santosh stated the following:
Daniel Rudy wrote:
>At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:
>>santosh wrote, On 05/03/07 15:14:
Daniel Rudy wrote:
At about the time of 3/3/2007 8:57 PM, su**************@yahoo.com, India
stated the following:
>Suppose we have
>char array[10];
>>
>C allows taking the address of array[10] (ie &array[10] is valid)
>though the element array[10] cannot be accessed.
>>
>Is this allowed for use in binary search method (as given in K & R
>second edition page 137) or is there any other reason ?
>>
You can make a pointer point to anything. As to how useful it is...well
that's up to you.
>
I can do this:
>
char a[10], *p;
p = &a[65536];
No you can't. Or rather you can, but since you are doing pointer
arithmetic that goes more than 1 past the end of the object the pointer
arithmetic invokes undefined behaviour and anything can happen. Note
that the [] operator is defined in terms of pointer arithmetic.

p is a pointer, it does point to something, but if I try to use it, then
I will probably get a segmentation fault or a memory fault. In either
case, the program will dump core.
Not necessarily. The behaviour is undefined if you happen to access
memory you don't own. Undefined means anything can happen. Under
modern memory protected OSen, the programme will, as you note, be
terminated, but under other systems, it could very well keep running,
but yield wrong results or a system hangup.
You don't have to attempt to dereference the pointer to invoke undefined
behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.
Huh?

Just calculating a pointer like that can cause UB? How?

Yes, since theoretically, an implementation can have different address
spaces for each object. So calculating a value beyond one past the
object, or before it, could trigger a trap.

<snip>
I just wrote the following program, and basically it did what it was
supposed to do:

/*
Undefined Behavior Test Program #2
*/

#include <stdio.h>
#include <stdlib.h>

int main(void)
{
char a[10], *p;

printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);
return(0);
}

I got this result:

strata:/home/dr2867/c/test 1065 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
strata:/home/dr2867/c/test 1066 $$$ ->
Now for program 2:

/*
Undefined Behavior Test Program #2
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(void)
{
char a[10], *p;

/* calculate an out of bounds pointer */
printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);

/* try and use it */
printf("Now we try something else...\n");
memcpy(a, p, sizeof(a));
printf("How did you like that?\n");
return(0);
}

And this is what I got:

strata:/home/dr2867/c/test 1072 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
Now we try something else...
Memory fault (core dumped)
strata:/home/dr2867/c/test 1073 $$$ ->
This tells me that a pointer is a variable...nothing more, nothing less.
It's a unit of storage in the computer's memory that holds a value
regardless of what that location's intended use is. Calculating some
junk and putting it there doesn't do anything except put junk at that
location (The location of the actual pointer itself, not what it points
to.).

Now, if you try to use that junk (pointer) for it's intended use of
pointing to a memory object, that's when you get undefined behavior.
So, looking at what I did, I got a memory fault...also known as a
general protection fault to the windows crowd.

The lesson here folks is do not access an array beyond it's bounds, and
don't go trying to access memory that doesn't belong to you. Your
programs and your hairline live much longer.
--
Daniel Rudy

Email address has been base64 encoded to reduce spam
Decode email address using b64decode or uudecode -m

Why geeks like computers: look chat date touch grep make unzip
strip view finger mount fcsk more fcsk yes spray umount sleep
Mar 5 '07 #12
Daniel Rudy <ZGNydWR5QHBhY2JlbGwubmV0wrote:
>We did it. Result is 0xbfc0ec1f
Here are the relevant parts of the standard that say it's undefined
behavior, which means it's totally possible that your implementation
could behave exactly as it did. :)

C99 6.5.2.1p2, Array subscripting:

# A postfix expression followed by an expression in square brackets []
# is a subscripted designation of an element of an array object. The
# definition of the subscript operator [] is that E1[E2] is identical to
# (*((E1)+(E2))). Because of the conversion rules that apply to the
# binary + operator, if E1 is an array object (equivalently, a pointer
# to the initial element of an array object) and E2 is an integer,
# E1[E2] designates the E2-th element of E1 (counting from zero).

C99 6.5.6p8, Additive operators:

# When an expression that has integer type is added to or subtracted
# from a pointer, the result has the type of the pointer operand. If the
# pointer operand points to an element of an array object, and the array
# is large enough, the result points to an element offset from the
# original element such that the difference of the subscripts of the
# resulting and original array elements equals the integer expression.
# In other words, if the expression P points to the i-th element of an
# array object, the expressions (P)+N (equivalently, N+(P)) and (P)-N
# (where N has the value n) point to, respectively, the i+n-th and the
# i-n-th elements of the array object, provided they exist. Moreover, if
# the expression P points to the last element of an array object, the
# expression (P)+1 points one past the last element of the array object,
# and if the expression Q points one past the last element of an array
# object, the expression (Q)-1 points to the last element of the array
# object. If both the pointer operand and the result point to elements
# of the same array object, or one past the last element of the array
# object, the evaluation shall not produce an overflow; otherwise, the
# behavior is undefined. If the result points one past the last element
# of the array object, it shall not be used as the operand of a unary *
# operator that is evaluated.
On the other hand, it sounds to me like you're given more leeway to
blindly convert an integer to a pointer:

C99 6.3.2.3p5, Pointers:

# An integer may be converted to any pointer type. Except as previously
# specified [NULL pointers], the result is implementation-defined, might
# not be correctly aligned, might not point to an entity of the
# referenced type, and might be a trap representation.

-Beej

Mar 5 '07 #13
On Mar 5, 4:26 pm, Daniel Rudy <spamt...@spamthis.netwrote:
Just calculating a pointer like that can cause UB? How?
Because the C Standard says so.

#include <stdio.h>

#define BAD_VALUE ???

size_t test (double *p, size_t n)
{
double* q;
for (q = p; q < p + n; ++q)
if (*q == 1.0) return q-p;

return 9999;
}

int main (void)
{
double a[3] = { 0.0, 1.0, 2.0 };
size_t n = BAD_VALUE;

if (n >= 2 && test (a, n) == 9999)
printf ("Undefined behavior!!!\n");

return 0;
}

Can you define BAD_VALUE in such a way that the program prints
"Undefined behavior!!!"?

Mar 5 '07 #14
Daniel Rudy <sp******@spamthis.netwrites:
[...]
>Daniel Rudy wrote:
>>At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:
[...]
>>>You don't have to attempt to dereference the pointer to invoke undefined
behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.
Huh?

Just calculating a pointer like that can cause UB? How?
Calculating a pointer like that *does* cause undefined behavior. The
trick is to understand what "undefined behavior" means.
I just wrote the following program, and basically it did what it was
supposed to do:
[snip]
And this is what I got:
[snip]
This tells me that a pointer is a variable...nothing more, nothing less.
No, it doesn't tell you any such thing. The *standard* tells you that
performing pointer arithmetic that yields a result that doesn't point
either to an element of the array you started from, or just past the
last element, invokes undefined behavior -- whether you dereference it
or not.

One possible consequence of this undefined behavior (and a fairly
common one), is that it appears to work.

[...]
Now, if you try to use that junk (pointer) for it's intended use of
pointing to a memory object, that's when you get undefined behavior.
So, looking at what I did, I got a memory fault...also known as a
general protection fault to the windows crowd.
When you computed an invalid pointer value, you got undefined
behavior. (It happened to manifest itself quietly.) When you then
attempted to dereference that invalid pointer value, you again got
undefined behavior. (It happened to manifest itself as a program
crash.)

Undefined behavior, as defined by C99 3.4.3, is

behavior, upon use of a nonportable or erroneous program construct
or of erroneous data, for which this International Standard
imposes no requirements

NOTE Possible undefined behavior ranges from ignoring the
situation completely with unpredictable results, to behaving
during translation or program execution in a documented manner
characteristic of the environment (with or without the issuance of
a diagnostic message), to terminating a translation or execution
(with the issuance of a diagnostic message).

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <* <http://users.sdsc.edu/~kst>
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
Mar 6 '07 #15
Daniel Rudy wrote:
At about the time of 3/5/2007 8:32 AM, santosh stated the following:
Daniel Rudy wrote:
At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:
<snip>
>behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.

Huh?

Just calculating a pointer like that can cause UB? How?
Yes, since theoretically, an implementation can have different address
spaces for each object. So calculating a value beyond one past the
object, or before it, could trigger a trap.

<snip>

I just wrote the following program, and basically it did what it was
supposed to do:
When you invoke undefined behaviour, in the context of the C Standard,
then there's no such thing as "what it's supposed to do".
/*
Undefined Behavior Test Program #2
*/
How can you test undefined behaviour?
#include <stdio.h>
#include <stdlib.h>

int main(void)
{
char a[10], *p;

printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);
return(0);
}

I got this result:

strata:/home/dr2867/c/test 1065 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
strata:/home/dr2867/c/test 1066 $$$ ->
Now for program 2:

/*
Undefined Behavior Test Program #2
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(void)
{
char a[10], *p;

/* calculate an out of bounds pointer */
printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);

/* try and use it */
printf("Now we try something else...\n");
memcpy(a, p, sizeof(a));
printf("How did you like that?\n");
return(0);
}

And this is what I got:

strata:/home/dr2867/c/test 1072 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
Now we try something else...
Memory fault (core dumped)
strata:/home/dr2867/c/test 1073 $$$ ->
This tells me that a pointer is a variable...nothing more, nothing less.
It's a unit of storage in the computer's memory that holds a value
regardless of what that location's intended use is. Calculating some
junk and putting it there doesn't do anything except put junk at that
location (The location of the actual pointer itself, not what it points
to.).
That's the case for many, but by no means all architectures. Believe
it or not, there *are*, (or atleast were), very strange machines, that
the C Standard intended to support. That a pointer is an ordinary
object, and that merely calculating a wrong value doesn't cause any
untoward behaviour, is characteristic of merely one particular
hardware architecture.

<snip>

Mar 6 '07 #16
At about the time of 3/5/2007 5:04 PM, santosh stated the following:
Daniel Rudy wrote:
>At about the time of 3/5/2007 8:32 AM, santosh stated the following:
>>Daniel Rudy wrote:
At about the time of 3/5/2007 7:31 AM, Flash Gordon stated the following:

<snip>
>>>>behaviour. Merely calculating a pointer before or more than 1 past the
end of an object invokes undefined behaviour even if you do nothing with
it. Of course, dereferencing a pointer that does not point to a C object
also invokes undefined behaviour that often behaves as you describe,
however it is always possible (as far as the C standard is concerned)
that instead it will make daemons fly out of your nose.
Huh?

Just calculating a pointer like that can cause UB? How?
Yes, since theoretically, an implementation can have different address
spaces for each object. So calculating a value beyond one past the
object, or before it, could trigger a trap.

<snip>
I just wrote the following program, and basically it did what it was
supposed to do:

When you invoke undefined behaviour, in the context of the C Standard,
then there's no such thing as "what it's supposed to do".
>/*
Undefined Behavior Test Program #2
*/

How can you test undefined behaviour?
>#include <stdio.h>
#include <stdlib.h>

int main(void)
{
char a[10], *p;

printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);
return(0);
}

I got this result:

strata:/home/dr2867/c/test 1065 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
strata:/home/dr2867/c/test 1066 $$$ ->
Now for program 2:

/*
Undefined Behavior Test Program #2
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(void)
{
char a[10], *p;

/* calculate an out of bounds pointer */
printf("Here we go...\n");
p = &a[65535];
printf("We did it. Result is %p\n", (void *)p);

/* try and use it */
printf("Now we try something else...\n");
memcpy(a, p, sizeof(a));
printf("How did you like that?\n");
return(0);
}

And this is what I got:

strata:/home/dr2867/c/test 1072 $$$ ->./ub002
Here we go...
We did it. Result is 0xbfc0ec1f
Now we try something else...
Memory fault (core dumped)
strata:/home/dr2867/c/test 1073 $$$ ->
This tells me that a pointer is a variable...nothing more, nothing less.
It's a unit of storage in the computer's memory that holds a value
regardless of what that location's intended use is. Calculating some
junk and putting it there doesn't do anything except put junk at that
location (The location of the actual pointer itself, not what it points
to.).

That's the case for many, but by no means all architectures. Believe
it or not, there *are*, (or atleast were), very strange machines, that
the C Standard intended to support. That a pointer is an ordinary
object, and that merely calculating a wrong value doesn't cause any
untoward behaviour, is characteristic of merely one particular
hardware architecture.

<snip>
No, I believe you when you talk about very strange machines out there.
I've seen some bazaar stuff myself. Oh, I did try it on a PowerPC and a
Sparc machine and it does the exact same thing, so for the majority of
the platforms out there, this does work as *I* expected. But it seems
the standard disagrees with me, so I'm going to leave it alone.

Best advise? Don't do it in the first place.

--
Daniel Rudy

Email address has been base64 encoded to reduce spam
Decode email address using b64decode or uudecode -m

Why geeks like computers: look chat date touch grep make unzip
strip view finger mount fcsk more fcsk yes spray umount sleep
Mar 6 '07 #17
Daniel Rudy said:

<snip>
No, I believe you when you talk about very strange machines out there.
I've seen some bazaar stuff myself. Oh, I did try it on a PowerPC and
a Sparc machine and it does the exact same thing, so for the majority
of
the platforms out there, this does work as *I* expected.
Power PC + Sparc < majority of platforms.
But it seems
the standard disagrees with me, so I'm going to leave it alone.
Wise chap.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at the above domain, - www.
Mar 6 '07 #18
On Mon, 05 Mar 2007 18:53:52 -0800, in comp.lang.c , Daniel Rudy
<sp******@spamthis.netwrote:
>No, I believe you when you talk about very strange machines out there.
I've seen some bazaar stuff myself.

Oooo, an eggcorn!
The word you were looking for was "bizarre" by the way.
--
Mark McIntyre

"Debugging is twice as hard as writing the code in the first place.
Therefore, if you write the code as cleverly as possible, you are,
by definition, not smart enough to debug it."
--Brian Kernighan
Mar 6 '07 #19
Daniel Rudy <ZGNydWR5QHBhY2JlbGwubmV0wrote:
>the platforms out there, this does work as *I* expected. But it seems
the standard disagrees with me, so I'm going to leave it alone.
IMHO, there are many different times and reasons that breaking the
standard is the Right Thing to do. Unlike Richard, most of my code
doesn't tend to be Standard Only.

I think what's more important is that you know when you are using
undefined or unspecified functionality, and note it mentally or
commentally (a word?). Or wrap the nonstandard stuff up cleanly in
functions. Or something.

/* non-portable code ahead: */
char *v = (char*)0xf000; /* start of video ram on the Osborne 1 */
/* Z80 is little-endian!: */
*((unsigned short*)v) = 0x6542; /* put 'Be' on the screen */
*((unsigned short*)(v+2)) = 0x6a65; /* put 'ej' after that */

(I didn't test that. I no longer have an Osborne 1. But I remember
where screen memory starts, uselessly. gcc did compile it cleanly, and
it segfaulted when I ran it. :)

It'll help people who are trying to port your code if something gets
weird, and it'll help you port other peoples' code. Maybe you are doing
some out of bounds array accessing, and it just isn't working like
you're expecting--but you know that could be because the Standard allows
for that kind of unexpected behavior.

Over the years, I've seen similar things rear their heads: a misaligned
memory access worked great on one platform, and silently produced bad
results on another platform. Knowing that it wasn't portable made
finding and repairing the bug that much easier.

-Beej

Mar 6 '07 #20
In article <es**********@aioe.orgBeej Jorgensen <be**@beej.uswrote:
>IMHO, there are many different times and reasons that breaking the
standard is the Right Thing to do.
I agree, although I will modify that to say "the C Standards"
(C89, C95, C99). Often one uses some sort of mostly-standard
(or even fairly-extended) C along with some auxiliary standard,
such as the architecture manual for your the hardware in
question. In this case, violating the requirements give in
the "hardware standard" is rarely (but still sometimes) the
Right Thing.
>Unlike Richard, most of my code doesn't tend to be Standard Only.
(I find that more than half of the code I write is, and less than
half is not. The big trick is keeping these parts as separate as
possible.)
>I think what's more important is that you know when you are using
undefined or unspecified functionality, and note it mentally or
commentally (a word?). Or wrap the nonstandard stuff up cleanly in
functions. Or something.
Even more important than that is making a trade-off decision:
Is there a "portable way" to do it? If so, what are the costs
and benefits? If the majority of some body of code *could* be
portable at some (nonzero) cost, is it worth paying that cost?
The answers to these questions are Engineering Answers, and can
be difficult to compute with any accuracy since the costs and
benefits are often both somewhat fuzzy. Worse, the costs tend
to be up-front, with the benefits coming later (if at all).

Once you do decide, for whatever reason, to "go non-standard",
though, this sort of marking and separating out the "nonportable
parts" *is* a good idea. You will still get the blame for the
lack-of-later-benefits when the next guy has to fix the code for
the new system, of course. :-)
--
In-Real-Life: Chris Torek, Wind River Systems
Salt Lake City, UT, USA (40°39.22'N, 111°50.29'W) +1 801 277 2603
email: forget about it http://web.torek.net/torek/index.html
Reading email is like searching for food in the garbage, thanks to spammers.
Mar 7 '07 #21
Daniel Rudy wrote:
I can do this:

char a[10], *p;
p = &a[65536];

p is a pointer, it does point to something,
No. Simply calculating (a + 65535) is undefined.

--
pete
Mar 11 '07 #22

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

2
by: Brian | last post by:
I'm diddlying with a script, and found some behavior I don't understand. Take this snippet: for ($i = 0; $i <= count($m); $i++) { array_shift($m); reset($m); }
2
by: Stormkid | last post by:
Hi Group I'm trying to figure out a way that I can take two (two dimensional) arrays and avShed and shed, and subtract the matching elements in shed from avShed I've pasted the arrays blow from a...
15
by: lawrence | last post by:
I wanted to test xml_parse_into_struct() so I took the example off of www.php.net and put this code up on a site: <?php $simple = <<<END <item>
8
by: vcardillo | last post by:
Hello all, Okay, I am having some troubles. What I am doing here is dealing with an employee hierarchy that is stored in an array. It looks like this: $employees = array( "user_id" => array(...
12
by: Sam Collett | last post by:
How do I remove an item with a specified value from an array? i.e. array values 1,2,2,5,7,12,15,21 remove 2 from array would return 1,5,7,12,15,21 (12 and 21 are NOT removed, duplicates are...
8
by: Mike S. Nowostawsky | last post by:
I tried using the "toUpperCase()" property to change the value of an array entity to uppercase BUT it tells me that the property is invalid. It seems that an array is not considered an object when...
58
by: jr | last post by:
Sorry for this very dumb question, but I've clearly got a long way to go! Can someone please help me pass an array into a function. Here's a starting point. void TheMainFunc() { // Body of...
104
by: Leszek | last post by:
Hi. Is it possible in javascript to operate on an array without knowing how mamy elements it has? What i want to do is sending an array to a script, and this script should add all values from...
7
by: Jim Carlock | last post by:
Looking for suggestions on how to handle bad words that might get passed in through $_GET variables. My first thoughts included using str_replace() to strip out such content, but then one ends...
17
by: =?Utf-8?B?U2hhcm9u?= | last post by:
Hi Gurus, I need to transfer a jagged array of byte by reference to unmanaged function, The unmanaged code should changed the values of the array, and when the unmanaged function returns I need...
1
by: CloudSolutions | last post by:
Introduction: For many beginners and individual users, requiring a credit card and email registration may pose a barrier when starting to use cloud servers. However, some cloud server providers now...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome former...
0
by: ryjfgjl | last post by:
In our work, we often need to import Excel data into databases (such as MySQL, SQL Server, Oracle) for data analysis and processing. Usually, we use database tools like Navicat or the Excel import...
0
by: taylorcarr | last post by:
A Canon printer is a smart device known for being advanced, efficient, and reliable. It is designed for home, office, and hybrid workspace use and can also be used for a variety of purposes. However,...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: aa123db | last post by:
Variable and constants Use var or let for variables and const fror constants. Var foo ='bar'; Let foo ='bar';const baz ='bar'; Functions function $name$ ($parameters$) { } ...
0
by: ryjfgjl | last post by:
If we have dozens or hundreds of excel to import into the database, if we use the excel import function provided by database editors such as navicat, it will be extremely tedious and time-consuming...
0
by: ryjfgjl | last post by:
In our work, we often receive Excel tables with data in the same format. If we want to analyze these data, it can be difficult to analyze them because the data is spread across multiple Excel files...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.