-2

A very simple program testing the STL implementations between Intel compiler on linux (Intel 18.0) and visual c++ on windows (MSVC 2015).

  1. Primarily, how to make linux fatal out/ crash the same way as windows (since i have a huge codebase). Technically i was expecting a signal 11 from linux, not to throw a garbage value everytime for whatever the size of vector i tested.

  2. Can someone explain what is happening under the hood (memory allocation wise and their rules and if it is implementation/platform/compiler dependent).? Just for my understanding.

'

#include "iostream"
#include "vector"
using namespace std;
int main(int argc,char* argv[])
{   
   vector<int> v;
   //v.resize(5);  (my bad, please ignore this, i was testing and posted incorrect version)
   cout<<"Initial vector size: "<<v.size()<<endl;
   for(int i=1;i<=5;++i)
   {
       v.push_back(i);
   }
   cout<<"size of vector after: "<<v.size()<<endl;

   for(int j=5;j>=0;--j) // Notice my upper bound.
   {
      cout<< "printing " <<v[j]<<std::endl;
   }
   return 0;
}

Both had no problems compiling as one can expect. Subsequently, Windows crashed with a nice message "vector subscript out of range" while linux threw some garbage value everytime and continued.

Hashmenow
  • 3
  • 3
  • Linux is not like Windows. On the MS platform you have `-DDEBUG` and checked iterators under "Debug" builds. Linux does not really have a concept of a "Debug" build. On Linux with GCC you need `-D_GLIBCXX_DEBUG`. I don't recall if `-D_GLIBCXX_DEBUG` checks ranges. And I don't know if ICC honors it, either. – jww Jul 18 '18 at 19:33
  • 4
    I am not sure why your program crashes on Windows. Your program looks perfectly fine to me. – R Sahu Jul 18 '18 at 19:33
  • Cannot reproduce, works as expected https://ideone.com/NVnX4B – Slava Jul 18 '18 at 19:33
  • 1
    @jww but it is still a perfectly conforming program. – SergeyA Jul 18 '18 at 19:35
  • 1
    I see nothing in the posted code that would make it crash. FWIW `#include "iostream" #include "vector"` should be `#include #include ` – NathanOliver Jul 18 '18 at 19:35
  • 1
    @jww I am not sure what OP wants to achieve, but behavior is exactly as expected – Slava Jul 18 '18 at 19:36
  • @Someprogrammerdude only that nowhere OP goes out of bounds. – SergeyA Jul 18 '18 at 19:36
  • Asker means `v.resize(5);` to be `v.reserve(5);`, perhaps? – user4581301 Jul 18 '18 at 19:38
  • 2
    Either your crashing program is missing that `resize` call or does something else you don't show with your code here. Did you copy-paste the actual code that causes the crash? You did not rewrite it into the question? If you did rewrote the code for the question, it's easy to add something by mistake, and even to *fix* the problem (still by mistake). Unfortunately that can make the question quite worthless, so please copy (as text) the [Minimal, Complete, and Verifiable Example](http://stackoverflow.com/help/mcve) that causes the crash, and paste it here without any modifications. – Some programmer dude Jul 18 '18 at 19:38
  • And if you catch the crash in your debugger, where does it happen? At what index (if any)? – Some programmer dude Jul 18 '18 at 19:39
  • @RSahu I'm trying to access v[5] or the 6th element and windows crashes as it is out of bounds. – Hashmenow Jul 18 '18 at 19:42
  • 1
    Actually, in the code you show the vector have *ten* elements. That's why nobody understands what the problem is. – Some programmer dude Jul 18 '18 at 19:43
  • @Hashmenow, that does not make sense. At the time you are accessing `v[5]`, `V` has 10 elements in it. – R Sahu Jul 18 '18 at 19:43
  • My bad all, please remove the resize. I was testing and posted the wrong version. – Hashmenow Jul 18 '18 at 19:44
  • @Hashmenow You can **[edit]** ( <- click this link) your post to put the code that actually crashes – NathanOliver Jul 18 '18 at 19:47
  • @NathanOliver : thank you, commented the line, crashes now on Windows and linux printing garbage. – Hashmenow Jul 18 '18 at 19:53
  • Now that the question is fixed, Here is a close match: [Accessing an array out of bounds gives no error, why?](https://stackoverflow.com/questions/1239938/accessing-an-array-out-of-bounds-gives-no-error-why) Odds are good that a release build from MSVC will have similar behaviour to the Linux and ICC builds. This cannot be guaranteed, though. – user4581301 Jul 18 '18 at 20:06
  • @user4581301 this case is little different AFAIK, `std::vector` most probably reserves more memory that for 5 elements (I would say at least 6 :) to make it even) so even writing there may not crash the program. With array situation is different, as writing out of bounds will modify stack. – Slava Jul 18 '18 at 20:10
  • Not going to argue that, but what's probably the most important part, "The language simply says what should happen if you access the elements *within* the bounds", still applies. What happens in UB at the implementation level, is the point of the question, but it probably shouldn't be. Just for fun, I built a 2015 release build. No crash. Without the extra-friendly checks in the debug build, the out of bounds access prints garbage. – user4581301 Jul 18 '18 at 20:59
  • @user4581301 Precisely. – Hashmenow Jul 18 '18 at 21:57

1 Answers1

2

Assuming you put v.resize(5) by mistake, here are some answers:

how to make linux fatal out/ crash the same way as windows (since i have a huge codebase).

Use std::vector::at() that validates index and throws exception by design. std::vector::operator[] not suppose to validate index and even if some platform does it for some configuration (looks like Windows compiler in debug has such validation), you cannot demand it everywhere.

Technically i was expecting a signal 11 from linux, not to throw a garbage value everytime for whatever the size of vector i tested.

It is a problem of your expectation. Giving invalid index to std::vector::operator[] leads to Undefined Behaviour, and you cannot expect that to give signal 11 or something else in particular.

FYR:

std::vector::operator[]

Returns a reference to the element at specified location pos. No bounds checking is performed.

std::vector::at()

If pos is not within the range of the container, an exception of type std::out_of_range is thrown.

emphasis is mine.

As for memory allocation, it is implementation specific, most of them would not allocate memory exactly for 5 elements but more in advance, to make it efficient, so that's why your code on Linux did not crush, but produced garbage, as you read value from uninitialized memory. But that can change any moment and you should not rely on this behavior in any way.

Slava
  • 43,454
  • 1
  • 47
  • 90