https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82745
--- Comment #5 from Jonathan Wakely <redi at gcc dot gnu.org> --- (In reply to helge from comment #4) > (In reply to Jonathan Wakely from comment #2) > > Narrowing conversions only cause a diagnostic in braced-init-list, not in > > other contexts. This is how C++ has worked since day one. > > I must admit that I'm no compiler expert, nor do I have any deep knowledge > of the standard. However, I think you must be mistaken here. I assure you that "narrowing conversion" is a new term introduced by C++11, in the context of list initialization. Like C, C++ has always allowed implicit conversions that lose precision. They are only disallowed inside a braced-init-list, because C++11 introduced that that as a new form of initialization that doesn't affect historical code (well, most historical code, except for aggregate initialization). -Wsystem-headers will give you -Wconversion warnings for the code inside <memory>: /usr/include/c++/7/bits/unique_ptr.h:825:30: warning: conversion to ‘unsigned char’ from ‘unsigned int’ may alter its value [-Wconversion] { return unique_ptr<_Tp>(new _Tp(std::forward<_Args>(__args)...)); } ^ This is the same issue as PR 58876, namely that the problem happens inside a system header, so the diagnostics are suppressed by default. It has nothing to do with perfect forwarding or std::forward.