On Sat, Aug 3, 2019 at 4:30 PM Sam Varshavchik <mrsam@xxxxxxxxxxxxxxx> wrote: > > Tom Hughes writes: > > > But I think upstream is giving very bad advice... > > > > That define does not "add extra crashes" in the way that they > > seem to think - well I mean it does literally but those crashes > > are reports of program errors on their part. > > > > Specifically in this case they appear to be accessing a > > std::vector at an index beyond the end, so they are accessing > > memory that may not be allocated at all, and if it is does > > not belong to the vector in question. So the program is quite > > likely to crash there one day anyway, the extra assertion just > > makes sure it always does. > > I believe that the following construct trips this assertion: > > # std::vector<int> foo; > # > # std::vector<int> bar; > # > # // Populate foo with something. > # > # std::copy(&foo[0], &foo[foo.size()], std::back_insert_iterator{bar}); > > There's nothing wrong with this. There is no out of bounds access. You just formed a reference past the end of an array. I doubt that is valid according to the standard. It certainly fails the smell test. I *think* the standard defines &foo[foo.size] as being equivalent to &*(foo.begin() + foo.size()), which certainly appears to be invalid. On a cursory search of the standard, I couldn't find where it says what operator* on this type of iterator does at all, let alone whether it's valid for one-past-the-end iterators, but I'm pretty sure that your code is, indeed, wrong. > I do not > believe that this is undefined behavior. The defined semantics of > std::vector, and its operator[], are well defined here. > > I ran into these new assertions with my own code as well, after updating to > F28 (where they were enabled by default the first time, IIRC, not sure why > this shows up only now, for that package). > > I ended up tweaking my code to avoid the assertions, rather than disabling > them. For this particular situation, my original change was to try > > std::copy(&foo[0], &foo[0]+foo.size(), std::back_insert_iterator{bar}); > What you want is foo.begin() and foo.end() or, if you really want to play with pointers, foo.data(). _______________________________________________ devel mailing list -- devel@xxxxxxxxxxxxxxxxxxxxxxx To unsubscribe send an email to devel-leave@xxxxxxxxxxxxxxxxxxxxxxx Fedora Code of Conduct: https://docs.fedoraproject.org/en-US/project/code-of-conduct/ List Guidelines: https://fedoraproject.org/wiki/Mailing_list_guidelines List Archives: https://lists.fedoraproject.org/archives/list/devel@xxxxxxxxxxxxxxxxxxxxxxx