Skip to content

Commit

Permalink
consolidated implementation of BigEndian
Browse files Browse the repository at this point in the history
- works for any type size
- checks that we are dealing with numbers
- remove pointers in favor of more elegant c++ unions
  • Loading branch information
glesur committed Jul 26, 2024
1 parent f065cc1 commit 5dfa7c9
Show file tree
Hide file tree
Showing 3 changed files with 68 additions and 27 deletions.
31 changes: 4 additions & 27 deletions src/output/vtk.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,25 +21,18 @@
#include "idefix.hpp"
#include "input.hpp"
#include "dataBlock.hpp"
#include "bigEndian.hpp"
#include "scalarField.hpp"


// Forward class declaration
class Output;
class DataBlock;


class BaseVtk {
private:
// Endianness swaping function and variable
bool shouldSwapEndian {true};

protected:
BaseVtk() {
// Test endianness
int tmp1 = 1;
unsigned char *tmp2 = (unsigned char *) &tmp1;
if (*tmp2 == 0)
this->shouldSwapEndian = false;
// Initialise the root tag (used for MPI non-collective I/Os)
this->isRoot = idfx::prank == 0;
}
Expand Down Expand Up @@ -68,25 +61,9 @@ class BaseVtk {
// DataBlock parent
DataBlock *data;

/* ****************************************************************************/
/** Determines if the machine is little-endian. If so,
it will force the data to be big-endian.
@param in_number floating point number to be converted in big endian */
/* *************************************************************************** */
// BigEndian conversion
BigEndian BigEndian;

template <typename T>
T BigEndian(T in_number) {
if (shouldSwapEndian) {
unsigned char *bytes = (unsigned char*) &in_number;
unsigned char tmp = bytes[0];
bytes[0] = bytes[3];
bytes[3] = tmp;
tmp = bytes[1];
bytes[1] = bytes[2];
bytes[2] = tmp;
}
return(in_number);
}

void WriteHeaderString(const char* header, IdfxFileHandler fvtk) {
#ifdef WITH_MPI
Expand Down
1 change: 1 addition & 0 deletions src/utils/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
add_subdirectory(iterativesolver)

target_sources(idefix
PUBLIC ${CMAKE_CURRENT_LIST_DIR}/bigEndian.hpp
PUBLIC ${CMAKE_CURRENT_LIST_DIR}/dumpImage.cpp
PUBLIC ${CMAKE_CURRENT_LIST_DIR}/dumpImage.hpp
PUBLIC ${CMAKE_CURRENT_LIST_DIR}/lookupTable.hpp
Expand Down
63 changes: 63 additions & 0 deletions src/utils/bigEndian.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
// ***********************************************************************************
// Idefix MHD astrophysical code
// Copyright(C) Geoffroy R. J. Lesur <geoffroy.lesur@univ-grenoble-alpes.fr>
// and other code contributors
// Licensed under CeCILL 2.1 License, see COPYING for more information
// ***********************************************************************************

#ifndef UTILS_BIGENDIAN_HPP_
#define UTILS_BIGENDIAN_HPP_

#include <cstddef>
#include <type_traits>
#include "idefix.hpp"

/* ****************************************************************************/
/** Determines if the machine is little-endian. If so,
it will force the data to be big-endian.
@param in_number floating point number to be converted in big endian */
/* *************************************************************************** */

class BigEndian {
public:
BigEndian() {
// Test endianness
union {
uint32_t i;
char c[4];
} bint = {0x01020304};

if(bint.c[0] == 1)
this->shouldSwapEndian = false;
else
this->shouldSwapEndian = true;
}

// Swap when needed
template <class T>
T operator() (T in_number) {
static_assert(std::is_arithmetic_v<T> == true);
T out_number;
if (this->shouldSwapEndian) {
constexpr int size = sizeof(T);
union {
T u;
unsigned char byte[size];
} in, out;
in.u = in_number;
for(int n = 0 ; n < size ; n++) {
out.byte[size-n-1] = in.byte[n];
}
out_number = out.u;
} else {
out_number = in_number;
}
return(out_number);
}

private:
// Endianness swaping flag
bool shouldSwapEndian;
};

#endif // UTILS_BIGENDIAN_HPP_

0 comments on commit 5dfa7c9

Please sign in to comment.