Export (0) Print
Expand All

Checked Iterators

Updated: March 2012

Checked iterators ensure that the bounds of your container are not overwritten.

Checked iterators apply to release builds and debug builds. See Debug Iterator Support for more information about how to use iterators when you compile in debug mode.

For information about how to disable warnings that are generated by checked iterators, see _SCL_SECURE_NO_WARNINGS.

You can use the following symbols with the checked iterators feature.

_SECURE_SCL

If defined as 1, unsafe use of iterators causes a runtime error. If defined as 0, checked iterators are disabled. The exact behavior of the runtime error depends on the value of _SECURE_SCL_THROWS. By default, the value for _SECURE_SCL is 0 for release builds and 1 for debug builds. In other words, by default, checked iterators are enabled for debug builds only.

_SECURE_SCL_THROWS

If defined as 1, the use of an out-of-range iterator causes an exception at run time. If the iterator is defined as 0, the program is terminated by calling invalid_parameter. The default value for _SECURE_SCL_THROWS is 0; this means that the program will be terminated by default. Requires that _SECURE_SCL is also defined.

When _SECURE_SCL=1 is defined:

  • All standard iterators (vector::iterator, for example) are checked.

  • The checked form of an algorithm will be used, for standard functions that have checked forms (see the list later in this document).

  • If an output iterator is a checked iterator:

    • You will get checked behavior on calls to the standard function (std::copy, for example).

    • You will get checked behavior on calls to a checked function (stdext::checked_copy, for example).

    • You will get checked behavior on calls to an unchecked function (stdext::unchecked_copy, for example).

  • If the output iterator is an unchecked iterator (an array, for example):

    • Calls to the standard function (std::copy, for example) will cause compiler warnings.

    • Calls to the checked function (stdext::checked_copy, for example) will cause compiler warnings.

    • You will get unchecked behavior on calls to an unchecked function (stdext::unchecked_copy, for example).

  • The following functions will generate a runtime error if there is an access that is outside the bounds of the container:

When _SECURE_SCL=0 is defined:

  • All standard iterators are unchecked (iterators can move beyond the container boundaries, which leads to undefined behavior).

  • The unchecked form of a function will be used, for standard functions that have checked forms (see the list later in this document).

  • If an output iterator is a checked iterator:

    • You will get checked behavior on calls to the standard function (std::copy, for example).

    • You will get checked behavior on calls to a checked function (stdext::checked_copy, for example).

    • You will get checked behavior on calls to an unchecked function (stdext::unchecked_copy, for example).

  • If an output iterator is an unchecked iterator:

    • You will get unchecked behavior on calls to the standard function (std::copy, for example).

    • Calls to a checked function (stdext::checked_copy, for example) will cause compiler warnings.

    • You will get unchecked behavior on calls to an unchecked function (stdext::unchecked_copy, for example).

A checked iterator refers to an iterator that will throw an exception or call invalid_parameter if you attempt to move past the boundaries of the container. For more information about invalid_parameter, see Parameter Validation.

A checked algorithm enforces the use of a checked destination iterator. If it is passed an unchecked destination iterator, a checked algorithm will compile, but with warnings. See _SCL_SECURE_NO_WARNINGS for information about how to disable these warnings.

There are two iterator adaptors that support checked iterators:

The following algorithms enforce the use of a checked iterator as output iterator. This is useful when you want to compile by using _SECURE_SCL=0, and when you identify some code where you want to enforce the use of checked iterators. The following algorithms are defined in the stdext namespace.

NoteNote

The following algorithms are Microsoft extensions to the Standard C++ Library. Code that is implemented by using these algorithms is not portable.

The following algorithms enable the use of an unchecked iterator as output iterator. This is useful when you want to compile by using _SECURE_SCL=1, and when you want to selectively enable the use of unchecked iterators. The following algorithms are defined in the stdext namespace.

NoteNote

The following algorithms are Microsoft extensions to the Standard C++ Library. Code that is implemented by using these algorithms is not portable.

When you compile by using _SECURE_SCL 1, a runtime error will occur if you attempt to access an element that is outside the bounds of the container by using the indexing operator of certain classes (see earlier in this document).

// checked_iterators_1.cpp
// compile with: /EHsc
#define _SECURE_SCL 1
#define _SECURE_SCL_THROWS 1
#include <vector>
#include <iostream>
using namespace std;
int main() {
   vector<int> v;
   v.push_back(67);
   int i = v[0];
   cout << i << endl;

   try {
      i = v[1];
   }
   catch (std::out_of_range) {
      cout << "invalid container access" << endl;
   }
};
67
invalid container access

When you compile by using _SECURE_SCL 1, a runtime error will occur if you attempt to access an element by using front or back of certain classes (see earlier in this document), when the container is empty.

// checked_iterators_2.cpp
// compile with: /EHsc
#define _SECURE_SCL 1
#define _SECURE_SCL_THROWS 1

#include <vector>
#include <iostream>

int main() {
   using namespace std;   
   vector <int> v1;
   try {
      int& i = v1.front();
   }
   catch (std::out_of_range) {
      cout << "vector is empty!!" << endl;
   }
}
vector is empty!!

When you compile by using _SECURE_SCL 1, the compiler enforces the use of a checked iterator on standard algorithms that also have checked and unchecked versions (see earlier in this document).

// checked_iterators_3.cpp
// compile with: /EHsc /W3
#define _SECURE_SCL 1
#include <algorithm>
#include <iostream>
using namespace std;
using namespace stdext;
int main() {
    int a[] = { 1, 2, 3 };
    int *b = new int[10];
    int c[10];

    copy(a, a + 3, b);   // C4996 unchecked iterator
    copy(a, a + 3, checked_array_iterator<int*>(c, _countof(c)));  // OK

    delete[] b;
}

The following example sets _SECURE_SCL to 0, and thereby disables checked iterators. With checked iterators disabled, you must take extra caution to ensure that you do not iterate beyond the bounds of your container.

// checked_iterators_4.cpp
// compile with: /EHsc
#define _SECURE_SCL 0
#include <vector>
#include <iostream>
using namespace std;
int main() {
   vector<int> v;
   v.push_back(67);
   int i = v[0];
   cout << i << endl;
};
67

Date

History

Reason

March 2012

Added value description enhancement for _SECURE_SCL.

Content bug fix.

Community Additions

ADD
Show:
© 2014 Microsoft