Hi Nathan, I'll have a look. Thanks for submitting, Christian On Fri, Jun 18, 2010 at 1:34 PM, Nathan Crookston <nathan.crookston@gmail.com> wrote:
All,
While writing some image conversion code using scoped_channel_value I encountered several compiler warnings. The following minimal code demonstrates:
Compiled with VC8, command line: "cl simple.cpp /Iboost /W3 /EHsc"
////// BEGIN CODE /////////////////////////////
#include "boost/gil/gil_all.hpp"
namespace boost { namespace gil {
const boost::uint16_t bits12_max_val = 0xFFF; struct bits12_min { static boost::uint16_t apply() { return 0; } }; struct bits12_max { static boost::uint16_t apply() { return bits12_max_val; } };
typedef boost::gil::scoped_channel_value<boost::uint16_t, bits12_min, bits12_max> bits12;
namespace detail { template <> struct unsigned_integral_max_value<bits12> : public mpl::integral_c<uint32_t,bits12_max_val> {};
template <> struct unsigned_integral_num_bits<bits12> : public mpl::int_<12> {};
}//end detail
GIL_DEFINE_BASE_TYPEDEFS(12, gray)
const boost::uint16_t bits14_max_val = 0x3FFF; struct bits14_min { static boost::uint16_t apply() { return 0; } }; struct bits14_max { static boost::uint16_t apply() { return bits14_max_val; } };
typedef boost::gil::scoped_channel_value<boost::uint16_t, bits14_min, bits14_max> bits14;
namespace detail { template <> struct unsigned_integral_max_value<bits14> : public mpl::integral_c<uint32_t,bits14_max_val> {};
template <> struct unsigned_integral_num_bits<bits14> : public mpl::int_<14> {};
}//end detail
GIL_DEFINE_BASE_TYPEDEFS(14, gray) } } //end gil, boost
using namespace boost::gil;
int main() { gray14_image_t img14(2,2); color_converted_view<gray12_pixel_t>(view(img14))(1,0);
gray32f_image_t img32f(2,2); color_converted_view<gray12_pixel_t>(view(img32f))(1,0);
return 0; }
////// END CODE ///////////////////////////////
It produces the following warnings, trimmed to only those I thought relevant:
///////////////// BEGIN Relevant Warnings ////////////////////////////////////// c:\cygwin\home\ncrookston\boost\boost\gil\channel_algorithm.hpp(257) : warning C 4244: 'argument' : conversion from 'const double' to 'boost::uint16_t', possible loss of data c:\cygwin\home\ncrookston\boost\boost\gil\channel_algorithm.hpp(252) : w hile compiling class template member function 'boost::gil::scoped_channel_value< BaseChannelValue,MinVal,MaxVal> boost::gil::detail::channel_converter_unsigned_i ntegral_nondivisible<SrcChannelV,DstChannelV,SrcLessThanDst,CannotFitInInteger>: :operator ()(SrcChannelV) const' with [ BaseChannelValue=boost::uint16_t, MinVal=boost::gil::bits12_min, MaxVal=boost::gil::bits12_max, SrcChannelV=boost::gil::scoped_channel_value<boost::uint16_t,boost:: gil::bits14_min,boost::gil::bits14_max>, DstChannelV=boost::gil::scoped_channel_value<boost::uint16_t,boost:: gil::bits12_min,boost::gil::bits12_max>, SrcLessThanDst=false, CannotFitInInteger=false ]
<snip lots of instantiation backtrace>
c:\cygwin\home\ncrookston\boost\boost\gil\channel_algorithm.hpp(268) : warning C 4244: 'argument' : conversion from 'float' to 'boost::uint16_t', possible loss o f data c:\cygwin\home\ncrookston\boost\boost\gil\channel_algorithm.hpp(268) : w hile compiling class template member function 'boost::gil::scoped_channel_value< BaseChannelValue,MinVal,MaxVal> boost::gil::channel_converter_unsigned<SrcChanne lV,DstChannelV>::operator ()(boost::gil::bits32f) const' with [ BaseChannelValue=boost::uint16_t, MinVal=boost::gil::bits12_min, MaxVal=boost::gil::bits12_max, SrcChannelV=boost::gil::scoped_channel_value<float,boost::gil::float _zero,boost::gil::float_one>, DstChannelV=boost::gil::scoped_channel_value<boost::uint16_t,boost:: gil::bits12_min,boost::gil::bits12_max> ]
<snip lots more instantiation backtrace>
/////////////////////// END Relevant Warnings //////////////////////////////////////////////////
Interestingly, g++ doesn't have an issue with the code.
The following patch corrects the problem. I'd be happy to create a trac ticket, write some tests, etc. Please advise.
////////////// BEGIN Patch ////////////////////////////////////// Index: channel_algorithm.hpp =================================================================== --- channel_algorithm.hpp (revision 63088) +++ channel_algorithm.hpp (working copy) @@ -243,7 +243,18 @@ } };
+// Determines the base type of the channel. +template <typename Channel> +struct base_channel { typedef Channel type; };
+template <typename BaseChannelValue, typename MinVal, typename MaxVal> +struct base_channel<scoped_channel_value<BaseChannelValue,MinVal,MaxVal> > +: public base_channel<BaseChannelValue> {}; + +template <int NumBits> +struct base_channel<packed_channel_value<NumBits> > +{ typedef typename packed_channel_value<NumBits>::integer_t type; }; + // Both source and destination are unsigned integral channels, // the dst max value is less than (or equal to) the src max value, // and the src max value is not divisible by the dst max value @@ -253,8 +264,8 @@ typedef typename unsigned_integral_max_value<SrcChannelV>::value_type integer_t;
static const double div = unsigned_integral_max_value<SrcChannelV>::value / double(unsigned_integral_max_value<DstChannelV>::value); - static const integer_t div2 = integer_t(div/2); - return DstChannelV((src + div2) / div); + static const integer_t div2 = static_cast<integer_t>(div/2); + return static_cast<typename base_channel<DstChannelV>::type>((src + div2) / div); } };
@@ -265,7 +276,8 @@ /////////////////////////////////////////////////////
template <typename DstChannelV> struct channel_converter_unsigned<bits32f,DstChannelV> : public std::unary_function<bits32f,DstChannelV> { - DstChannelV operator()(bits32f x) const { return DstChannelV(x*channel_traits<DstChannelV>::max_value()+0.5f); } + DstChannelV operator()(bits32f x) const { return + static_cast<typename detail::base_channel<DstChannelV>::type>(x*channel_traits<DstChannelV>::max_value()+0.5f); } };
template <typename SrcChannelV> struct channel_converter_unsigned<SrcChannelV,bits32f> : public std::unary_function<SrcChannelV,bits32f> {
//////// END patch ////////////////
Thanks, Nate _______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users