Hello, in my application I have the need to read EXR files and split them up into layers and channels.
I'm currently using OpenExr-1.6.1 on Linux (64 bit). Therefore I open the file, read the header (dimensions and channels) and iterate over all channels mentioned there. For each channel I create a memory area where the data should be put upon reading the content. This memory area is added to the framebuffer. This works for all openexr sample images except Tiles/Spirals.exr ScanLines/Blobbies.exr These two make the application crash. It seems that memory gets heavily corrupted. Does anyone of you have an idea of what I'm doing wrong? ----- snip ----- #include "Iex.h" #include "ImfInputFile.h" #include "ImfHeader.h" #include "ImfChannelList.h" #include "ImfFrameBuffer.h" #include <stdexcept> #include <vector> namespace { /*! * \brief Determines the number of bytes we need to store a pixel of type \c n_type * * \return 0 on error, a value > 0 otherwise */ unsigned char getPixelSize(Imf::PixelType n_type) { switch (n_type) { case Imf::UINT: return sizeof(unsigned int); case Imf::HALF: return 2; // per definition, a Half is a 16 bit float value case Imf::FLOAT: return sizeof(float); } return 0; } } int main(int argc, char** argv) { Imf::InputFile f(argv[1]); if (!f.isComplete()) { throw std::runtime_error("File not complete"); } const Imf::Header& hdr = f.header(); Imath::Box2i sz = hdr.dataWindow(); size_t width = sz.max.x - sz.min.x + 1; size_t height = sz.max.y - sz.min.y + 1; std::vector<char*> buffers; // to free them later Imf::FrameBuffer frameBuffer; const Imf::ChannelList& channels(hdr.channels()); // all the channels // get all the channels, allocate data for the buffer and create a slice within the FrameBuffer for (Imf::ChannelList::ConstIterator channel = channels.begin(); channel != channels.end(); ++channel) { // XXX: use an auto_ptr here and put it into a Boost Pointer Container char *tmpBuf = new char[width * height * getPixelSize(channel.channel().type) * 2]; buffers.push_back(tmpBuf); // calculate the address of pixel (0,0) char *base = tmpBuf + (getPixelSize(channel.channel().type) * (sz.min.x - sz.min.y * width)); // create a Slice in the Framebuffer frameBuffer.insert(channel.name(), Imf::Slice( channel.channel().type, base, getPixelSize(channel.channel().type), getPixelSize(channel.channel().type) * width, channel.channel().xSampling, channel.channel().ySampling, 0.0)); } f.setFrameBuffer(frameBuffer); f.readPixels(sz.min.y, sz.max.y); for (std::vector<char*>::iterator i = buffers.begin(); i != buffers.end(); ++i) { std::cerr << "Free buffer at: " << (void*) *i << std::endl; delete *i; } return 0; } ----- snip ----- Many thanks, Ronny
_______________________________________________ Openexr-devel mailing list Openexr-devel@nongnu.org http://lists.nongnu.org/mailman/listinfo/openexr-devel