This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of C++17 status.

### 2380. May `<cstdlib>` provide `long ::abs(long)` and `long long ::abs(long long)`?

Section: 16.4.2.3 [headers] Status: C++17 Submitter: Richard Smith Opened: 2014-03-31 Last modified: 2017-07-30

Priority: 2

View all other issues in [headers].

View all issues with C++17 status.

Discussion:

99 [depr.c.headers] p3 says:

> [Example: The header `<cstdlib>` assuredly provides its declarations and definitions within the namespace `std`. It may also provide these names within the global namespace. The header `<stdlib.h>` assuredly provides the same declarations and definitions within the global namespace, much as in the C Standard. It may also provide these names within the namespace `std`. — end example]

This suggests that `<cstdlib>` may provide `::abs(long)` and `::abs(long long)`. But this seems like it might contradict the normative wording of 16.4.2.3 [headers] p4:

> Except as noted in Clauses 18 through 30 and Annex D, the contents of each header `cname` shall be the same as that of the corresponding header `name.h`, as specified in the C standard library (1.2) or the C Unicode TR, as appropriate, as if by inclusion. In the C++ standard library, however, the declarations (except for names which are defined as macros in C) are within namespace scope (3.3.6) of the namespace `std`. It is unspecified whether these names are first declared within the global namespace scope and are then injected into namespace `std` by explicit using-declarations (7.3.3).

Note that this allows `<cstdlib>` to provide `::abs(int)`, but does not obviously allow `::abs(long)` nor `::abs(long long)`, since they are not part of the header `stdlib.h` as specified in the C standard library.

28.7 [c.math] p7 adds signatures `std::abs(long)` and `std::abs(long long)`, but not in a way that seems to allow `::abs(long)` and `::abs(long long)` to be provided.

I think the right approach here would be to allow `<cstdlib>` to either provide no `::abs` declaration, or to provide all three declarations from namespace `std`, but it should not be permitted to provide only `int abs(int)`. Suggestion:

Change in 16.4.2.3 [headers] p4:

> […]. It is unspecified whether these names (including any overloads added in Clauses 18 through 30 and Annex D) are first declared within the global namespace scope and are then injected into namespace `std` by explicit using-declarations (7.3.3).

[2015-05, Lenexa]

MC: do we need to defer this?
PJP: just need to get my mind around it, already playing dirty games here, my reaction is just do it as it will help C++
STL: this is safe
TP: would be surprising if using abs didn't bring in all of the overloads
MC: that's Richard's argument
MC: move to ready

Proposed resolution:

This wording is relative to N3936.

1. Modify 16.4.2.3 [headers] p4 as indicated:

   > Except as noted in Clauses 18 through 30 and Annex D, the contents of each header `cname` shall be the same as that of the corresponding header `name.h`, as specified in the C standard library (1.2) or the C Unicode TR, as appropriate, as if by inclusion. In the C++ standard library, however, the declarations (except for names which are defined as macros in C) are within namespace scope (3.3.6) of the namespace `std`. It is unspecified whether these names (including any overloads added in Clauses 18 through 30 and Annex D) are first declared within the global namespace scope and are then injected into namespace `std` by explicit using-declarations (7.3.3).