25 #include <libopenraw/debug.h>
28 #include "mrwcontainer.hpp"
30 using namespace Debug;
38 : m_start(start), m_container(_container), m_loaded(false)
40 LOGDBG2(
"> DataBlock start == %lld\n", (
long long int)start);
41 if (m_container->
fetchData(m_name, m_start, 4) != 4) {
43 LOGWARN(
" Error reading block name %lld\n", (
long long int)start);
46 auto result = m_container->
readInt32(m_container->file(), m_container->endian());
49 LOGWARN(
" Error reading block length %lld\n", (
long long int)start);
52 m_length = result.value();
53 LOGDBG1(
" DataBlock %s, length %d at %lld\n",
name().c_str(), m_length,
54 (
long long int)m_start);
55 LOGDBG2(
"< DataBlock\n");
63 mc->file()->seek(m_start + DataBlockHeaderLength + off, SEEK_SET);
64 return mc->readUInt8(mc->file());
71 mc->file()->seek(m_start + DataBlockHeaderLength + off, SEEK_SET);
72 return mc->
readUInt16(mc->file(), mc->endian());
81 s = mc->
fetchData(buf, m_start + DataBlockHeaderLength + off, 8);
103 if ((p[0] == 0x00) && (p[1] ==
'M') && (p[2] ==
'R') && (p[3] ==
'M')) {
105 LOGDBG1(
"Identified MRW file\n");
110 LOGDBG1(
"Unidentified MRW file\n");
120 LOGDBG1(
"> MRWContainer::locateDirsPreHook()\n");
121 m_endian = ENDIAN_BIG;
124 mrm = std::make_shared<MRW::DataBlock>(m_offset,
this);
125 if (mrm->name() !=
"MRM") {
126 LOGWARN(
"MRW file begins not with MRM block, "
127 "but with unrecognized DataBlock :: name == %s\n",
128 mrm->name().c_str());
135 position = mrm->offset() + MRW::DataBlockHeaderLength;
136 while (position < pixelDataOffset()) {
137 auto ref = std::make_shared<MRW::DataBlock>(position,
this);
138 LOGDBG1(
"Loaded DataBlock :: name == %s\n", ref->name().c_str());
139 if (!ref || !ref->loaded()) {
142 if (ref->name() ==
"PRD") {
144 LOGWARN(
"File contains duplicate DataBlock :: name == %s\n",
145 ref->name().c_str());
148 }
else if (ref->name() ==
"TTW") {
150 LOGWARN(
"File contains duplicate DataBlock :: name == %s\n",
151 ref->name().c_str());
154 }
else if (ref->name() ==
"WBG") {
156 LOGWARN(
"File contains duplicate DataBlock :: name == %s\n",
157 ref->name().c_str());
160 }
else if (ref->name() ==
"RIF") {
162 LOGWARN(
"File contains duplicate DataBlock :: name == %s\n",
163 ref->name().c_str());
166 }
else if (ref->name() !=
"PAD") {
167 LOGWARN(
"File contains unrecognized DataBlock :: name == %s\n",
168 ref->name().c_str());
170 position = ref->offset() + MRW::DataBlockHeaderLength + ref->length();
175 LOGWARN(
"File does NOT contain expected DataBlock :: name == PRD\n");
179 LOGWARN(
"File does NOT contain expected DataBlock :: name == TTW\n");
183 LOGWARN(
"File does NOT contain expected DataBlock :: name == WBG\n");
187 LOGWARN(
"File does NOT contain expected DataBlock :: name == RIF\n");
192 if (fetchData(version,
193 prd->offset() + MRW::DataBlockHeaderLength + MRW::PRD_VERSION,
196 LOGDBG1(
" Error reading version string\n");
199 m_version = std::string(version);
200 LOGDBG1(
" MRW file version == %s\n", m_version.c_str());
206 m_offset = ttw->offset() + MRW::DataBlockHeaderLength;
211 setExifOffsetCorrection(m_offset);
212 LOGDBG1(
"setting correction to %lld\n", (
long long int)m_offset);
215 m_file->seek(m_offset, SEEK_SET);
216 LOGDBG1(
"< MRWContainer\n");
std::shared_ptr< Stream > Ptr
virtual bool locateDirsPreHook() override
hook to be called at the start of _locateDirs()
virtual IfdFileContainer::EndianType isMagicHeader(const char *p, int len) override
Option< uint16_t > uint16_val(off_t offset) const
Option< std::string > string_val(off_t offset) const
Option< uint8_t > uint8_val(off_t offset) const
Option< uint16_t > readUInt16(const IO::Stream::Ptr &f, EndianType endian) const
Read an uint16 following the m_endian set.
EndianType
Define the endian of the container.
size_t fetchData(void *buf, off_t offset, size_t buf_size) const
Fetch the data chunk from the file.
Option< int32_t > readInt32(const IO::Stream::Ptr &f, EndianType endian) const
Read an int32 following the m_endian set.
An option type inspired by Rust.
Global namespace for libopenraw.