[Bug libstdc++/61761] [C++11] std::proj returns incorrect values
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61761 --- Comment #5 from Jan van Dijk --- Does the usage of numeric_limits<_Tp> in complex work well for user-defined _Tp? For complex, at present MyType can be required to be constructible from INFINITY to make proj work. Wouldn't using numeric_limits<_Tp> dictate a (forbidden) numeric_limits specialization to provide numeric_limits::infinity()?
[Bug libstdc++/61761] [C++11] std::proj returns incorrect values
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61761 Jan van Dijk changed: What|Removed |Added CC||j.v.dijk at tue dot nl --- Comment #2 from Jan van Dijk --- Is it not perfectly fine that your patch works only for _Tp equal to float, double or long double? Anything else is unspecified per 24.5(2). Does libstdc++ advertise to go beyond the standard and support other scalar types as well? (And if so: is that policy documented anywhere?) That said, I think that the correct patch would be: Index: libstdc++-v3/include/std/complex === --- libstdc++-v3/include/std/complex(revision 270684) +++ libstdc++-v3/include/std/complex(working copy) @@ -1902,11 +1902,9 @@ std::complex<_Tp> __complex_proj(const std::complex<_Tp>& __z) { - const _Tp __den = (__z.real() * __z.real() -+ __z.imag() * __z.imag() + _Tp(1.0)); - - return std::complex<_Tp>((_Tp(2.0) * __z.real()) / __den, - (_Tp(2.0) * __z.imag()) / __den); + if (isinf(__z.real()) || isinf(__z.imag())) +return std::complex<_Tp>(INFINITY, copysign(0.0, __z.imag())); + return __z; } #if _GLIBCXX_USE_C99_COMPLEX Note that the combinations finite,nan and nan,finite should return __z unmodified. As the OP mentions, this was a problem in glibc as well that was later fixed, see: https://sourceware.org/ml/libc-alpha/2013-08/msg00374.html The patch above makes libstdc++ do exactly what is also found in current glibc's implementation in s_cproj_template.c
[Bug libstdc++/87982] No error for std::generate_n(ptr, ptr, f)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87982 --- Comment #10 from Jan van Dijk --- Thanks a lot. And sorry for being pedantic, but I believe that the documentation of the return value of generate_n is still wrong for negative __n (see the first part of comment #5).
[Bug libstdc++/87982] No error for std::generate_n(ptr, ptr, f)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87982 --- Comment #5 from Jan van Dijk --- Thanks a lot for this change. One more nit: the standard clause 28.6.7(2) allows (== does not forbid) negative count arguments, in which case generate_n is a no-op returning __first, but this is not reflected by the libstdc++ documentation of the return value, which claims __first+__n unconditionally. Somewhat off-topic: IMHO the standard is not explicit about the fact that gen() is (of course) to be invoked separately for every element in the range: "The generate_n algorithms invoke the function object gen and assign the return value of gen through all the iterators in the range...". But that may be me not being a native English speaker. The libstdc++ docs are more helpful for sure. And indeed, sorry for not being sufficiently precise: the standard does not say to *which* integral type the conversion must be possible so that type could be used internally, or better: simply used in the interface. Having the _Size template argument allows, in principle, the loop to be written without the conversion being actually done, but that would be such a pico-optimization that I still do not understand why the standard did not just fix the count type to (e.g.) std::ptrdiff_t --- but also that is outside the scope of this issue.
[Bug libstdc++/87982] No error for std::generate_n(ptr, ptr, f)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87982 Jan van Dijk changed: What|Removed |Added CC||j.v.dijk at tue dot nl --- Comment #3 from Jan van Dijk --- Isn't the real problem that the standard does not specify any requirements about the type of the count argument (or a precondition on its value)? Should that be a built-in integral type? Then the issue is solved by doing a static_assert> to the implementation. One could also argue that the counter merely be convertible to a std::size_t, and the question (to WG21) is why then the count type is a template argument in the first place. (One could also argue that it should be a std::ptrdiff_t, since the algorithm really operates on a range [ptr,ptr+count] --- that would also allow an assert(count>=0) in the implementation.) If the intention is really that also user-defined types are supported, the requirements on such types should be spelled out (by WG21). As an example, the code below uses a custom counter object that can can be converted to (=> and compared with) an integer value. Reasonable enough. However, it does not compile because of what really seems to be an undocumented implementation detail in stl_algo.h: the usage of decltype(__n + 0) to compute a counter type for internal usage. Is the code below valid or not? It is remarkable how much Sunday morning can be spent on such an innocuous issue :-) cat 87892_2.cpp #include struct counter { counter(unsigned n); operator unsigned() const; counter& operator--(); private: template counter operator+(T v) const; }; void foo() { int a[2]; std::generate_n(a, counter(2), []{ return 0;}); } g++ -c 87892_2.cpp In file included from /home/jan/local/gcc-head/include/c++/9.0.1/algorithm:62, from 87892_2.cpp:1: /home/jan/local/gcc-head/include/c++/9.0.1/bits/stl_algo.h: In instantiation of ‘_OIter std::generate_n(_OIter, _Size, _Generator) [with _OIter = int*; _Size = counter; _Generator = foo()::]’: 87892_2.cpp:15:48: required from here /home/jan/local/gcc-head/include/c++/9.0.1/bits/stl_algo.h:4448:27: error: ‘counter counter::operator+(T) const [with T = int]’ is private within this context 4448 | for (__decltype(__n + 0) __niter = __n; | ^~~ 87892_2.cpp:9:29: note: declared private here 9 | template counter operator+(T v) const; |
[Bug libstdc++/11196] _GNU_SOURCE vs. M_PI
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=11196 Jan van Dijk changed: What|Removed |Added CC||j.v.dijk at tue dot nl --- Comment #10 from Jan van Dijk --- Has this been (partly) fixed in the meantime? The OP's test program compiles just fine with: g++ (SUSE Linux) 4.8.3 20140627 [gcc-4_8-branch revision 212064] g++ (SUSE Linux) 5.3.1 20160412 [gcc-5-branch revision 234894] g++ (GCC) 7.0.0 20160516 (experimental) x86_64-w64-mingw32.shared-g++ (GCC) 4.9.3 I also see that GNU_SOURCE is no longer implicitly defined. At least, I do not see that in the output of "g++ -dM -E - < /dev/null" anymore. Are there any remaining issues, or should this report be closed?
[Bug c++/16106] Poor error message
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=16106 Jan van Dijk changed: What|Removed |Added CC||j.v.dijk at tue dot nl --- Comment #2 from Jan van Dijk --- It appears this has been fixed long time ago already: both g++ (SUSE Linux) 4.8.3 20140627 [gcc-4_8-branch revision 212064] g++ (GCC) 7.0.0 20160504 (experimental) print the desired error message: 16106.cpp: In constructor ‘A::A(T&) [with T = int]’: 16106.cpp:8:12: error: invalid initialization of non-const reference of type ‘int&’ from an rvalue of type ‘int’ A a; ^ 16106.cpp: In function ‘int main()’: 16106.cpp:8:12: error: invalid initialization of non-const reference of type ‘int&’ from an rvalue of type ‘int’ 16106.cpp:3:9: note: in passing argument 1 of ‘A::A(T&) [with T = int]’ A(T& t = T()) : tt(t) {}
[Bug c++/70933] New: [7.0 regression] ICE with -Wall on valid code in inchash::add_expr
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70933 Bug ID: 70933 Summary: [7.0 regression] ICE with -Wall on valid code in inchash::add_expr Product: gcc Version: 7.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ Assignee: unassigned at gcc dot gnu.org Reporter: j.v.dijk at tue dot nl Target Milestone: --- The reduced testcase at the end of this report makes rev. 235846 of the compiler ice with -Wall. Maybe related to PR70906. > g++ -c -Wall declarations.cpp declarations.cpp: In instantiation of ‘void test_declarations() [with T = unsigned int]’: declarations.cpp:22:30: required from here declarations.cpp:17:5: internal compiler error: in add_expr, at tree.c:7928 T& param = evaluator.declare_parameter("p1")=T(4); ^ 0x1020896 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7928 0x10202f2 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0x101ff75 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0x101ff75 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0x10202f2 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0x101ff75 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0x10202f2 inchash::add_expr(tree_node const*, inchash::hash&, unsigned int) ../../gcc-head/gcc/tree.c:7997 0xa9bf68 operand_equal_p(tree_node const*, tree_node const*, unsigned int) ../../gcc-head/gcc/fold-const.c:2761 0x8ae46a candidate_equal_p ../../gcc-head/gcc/c-family/c-common.c:2926 0x8ae4fb candidate_equal_p ../../gcc-head/gcc/c-family/c-common.c:2926 0x8ae4fb merge_tlist ../../gcc-head/gcc/c-family/c-common.c:2831 0x8b2725 verify_tree ../../gcc-head/gcc/c-family/c-common.c:3135 0x8b66aa verify_sequence_points(tree_node*) ../../gcc-head/gcc/c-family/c-common.c:3159 0x7fa287 finish_expr_stmt(tree_node*) ../../gcc-head/gcc/cp/semantics.c:682 0x699f0d initialize_local_var ../../gcc-head/gcc/cp/decl.c:6428 0x699f0d cp_finish_decl(tree_node*, tree_node*, bool, tree_node*, int) ../../gcc-head/gcc/cp/decl.c:6977 0x6cc84f tsubst_expr(tree_node*, tree_node*, int, tree_node*, bool) ../../gcc-head/gcc/cp/pt.c:15216 0x6c8f24 tsubst_expr(tree_node*, tree_node*, int, tree_node*, bool) ../../gcc-head/gcc/cp/pt.c:15105 0x6c9d27 tsubst_expr(tree_node*, tree_node*, int, tree_node*, bool) ../../gcc-head/gcc/cp/pt.c:15290 0x6c697d instantiate_decl(tree_node*, int, bool) ../../gcc-head/gcc/cp/pt.c:22019 jan@linux-pwd6:~/src/gum-cvs/plmathparser/testsuite> cat declarations.cpp struct string { string(const char*); }; template struct expression_evaluator { typedef T result_type; result_type& declare_parameter(const string& name); }; template void test_declarations() { expression_evaluator evaluator; T& param = evaluator.declare_parameter("p1")=T(4); } void foo() { test_declarations(); }
[Bug libstdc++/67375] abi::__cxa_demangle crashes demangling a lambda
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67375 Jan van Dijk changed: What|Removed |Added CC||j.v.dijk at tue dot nl --- Comment #1 from Jan van Dijk --- Has this been fixed in the meantime? I tried to reproduce this on an x86_64 box (OpenSuSE Tumbleweed) with both g++ (SUSE Linux) 5.3.1 20160301 [gcc-5-branch revision 233849] g++ (GCC) 7.0.0 20160502 (experimental) Compilation with default options and running the test code does not dump core. Output: void c::DD::(c::FF&)::{lambda()#1}*& std::_AAA_::_M_bb(void c::DD::(c::FF&)::{lambda()#1}*&)::{lambda()#1}*>()
[Bug middle-end/48323] [4.5/4.6/4.7 Regression] Lifetime of local variables: global versus member function
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=48323 --- Comment #4 from Jan van Dijk 2011-03-28 22:17:15 UTC --- (In reply to comment #3) Sorry for being pedantic, but would you care to explain how your observation renders this report invalid? I am afraid I do not understand this resolution. Do you assert that the two cases (static local in global vs. class scope function) are deliberately treated differently? If so, is this an implementation choice, or is it based on a document that I should have read (which one)? If this isn't changed back, shouldn't this change at least be documented? It may break more user code, not just mine... Thanks again for your time.
[Bug c++/48323] New: Lifetime of local variables: global versus member function
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=48323 Summary: Lifetime of local variables: global versus member function Product: gcc Version: 4.5.1 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ AssignedTo: unassig...@gcc.gnu.org ReportedBy: j.v.d...@tue.nl [First presented on gcc-help. Submitted as per the suggestion of Ian Lance Taylor, see http://gcc.gnu.org/ml/gcc-help/2011-03/msg00340.html ] Consider the following shared object: // g++ -o libtest.so -shared -fPIC dltestlib.cpp #include int global_f() { static int i=0; return i; } struct C { int class_scope_f() { static int i=0; return i; } C() { global_f(); // class_scope_f(); // CULPRIT } ~C() { std::cout << "Destructor called" << std::endl; } }; static C c; Also consider the following test program, which merely loads and unloads this library using dlopen/dlclose. // g++ dltest2.cpp -ldl #include #include int main(int argc, const char* argv[]) { if (argc!=2) return -1; const char* fname = argv[1]; std::cout << "Opening: " << fname << std::endl; void* handle = dlopen( fname, RTLD_NOW | RTLD_LOCAL); std::cout << "Handle after dlopen: " << handle << std::endl; if(!handle) { std::cout << dlerror() << std::endl; } dlclose(handle); // do not load. Only check if the file is resident. handle = dlopen( fname, RTLD_NOW | RTLD_NOLOAD); std::cout << "Handle after dlclose: " << handle << std::endl; std::cout << "Exiting..." << std::endl; } Providing the abovementioned library as argument, I get the expected result: ./a.out /home/jan/src/gum-cvs/ideas/jan/libtest.so Opening: /home/jan/src/gum-cvs/ideas/jan/libtest.so Handle after dlopen: 0x602050 Destructor called Handle after dlclose: 0 Exiting... In particular, the library *is* unloaded by dlclose (so the global destructor of object c in the library is called before the program is exiting.) And now for the problem... If I comment in line 11 of the library module (marked CULPRIT), thus calling class_scope_f(), and try again, the result is: Opening: /home/jan/src/gum-cvs/ideas/jan/libtest.so Handle after dlopen: 0x602050 Handle after dlclose: 0x602050 Exiting... Destructor called Now the library unloading fails (the handle is still !=0, and indeed the destructor of c is not called before the program terminates). I assume this is because there is a difference in lifetime between local static variables in functions in global scope vs. those of member functions. Is this the intended behaviour? (I say 'intended', not 'mandated', because I know so's are beyond the scope of ISO-C++.) If not, should I file a report? I am on OpenSuSE 11.4; that is: glibc 2.11.3, gcc 4.5.1, binutils 2.21.