// This is included by any decompiled source file

#ifndef B8D59B54_1674_4C0F_AA2C_611385FF5D03
#define B8D59B54_1674_4C0F_AA2C_611385FF5D03

#if RE_DBG_INJECTED
#include "dbg_mem.h"
#else
#include "static_mem.h"
#endif

#include "base.h"

#include <gh_types.h>
#include <gh_global.h>

#ifdef _WIN32
#include <direct.h>
#include <process.h>
#else
#include <unistd.h>
#endif

template <size_t Offset, size_t Size> struct Field {};

template <size_t Size> struct _FieldBinderSizeTraits {
  using type = undefined;
};
template <> struct _FieldBinderSizeTraits<4> {
  using type = undefined4;
};
template <> struct _FieldBinderSizeTraits<2> {
  using type = undefined2;
};
template <> struct _FieldBinderSizeTraits<3> {
  using type = undefined3;
};

template <size_t Size> struct FieldBinder {
  void *dst;
  using ExpectedType = typename _FieldBinderSizeTraits<Size>::type;

  operator ExpectedType &() const {
    return *reinterpret_cast<ExpectedType *>(dst);
  }

  template <typename T> T *operator=(T *src) {
    union V {
      T *a;
      void *b;
    };
    V *trick = reinterpret_cast<V *>(this);
    return trick->a = src;
  }
  ExpectedType &operator=(ExpectedType src) {
    return *reinterpret_cast<ExpectedType *>(dst) = src;
  }
  ExpectedType &operator=(FieldBinder<Size> &other) {
    return *reinterpret_cast<ExpectedType *>(dst) =
               *reinterpret_cast<ExpectedType *>(other.dst);
  }
};

template <size_t Offset, size_t Size>
inline FieldBinder<Size> operator+(const void *str,
                                   Field<Offset, Size> offset) {
  return FieldBinder<Size>{.dst = (uint8_t *)str + Offset};
}

typedef uint32_t cc_type_t;

template <typename T0, typename T1>
inline constexpr undefined3 CONCAT12(T0 a, T1 b) {
  return undefined3(cc_type_t(a) << 16 | cc_type_t(b));
}
template <typename T0, typename T1>
inline constexpr cc_type_t CONCAT11(T0 a, T1 b) {
  return cc_type_t(a) << 8 | cc_type_t(b);
}
template <typename T0, typename T1>
inline constexpr cc_type_t CONCAT21(T0 a, T1 b) {
  return cc_type_t(a) << 8 | cc_type_t(b);
}

template <typename T0, typename T1>
inline constexpr cc_type_t CONCAT22(T0 a, T1 b) {
  return cc_type_t(a) << 16 | cc_type_t(b);
}

template <typename T0, typename T1>
inline constexpr cc_type_t CONCAT23(T0 a, T1 b) {
  return cc_type_t(a) << 24 | cc_type_t(b);
}

template <typename T0, typename T1>
inline constexpr cc_type_t CONCAT31(T0 a, T1 b) {
  return cc_type_t(a) << 8 | cc_type_t(b);
}

template <typename T0> inline constexpr char SUB21(T0 a, size_t b) {
  return cc_type_t(a) >> (b * 8);
}

template <typename T0> inline constexpr char SUB41(T0 a, size_t b) {
  return cc_type_t(a) >> (b * 8);
}

template <typename T0> inline constexpr uint16_t SUB42(T0 a, size_t b) {
  return cc_type_t(a) >> (b * 8);
}

inline longlong r3_ftol(float a) { return (longlong)a; }

constexpr byte R3ModId_not_initialized = 0xff;

#include "stub.h"

#endif /* B8D59B54_1674_4C0F_AA2C_611385FF5D03 */
