Acces the 11th element of a 10 element array 
Author Message
 Acces the 11th element of a 10 element array

Ok!! I know I will receive lot's of flame for that one so I try to cool down

Like any C programmer it happens that I declare for example an array of
10 elements and write to the 11th one : one of the best results is to make
those bugs very difficult to detect. Even worse : when writing to the 11th
element it sometimes happens that it corrupts the variable that sits quietly
behind in memory! I know that in Pascal for example you've got a mechanism
to prevent you writing further than what you declared, why is in not
implemented in C ?

1) Because the way "int x[10];" works only records the address of x but not
it's size ? (but if yes how is the variable cleared from the stack?)

2) Because the first one who implemented a C compiler never thought about it
and now it's too late (the famous "historical reason") ?

3) Because it is helpfull for ... <insert here your reason why you find that
it may help you>

Personnally I cant think of any reason why
int x[10];
x[10]=255;
should not produce a run-time error message (of course that simple example
can be detected by lint but try to do that with variables...)

--
-----------------------------------------------------------------------------

"The sysop has dropped to dos, please wait..." : ms/dos BBS
-----------------------------------------------------------------------------



Mon, 04 Apr 1994 02:11:18 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Ok!! I know I will receive lot's of flame for that one so I try to cool down
>Like any C programmer it happens that I declare for example an array of
>10 elements and write to the 11th one : one of the best results is to make
>those bugs very difficult to detect. Even worse : when writing to the 11th
>element it sometimes happens that it corrupts the variable that sits quietly
>behind in memory! I know that in pascal for example you've got a mechanism
>to prevent you writing further than what you declared, why is in not
>implemented in C ?
>1) Because the way "int x[10];" works only records the address of x but not
>it's size ? (but if yes how is the variable cleared from the stack?)
>2) Because the first one who implemented a C compiler never thought about it
>and now it's too late (the famous "historical reason") ?
>3) Because it is helpfull for ... <insert here your reason why you find that
>it may help you>
>Personnally I cant think of any reason why
>int x[10];
>x[10]=255;
>should not produce a run-time error message (of course that simple example
>can be detected by lint but try to do that with variables...)

        Here are 2 very good reasons why C does not have array-limit checking:

        1) The addition of such code would make the language much bigger and
           slower

        2) C is based on the principle that the programmer knows what he is
           doing, so let him do it and don't get in his way.

---
John Gordon




Mon, 04 Apr 1994 08:01:36 GMT  
 Acces the 11th element of a 10 element array

Quote:
>behind in memory! I know that in pascal for example you've got a mechanism
>to prevent you writing further than what you declared, why is in not
>implemented in C ?
>Personnally I cant think of any reason why
>int x[10];
>x[10]=255;
>should not produce a run-time error message (of course that simple example
>can be detected by lint but try to do that with variables...)

How about the following code?

main()
{
  int arsmall[50];
  int arbig[500];

  sub(&arsmall[25]);   /* or sub(ar+25) */
  sub(arbig+45);
  sub(arsmall+50);

Quote:
}

void sub(int *x)
{
  x[-5]=0;
  x[10]=5;
  x[0]=7;

Quote:
}

Which will give the following changes in memory (illegal ones marked
with *):
arsmall[20]=0, arsmall[35]=5, arsmall[25]=7,
arbig[40]=0, arbig[55]=5, arbig[45]=7,
arsmall[44]=0, arsmall[60]=5*, arsmall[50]=7*.

So: IF you want array bounds checking, you not only have to know the
size of the array in the scope of the array itself, but you would also
have to pass the size around to functions that use array. actually not just
the size, but both the lower and upper border!
Als notice that passing the address of just one element beyond the
array (as in sub(arsmall+50), NO harm is done until you actually
reference beyond the array, i.e. arsmall[50-5] is OK, but arsmall[60]
and arsmall[50] are NOT.

Passing not only the address of the array, but also the borders would give
a runtime penalty. Also, what would you do if de function sub looks like
this:

void sub2(int *x)
{
  *x=5;

Quote:
}

in this case, when an array is passed to sub2, you would pass both
address and size, but what do you pass in case of:
int y;
sub2(&y);

OK, so you pass 1) the address of y, 2) the lower border (0) and 3) the
upper border (0). In stead of passing 1 parameter (the ptr), you pass 3!
And that for EVERY pointer parameter. Now that is a performance penalty.

Have you also thought about the implications when I use malloc'ed
dataspace?  

Conclusion:
Strictly spoken, it IS probably possible to do bounds checking, but then you
suffer a performance penalty, and ALL your code (including libraries)
would have to have the same compilation option (checkin on/off), because
otherwise functions like strcat would not know what to do with all these
param's)
--
___  __  ____________________________________________________________________


__/ \__/ ____________________________________________________________________



Mon, 04 Apr 1994 17:20:44 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Like any C programmer it happens that I declare for example an array of
>10 elements and write to the 11th one ...

One of the reasons I (am I suppose most people) use C is because it's fast.
If every time you reference an array, you want the run-time code to check
you aren't going past the end of the array, C will be slow *8+(

I expect Lint already checks for explicit addressing problems like
char a[10];
a[11] = 'h';

but if the 11 is the contents of a variable then it wouldn't be able to would
it?  If you don't trust your programming why not use Modula-2 or some program
that protects you at the expense of speed?

--
William O. Smith -- Warwick Univ, UK  | Life is a short warm moment,

                                      |  - Pink Floyd, "Free Four"



Mon, 04 Apr 1994 19:26:49 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Personnally I cant think of any reason why
>int x[10];
>x[10]=255;
>should not produce a run-time error message (of course that simple example
>can be detected by lint but try to do that with variables...)

>--
>-----------------------------------------------------------------------------

>"The sysop has dropped to dos, please wait..." : ms/dos BBS
>-----------------------------------------------------------------------------

I don't know why the C language doesn't do this, but I'm very glad that it
doesn't.  If you write a program in C that checks for out-of-bounds array
subscripts *every time* the array is accessed, you will realize how many
extra instructions are needed to implement such a check.  I am happier with
a language that lets me check for the possibility of going out of bounds at
a few appropriate times, and then gives very fast array access.

I think this desirable feature of C is one of the reasons that large array
manipulation routines written in C are faster (on a 286, DOS 3) than
comparable routines written in fortran.

If you want bulletproof array access, why not write that part in FORTRAN ?

(This response is based on my experience, and not any great theoretical
knowledge of either C or FORTRAN.  Please feel free to question or correct
me)


Sverdrup Technology         | 2001 Aerospace Parkway
NASA LeRC Group             | Brook Park, OH 44142
"Opinions are Mine, Only"   | (216) 826-6770



Mon, 04 Apr 1994 21:57:00 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Personnally I cant think of any reason why
>int x[10];
>x[10]=255;
>should not produce a run-time error message (of course that simple example
>can be detected by lint but try to do that with variables...)

You have sort of answered your own question.  You can't detect these errors
at run time because that would involve run-time detection.  Expensive if
you code properly.  Of course you can detect this stuff yourself:

#define BUFLEN 10
int x[BUFLEN], y;
...
if (y >= BUFLEN)
  [error code here]
else
  x[y] = 255;

But if you already know that y is in the correct range then the above test
becomes redundant and wasteful.  If your coding practices make this sort
of automatic checking necessary then C may not be the right language for
you.  Personally I prefer the power and speed over the hand holding.

--

D'Arcy Cain Consulting             |   There's no government
Toronto, Ontario, Canada           |   like no government!
+1 416 424 2871          DoD#0082  |



Mon, 04 Apr 1994 20:52:56 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Like any C programmer

Bzzzt!  5 yard penalty.

Quote:
>it happens that I declare for example an array of
>10 elements and write to the 11th one : ...
>I know that in pascal for example you've got a mechanism
>to prevent you writing further than what you declared, why is in not
>implemented in C ?

Because C is a language for {*filter*}s, and PASCAL is a language for children.

"I pushed my computer through a bandsaw while it was running and it caught
fire!  This is inexcusable!"

The C compiler's job is to produce fast binary code that implements what
the C code says.  Your job is to produce correct C code.

However, if you insist upon using C without {*filter*} supervision, there are at
least two C systems (Sabre C and "Safe C"), which implement that kind of
runtime checking, and lots more besides.

Just remember that a "nice" error message is not an excuse for a production
system failure: "line 666: illegal array offset" is no more comforting to
a user who has just lost hours of work than "bus error: core dumped".



Mon, 04 Apr 1994 23:06:57 GMT  
 Acces the 11th element of a 10 element array

pg> [why no array bounds check].

Primarily speed, a test added to every array access could actually be
quite a hit in the middle of a bottleneck loop (especially on a
processor which can pipeline things better if there are no conditional
branches in a segment of code).

That is why the test is not specified in the definition of the
language. As to why compilers don't give you the option of having the
tests, I presume no one has shouted at the vendors loud enough.

I would presume that ANSI says that writing beyond the end of an array
gives `implementation defined' behaviour, but that sort of presumption
is dangerous and I don't have the standard.

--

                                         |<



Mon, 04 Apr 1994 14:49:08 GMT  
 Acces the 11th element of a 10 element array

Quote:
>    Here are 2 very good reasons why C does not have array-limit checking:

OK, so how come Saber-C *does*, as far as I know, have array-limit
checking?  Does that mean that it's not C?  I suspect C on the AS/400
may have array-limit checking as well....

Quote:
>    1) The addition of such code would make the language much bigger and
>       slower

No, it makes the *compiled code* bigger and slower.  Don't confuse
language with implementation.

Quote:
>    2) C is based on the principle that the programmer knows what he is
>       doing, so let him do it and don't get in his way.

Too bad programmers *don't* always know what they're doing; I suspect
most of us can testify to cases where additional checking in C would
have made life better (cf. the testimonials in the Saber-C ads).


Tue, 05 Apr 1994 00:54:23 GMT  
 Acces the 11th element of a 10 element array

Quote:
>> I know that in pascal for example you've got a mechanism
>> to prevent you writing further than what you declared, why is in not
>> implemented in C ?

> Because C is a language for {*filter*}s, and PASCAL is a language for children.
> "I pushed my computer through a bandsaw while it was running and it caught
> fire!  This is inexcusable!"
> The C compiler's job is to produce fast binary code that implements what
> the C code says.  Your job is to produce correct C code.
> However, if you insist upon using C without {*filter*} supervision, there are at

      (...stuff deleted...)

Oh, come on.  Macho posturing doesn't add anything to the discussion.  You
mean you never write buggy code?  Or that debugging aids are crutches for
the weak?  The issue is one of practicality and efficiency, not desirability.
If bounds checking could be implemented at no cost, every C compiler
would do it, and most C programmers (except you, perhaps) would find it
useful.



Tue, 05 Apr 1994 04:25:42 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Ok!! I know I will receive lot's of flame for that one so I try to cool down
>Like any C programmer it happens that I declare for example an array of
>10 elements and write to the 11th one : one of the best results is to make
>those bugs very difficult to detect. Even worse : when writing to the 11th
>element it sometimes happens that it corrupts the variable that sits quietly
>behind in memory! I know that in pascal for example you've got a mechanism
>to prevent you writing further than what you declared, why is in not
>implemented in C ?

Well nobody has replied as I would have so...

Quote:
>3) Because it is helpfull for ... <insert here your reason why you find that
>it may help you>

Because it allows you to do something you would not be able to do.  You can
manually check some or all array accesses through explicit code, macros,
or C++ classes on top of the basic arrays C gives you.  You cannot as
easily implement such basic access on top of the child-proof version.

Some pascals let you turn off the bounds checking for versions to be
released, but not all.

BTW, someone else referred to Saber-C as for those who want to code
without {*filter*} supervision.  That's backwards -- Saber is {*filter*} supervision.


Your eyes are weary from staring at the CRT for so long.  You feel sleepy.
Notice how restful it is to watch the cursor blink.  Close your eyes.  The
opinions stated above are yours.  You can't imagine why you ever felt otherwise
i=3;do{putchar(((0x18|1<<!(i&2)|(!!i==i)*2)<<2|2>>i%2)^(2<<1+i));}while(i--);



Tue, 05 Apr 1994 05:23:47 GMT  
 Acces the 11th element of a 10 element array

Quote:

>Even worse : when writing to the 11th
>element it sometimes happens that it corrupts the variable that sits quietly
>behind in memory! I know that in pascal for example you've got a mechanism
>to prevent you writing further than what you declared, why is in not
>implemented in C ?

I have been using C for two reasons:

    1.  I often have need for a quasi-high-level, machine-independent,
        assembly language.  For these uses, I need the compactness
        of compiled code, and freedom, (and the attendant responsibility
        to pay attention to what I'm doing) of assembler, but it's nice
        to have the constructs of a high-level language.

        Ex.:  I once had two identical in-house-made boards to control.  I
        created a typedef that mirrored the construction of the boards,
        with unsigned chars, and unsigned shorts, and a couple of longs,
        then declared a pointer to that type, and pointed it at one or
        the other of the boards (instead of allocating storage), and
        proceeded to access the registers by assigning to or from the
        elements of the typedef'ed structure.

        If 'C' were converted into a TRUE high-level language, the world
        would lose its major high-level-assembly language, and gain one
        more true high-level language to join the other dozens already
        existing.  This would be more of a loss to me than a gain to the
        high-level people.

    2.  There are other programs that I could write in Pascal, if there
        weren't a couple of "design features" in Pascal that tend to
        cause excessive indentation, especially in hardware-control
        routines.   (I understand Pascal may also have a problem with
        dynamically allocating strings? but I don't remember)

        To solve this, either a "Pascal II" or a "High-C" (my apologies to
        the canned juice people) could be created that was like Pascal except
        with:

        a.  continue and break
        b.  return allowed more than one place per procedure

        This is because a common control sequence in the C code I've seen is:

           if(result = do_something(a,b,c))
           {
               log_error("my_routine: %s\n",error_explanation[result]);
               return result;
           }
           if(result = do_another_thing(d,e))
           {
           .
           .
           .
        where "normal" flow is to continue to the end of the procedure, but
        any of many errors could prevent the routine from continuing. (Which
        is why 0 is a common "good" return -- one good, many kinds of bad.)

        This leads to too much indenting if done in Pascal, IMO.

I haven't looked at Pascal in years, so if I am out of date or wrong,
correct me, but it seems to me that if C is being used where other
high-level languages should have been useful, maybe a hybrid should
be developed.  Let's just don't destroy C because other languages could
use improvement.


We must worship Universal Consciousness as each of the 5 genders in turn
if we wish to be fully open to Yr glory.
                                                -- St. Xyphlb of Alpha III



Tue, 05 Apr 1994 08:30:30 GMT  
 Acces the 11th element of a 10 element array
If you tend to have off-by-one bounds errors, try using assert() in
<assert.h>. That kind of thing is what it's there for. It allows you
to toggle on and off assertion checking using the cpp variabe NDEBUG.

                                        mi

PS - I always thought that bounds and pointer checking should be a pragma
that can be shut off for the release version. Anybody know a compiler
that'll do that for me?



Tue, 05 Apr 1994 01:09:42 GMT  
 Acces the 11th element of a 10 element array

Quote:

>OK, so how come Saber-C *does*, as far as I know, have array-limit
>checking?  Does that mean that it's not C?  I suspect C on the AS/400
>may have array-limit checking as well....

    Right - it's not a C compiler when it does bounds checking - it's
running as an interpreter (or so I'm led to believe).

Quote:
>>        2) C is based on the principle that the programmer knows what he is
>>           doing, so let him do it and don't get in his way.

>Too bad programmers *don't* always know what they're doing; I suspect
>most of us can testify to cases where additional checking in C would
>have made life better (cf. the testimonials in the Saber-C ads).

    It's a great debugging tool.  (Which tools, strangely enough, often
lead to very sloppy coding practices).

--
 _

3D systems, inc.            26081 Avenue Hall    Valencia, CA 91355
VOICE (805) 295-5600 x430   FAX (805) 257-1200

                96.37% of all statistics are made up.



Tue, 05 Apr 1994 04:32:18 GMT  
 Acces the 11th element of a 10 element array
|>   Here are 2 very good reasons why C does not have array-limit checking:
|
|OK, so how come Saber-C *does*, as far as I know, have array-limit
|checking?  Does that mean that it's not C?  I suspect C on the AS/400
|may have array-limit checking as well....
|
No, no, no, Saber-C is a full blown development environment. It's a mixture
of a compiler, an interpreter, a linker and a de{*filter*} (and much more.)
The way I understand it is implemented is: every byte of memory is tagged with
a few bits, indicating a `used before set' flag, an `owned by the process flag'
and maybe some others. So, the interpreter can always check if a memory reference
is legal or not, including bound checking. I really like the product.

[ ... ]

|Too bad programmers *don't* always know what they're doing; I suspect
|most of us can testify to cases where additional checking in C would
|have made life better (cf. the testimonials in the Saber-C ads).

Yep, I agree, and even worse, even if you know what you're doing, your fingers
might get stuck on the keyboard sometimes and start typing other things, things
you didn't intend to type ;-)




Tue, 05 Apr 1994 17:08:13 GMT  
 
 [ 25 post ]  Go to page: [1] [2]

 Relevant Pages 

1. checkout compilers (Was: Acces the 11th element of a 10 element array)

2. examine first 10 array elements from gdb

3. making pointers to structure elements using array elements

4. priority_queue: order of elements with equal priority is not preserved when popping elements

5. pointers to an array and accesing elements of the array

6. Acces The 11th Eleme

7. Adding new elements to array class instance?

8. Compiler error: invalid type for __gc array element

9. Array of zero elements

10. Initializing array elements in ctor-initial

11. reference array's first element?

12. Array elements as formal parameters?

 

 
Powered by phpBB® Forum Software