Commit ca15d37a authored by Mukund Sivaraman's avatar Mukund Sivaraman
Browse files

[2850] Split large switch block into methods

parent 10386454
......@@ -41,6 +41,123 @@ ZoneTableSegmentMapped::ZoneTableSegmentMapped(const RRClass& rrclass) :
{
}
void
ZoneTableSegmentMapped::openCreate(const std::string& filename) {
// In case there is a checksum mismatch, we throw. We want the
// segment to be automatically destroyed then.
std::auto_ptr<MemorySegmentMapped> segment
(new MemorySegmentMapped(filename, MemorySegmentMapped::CREATE_ONLY));
// There must be no previously saved checksum.
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (result.first) {
isc_throw(isc::Unexpected,
"There is already a saved checksum in a mapped segment "
"opened in create mode.");
}
// Allocate space for a checksum (which is saved during close).
void* checksum = segment->allocate(sizeof(uint32_t));
*static_cast<uint32_t*>(checksum) = 0;
segment->setNamedAddress(ZONE_TABLE_CHECKSUM_NAME, checksum);
// There must be no previously saved ZoneTableHeader.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
isc_throw(isc::Unexpected,
"There is already a saved ZoneTableHeader in a "
"mapped segment opened in create mode.");
}
void* ptr = segment->allocate(sizeof(ZoneTableHeader));
ZoneTableHeader* new_header = new(ptr)
ZoneTableHeader(ZoneTable::create(*segment, rrclass_));
segment->setNamedAddress(ZONE_TABLE_HEADER_NAME, new_header);
header_ = new_header;
mem_sgmt_.reset(segment.release());
}
void
ZoneTableSegmentMapped::openReadWrite(const std::string& filename) {
// In case there is a checksum mismatch, we throw. We want the
// segment to be automatically destroyed then.
std::auto_ptr<MemorySegmentMapped> segment
(new MemorySegmentMapped(filename,
MemorySegmentMapped::OPEN_OR_CREATE));
// If there is a previously saved checksum, verify that it is
// consistent. Otherwise, allocate space for a checksum (which is
// saved during close).
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (result.first) {
// The segment was already shrunk when it was last closed. Check
// that its checksum is consistent.
assert(result.second);
uint32_t* checksum = static_cast<uint32_t*>(result.second);
const uint32_t saved_checksum = *checksum;
// First, clear the checksum so that getCheckSum() returns a
// consistent value.
*checksum = 0;
const uint32_t new_checksum = segment->getCheckSum();
if (saved_checksum != new_checksum) {
isc_throw(isc::Unexpected,
"Saved checksum doesn't match mapped segment data");
}
} else {
void* checksum = segment->allocate(sizeof(uint32_t));
*static_cast<uint32_t*>(checksum) = 0;
segment->setNamedAddress(ZONE_TABLE_CHECKSUM_NAME, checksum);
}
// If there is a previously saved ZoneTableHeader, use
// it. Otherwise, allocate a new header.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
assert(result.second);
header_ = static_cast<ZoneTableHeader*>(result.second);
} else {
void* ptr = segment->allocate(sizeof(ZoneTableHeader));
ZoneTableHeader* new_header = new(ptr)
ZoneTableHeader(ZoneTable::create(*segment, rrclass_));
segment->setNamedAddress(ZONE_TABLE_HEADER_NAME, new_header);
header_ = new_header;
}
mem_sgmt_.reset(segment.release());
}
void
ZoneTableSegmentMapped::openReadOnly(const std::string& filename) {
// In case there is a checksum mismatch, we throw. We want the
// segment to be automatically destroyed then.
std::auto_ptr<MemorySegmentMapped> segment
(new MemorySegmentMapped(filename));
// There must be a previously saved checksum.
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (!result.first) {
isc_throw(isc::Unexpected,
"There is no previously saved checksum in a "
"mapped segment opened in read-only mode.");
}
// We can't verify the checksum here as we can't set the checksum to
// 0 for checksum calculation in a read-only segment. So we continue
// without verifying the checksum.
// There must be a previously saved ZoneTableHeader.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
assert(result.second);
header_ = static_cast<ZoneTableHeader*>(result.second);
} else {
isc_throw(isc::Unexpected,
"There is no previously saved ZoneTableHeader in a "
"mapped segment opened in read-only mode.");
}
mem_sgmt_.reset(segment.release());
}
void
ZoneTableSegmentMapped::reset(MemorySegmentOpenMode mode,
isc::data::ConstElementPtr params)
......@@ -86,117 +203,20 @@ ZoneTableSegmentMapped::reset(MemorySegmentOpenMode mode,
const std::string filename = mapped_file->stringValue();
// In case there is a checksum mismatch, we throw. We want the
// segment to be automatically destroyed then.
std::auto_ptr<MemorySegmentMapped> segment;
switch (mode) {
case CREATE: {
segment.reset(new MemorySegmentMapped
(filename,
MemorySegmentMapped::CREATE_ONLY));
// There must be no previously saved checksum.
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (result.first) {
isc_throw(isc::Unexpected,
"There is already a saved checksum in a mapped segment "
"opened in create mode.");
}
// Allocate space for a checksum (which is saved during close).
void* checksum = segment->allocate(sizeof(uint32_t));
*static_cast<uint32_t*>(checksum) = 0;
segment->setNamedAddress(ZONE_TABLE_CHECKSUM_NAME, checksum);
// There must be no previously saved ZoneTableHeader.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
isc_throw(isc::Unexpected,
"There is already a saved ZoneTableHeader in a "
"mapped segment opened in create mode.");
}
void* ptr = segment->allocate(sizeof(ZoneTableHeader));
ZoneTableHeader* new_header = new(ptr)
ZoneTableHeader(ZoneTable::create(*segment, rrclass_));
segment->setNamedAddress(ZONE_TABLE_HEADER_NAME, new_header);
header_ = new_header;
case CREATE:
openCreate(filename);
break;
}
case READ_WRITE: {
segment.reset(new MemorySegmentMapped
(filename, MemorySegmentMapped::OPEN_OR_CREATE));
// If there is a previously saved checksum, verify that it is
// consistent. Otherwise, allocate space for a checksum (which
// is saved during close).
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (result.first) {
// The segment was already shrunk when it was last
// closed. Check that its checksum is consistent.
assert(result.second);
uint32_t* checksum = static_cast<uint32_t*>(result.second);
const uint32_t saved_checksum = *checksum;
// First, clear the checksum so that getCheckSum() returns
// a consistent value.
*checksum = 0;
const uint32_t new_checksum = segment->getCheckSum();
if (saved_checksum != new_checksum) {
isc_throw(isc::Unexpected,
"Saved checksum doesn't match mapped segment data");
}
} else {
void* checksum = segment->allocate(sizeof(uint32_t));
*static_cast<uint32_t*>(checksum) = 0;
segment->setNamedAddress(ZONE_TABLE_CHECKSUM_NAME, checksum);
}
// If there is a previously saved ZoneTableHeader, use
// it. Otherwise, allocate a new header.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
assert(result.second);
header_ = static_cast<ZoneTableHeader*>(result.second);
} else {
void* ptr = segment->allocate(sizeof(ZoneTableHeader));
ZoneTableHeader* new_header = new(ptr)
ZoneTableHeader(ZoneTable::create(*segment, rrclass_));
segment->setNamedAddress(ZONE_TABLE_HEADER_NAME, new_header);
header_ = new_header;
}
case READ_WRITE:
openReadWrite(filename);
break;
}
case READ_ONLY: {
segment.reset(new MemorySegmentMapped(filename));
// There must be a previously saved checksum.
MemorySegment::NamedAddressResult result =
segment->getNamedAddress(ZONE_TABLE_CHECKSUM_NAME);
if (!result.first) {
isc_throw(isc::Unexpected,
"There is no previously saved checksum in a "
"mapped segment opened in read-only mode.");
}
// We can't verify the checksum here as we can't set the
// checksum to 0 for checksum calculation in a read-only
// segment. So we continue without verifying the checksum.
// There must be a previously saved ZoneTableHeader.
result = segment->getNamedAddress(ZONE_TABLE_HEADER_NAME);
if (result.first) {
assert(result.second);
header_ = static_cast<ZoneTableHeader*>(result.second);
} else {
isc_throw(isc::Unexpected,
"There is no previously saved ZoneTableHeader in a "
"mapped segment opened in read-only mode.");
}
}
case READ_ONLY:
openReadOnly(filename);
}
current_mode_ = mode;
mem_sgmt_.reset(segment.release());
}
// After more methods' definitions are added here, it would be a good
......
......@@ -98,10 +98,15 @@ public:
isc::data::ConstElementPtr params);
private:
// Internally holds a MemorySegmentMapped. This is NULL on
// construction, and is set by the \c reset() method.
void openCreate(const std::string& filename);
void openReadWrite(const std::string& filename);
void openReadOnly(const std::string& filename);
private:
isc::dns::RRClass rrclass_;
MemorySegmentOpenMode current_mode_;
// Internally holds a MemorySegmentMapped. This is NULL on
// construction, and is set by the \c reset() method.
boost::scoped_ptr<isc::util::MemorySegmentMapped> mem_sgmt_;
ZoneTableHeader* header_;
};
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment