Is Segmentation Fault Actual Undefined Behavior When We Refer to a Non-Static Data-Member

Is segmentation fault actual undefined behavior when we refer to a non-static data-member

Undefined behavior means that anything can happen with a standard conforming implementation. Really anything. (and your point 2 is UB)

An implementation could

  • explode your computer and harm you physically
  • make a black-hole which swallows the entire solar system
  • do nothing serious
  • light some LED on your keyboard
  • make some time-travel and kill all your grandparents before the birth of your own parents
  • etc....

and be conforming (in the event of UB); read also about the more familiar idea of nasal demons.

So what happens on UB is not predictable and is not reproducible (in general).

More seriously, think a bit about what UB could mean in the computer connected to the ABS brakes of your car, or in some artificial heart, or driving some nuclear power plant.

In particular, it might work sometimes. Since most OSes have ASLR your code has a tiny chance to work (e.g. if 0xa31a3442 happens to point to some valid location, e.g. on the stack, but you won't reproduce that on the next run!)

UB is a way to give freedom to implementors (e.g. of compilers or of OSes) and to computers to do whatever they "want", in other words to not care about consequences. This enables e.g. clever optimizations or nice implementation tricks. But you should care (and consequences are different if you are coding the embedded flight control system of a airplane, or just some hacky demo lighting LEDs with a RasberryPi, or a simple example for some C++ course running on Linux).

Recall that languages standards don't even require any computer (or any hardware) in the implementation: you might "run" your C++ code with a team of human slaves, but that would be highly unethical (and costly, and unreliable).

See also here for more references. You should at least read Lattner's blog on Undefined Behavior (most of what he wrote for C applies to C++ and many other languages having UB).


(added in december 2015 & june 2016)

NB. The valgrind tool and various -fsanitize= debugging options for recent GCC or Clang/LLVM are quite useful. Also, enable all warnings and debug info in your compiler (e.g. g++ -Wall -Wextra -g), and use appropriate instrumentation options such as -fsanitize=undefined. Be aware that it is impossible to detect statically and exhaustively at compile time all cases of UB (that would be equivalent to the Halting Problem).

PS. The above answer is not specific to C++; it also fits for C!

Why does the code work fine when I compile and run it even though I have not mentioned size of array?

What you get is Undefined Behavior.

Reading / Writing to unallocated memory does not automatically generate segmentation fault(s), but it is of course "bad practice" and should be avoided.

It's impossible to tell exactly what will happen with such code, where that array will be addressed or what is already there and hence - Undefined Behavior.

Note: As mentioned by @juanchopanza, the code as it is is illegal in C++ because arr is an incomplete type. Your compiler might (and obviously does) ignore this due to default settings, but a legal code that would demonstrate the same behavior is either:

class array {
public:
int *arr;
// ...

or

class array {
public:
int arr[1];
// ...

Out-of-bounds writing does not always cause an error [duplicate]

If you are asking WHY, there are all kinds of reasons why something like this might work. They depend upon the implementation.

Your malloc function might allocate memory behind the scenes in fixed sizes or it could allocate memory that is already rounded up to some value. Let us say for example that your malloc implementation always allocated in multiples of 8 bytes.

Then, your malloc(25) — malloc (29) calls might actually be allocating 32 bytes. So going beyond the end, might not be hurting you. When you go down to malloc (24) you might be going right off the end of the memory block.

We can only guess what what is actually happening here. The library is free to do as it wants within the bounds of the language specification.

As noted, the behavior here is completely undefined which is why you should not do this. A different library might give an entirely different result.

Unusual behaviour of strings [duplicate]

Accessing memory beyond the allocated chunk is an Undefined behavior.

for(i=0;i<5;i++)
{
b[i]=a[i]; //1. does not throw an error
}

In this loop you will end up assigning b[3]=a[3] and b[4]=a[4];

b[3] and b[4] are unallocated chunks of memory. So accessing them is an undefined behavior.

There can be unpredictable results due to undefined behavior.

According to standard:

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).

Edit:
For your doubt about segmentation fault:

Segmentation fault is a specific kind of error caused by accessing memory that “does not belong to you". But the reverse is not true i.e you can not say that you'll get a segmentation fault whenever you access an un-allocated memory.

There are systems out there that operate without memory protection, thus you cannot tell whether a piece of memory actually "belongs to you", and thus don't know whether segmentation fault will occur or not, only undefined behavior is assured.

Is placement new on a const variable with automatic storage duration legal? [duplicate]

Is the following code legal according to the standard?

The behaviour of the program is undefined:

[basic.life]

Creating a new object within the storage that a const complete object with static, thread, or automatic storage duration occupies, or within the storage that such a const object used to occupy before its lifetime ended, results in undefined behavior.

segmentation fault when trying to copy integers from .txt file

I have not checked your whole code, but here cause segmentation fault:

//determine the number of values
char *lineOne;

if(fgets(lineOne, 80, fp)!=1)
puts (lineOne);

You need to have memory for lineOne. Only a pointer does not mean you have memory for your buffer and you need to allocate it on heap or stack. Try it like this:

char lineOne[81]; // allocation on stack

or

char *lineOne = malloc(sizeof(*lineone) * 81); // allocate on heap


Related Topics



Leave a reply



Submit