Skip to content

Commit

Permalink
Rewrite code to be byte-order independent.
Browse files Browse the repository at this point in the history
Fixes #263.
  • Loading branch information
joto committed Jul 23, 2018
1 parent c7e7674 commit ff16782
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 13 deletions.
15 changes: 8 additions & 7 deletions include/osmium/io/detail/pbf_input_format.hpp
Expand Up @@ -44,7 +44,6 @@ DEALINGS IN THE SOFTWARE.
#include <osmium/thread/util.hpp>
#include <osmium/util/config.hpp>

#include <protozero/byteswap.hpp>
#include <protozero/pbf_message.hpp>
#include <protozero/types.hpp>

Expand Down Expand Up @@ -97,18 +96,20 @@ namespace osmium {
* the length of the following BlobHeader.
*/
uint32_t read_blob_header_size_from_file() {
uint32_t size_in_network_byte_order;
uint32_t size;

try {
const std::string input_data{read_from_input_queue(sizeof(size_in_network_byte_order))};
size_in_network_byte_order = *reinterpret_cast<const uint32_t*>(input_data.data());
// size is encoded in network byte order
const std::string input_data{read_from_input_queue(sizeof(size))};
const char* d = input_data.data();
size = (static_cast<uint32_t>(d[3])) |
(static_cast<uint32_t>(d[2]) << 8u) |
(static_cast<uint32_t>(d[1]) << 16u) |
(static_cast<uint32_t>(d[0]) << 24u);
} catch (const osmium::pbf_error&) {
return 0; // EOF
}

uint32_t size = size_in_network_byte_order;
::protozero::byteswap_inplace(&size);

if (size > static_cast<uint32_t>(max_blob_header_size)) {
throw osmium::pbf_error{"invalid BlobHeader size (> max_blob_header_size)"};
}
Expand Down
14 changes: 8 additions & 6 deletions include/osmium/io/detail/pbf_output_format.hpp
Expand Up @@ -62,7 +62,6 @@ DEALINGS IN THE SOFTWARE.
#include <osmium/util/misc.hpp>
#include <osmium/visitor.hpp>

#include <protozero/byteswap.hpp>
#include <protozero/pbf_builder.hpp>
#include <protozero/pbf_writer.hpp>
#include <protozero/types.hpp>
Expand Down Expand Up @@ -193,13 +192,16 @@ namespace osmium {
// data plus a few header bytes (https://zlib.net/zlib_tech.html).
pbf_blob_header.add_int32(FileFormat::BlobHeader::required_int32_datasize, static_cast<int32_t>(blob_data.size()));

auto sz = static_cast<uint32_t>(blob_header_data.size());
::protozero::byteswap_inplace(&sz);
const auto size = static_cast<uint32_t>(blob_header_data.size());

// write to output: the 4-byte BlobHeader-Size followed by the BlobHeader followed by the Blob
// write to output: the 4-byte BlobHeader size in network
// byte order followed by the BlobHeader followed by the Blob
std::string output;
output.reserve(sizeof(sz) + blob_header_data.size() + blob_data.size());
output.append(reinterpret_cast<const char*>(&sz), sizeof(sz));
output.reserve(4 + blob_header_data.size() + blob_data.size());
output += static_cast<char>((size >> 24u) & 0xffu);
output += static_cast<char>((size >> 16u) & 0xffu);
output += static_cast<char>((size >> 8u) & 0xffu);
output += static_cast<char>( size & 0xffu);
output.append(blob_header_data);
output.append(blob_data);

Expand Down

0 comments on commit ff16782

Please sign in to comment.