Main MRPT website
>
C++ reference for MRPT 1.9.9
mrpt
core
bit_cast.h
Go to the documentation of this file.
1
/* +------------------------------------------------------------------------+
2
| Mobile Robot Programming Toolkit (MRPT) |
3
| http://www.mrpt.org/ |
4
| |
5
| Copyright (c) 2005-2017, Individual contributors, see AUTHORS file |
6
| See: http://www.mrpt.org/Authors - All rights reserved. |
7
| Released under BSD License. See details in http://www.mrpt.org/License |
8
+------------------------------------------------------------------------+ */
9
10
// Copyright 2016 The Chromium Authors. All rights reserved.
11
// Use of this source code is governed by a BSD-style license that can be
12
// found in the LICENSE file.
13
#ifndef BASE_BIT_CAST_H_
14
#define BASE_BIT_CAST_H_
15
#include <string.h>
16
#include <type_traits>
17
//#include "base/compiler_specific.h" // mrpt
18
//#include "base/template_util.h" // mrpt
19
//#include "build/build_config.h" // mrpt
20
// bit_cast<Dest,Source> is a template function that implements the equivalent
21
// of "*reinterpret_cast<Dest*>(&source)". We need this in very low-level
22
// functions like the protobuf library and fast math support.
23
//
24
// float f = 3.14159265358979;
25
// int i = bit_cast<int32_t>(f);
26
// // i = 0x40490fdb
27
//
28
// The classical address-casting method is:
29
//
30
// // WRONG
31
// float f = 3.14159265358979; // WRONG
32
// int i = * reinterpret_cast<int*>(&f); // WRONG
33
//
34
// The address-casting method actually produces undefined behavior according to
35
// the ISO C++98 specification, section 3.10 ("basic.lval"), paragraph 15.
36
// (This did not substantially change in C++11.) Roughly, this section says: if
37
// an object in memory has one type, and a program accesses it with a different
38
// type, then the result is undefined behavior for most values of "different
39
// type".
40
//
41
// This is true for any cast syntax, either *(int*)&f or
42
// *reinterpret_cast<int*>(&f). And it is particularly true for conversions
43
// between integral lvalues and floating-point lvalues.
44
//
45
// The purpose of this paragraph is to allow optimizing compilers to assume that
46
// expressions with different types refer to different memory. Compilers are
47
// known to take advantage of this. So a non-conforming program quietly
48
// produces wildly incorrect output.
49
//
50
// The problem is not the use of reinterpret_cast. The problem is type punning:
51
// holding an object in memory of one type and reading its bits back using a
52
// different type.
53
//
54
// The C++ standard is more subtle and complex than this, but that is the basic
55
// idea.
56
//
57
// Anyways ...
58
//
59
// bit_cast<> calls memcpy() which is blessed by the standard, especially by the
60
// example in section 3.9 . Also, of course, bit_cast<> wraps up the nasty
61
// logic in one place.
62
//
63
// Fortunately memcpy() is very fast. In optimized mode, compilers replace
64
// calls to memcpy() with inline object code when the size argument is a
65
// compile-time constant. On a 32-bit system, memcpy(d,s,4) compiles to one
66
// load and one store, and memcpy(d,s,8) compiles to two loads and two stores.
67
template
<
class
Dest,
class
Source>
68
inline
Dest
bit_cast
(
const
Source&
source
)
69
{
70
static_assert(
71
sizeof
(Dest) ==
sizeof
(Source),
72
"bit_cast requires source and destination to be the same size"
);
73
static_assert(
74
std::is_trivially_copyable<Dest>::value
,
75
"bit_cast requires the destination type to be copyable"
);
76
static_assert(
77
std::is_trivially_copyable<Source>::value
,
78
"bit_cast requires the source type to be copyable"
);
79
Dest dest;
80
memcpy
(&dest, &
source
,
sizeof
(dest));
81
return
dest;
82
}
83
#endif // BASE_BIT_CAST_H_
bit_cast
Dest bit_cast(const Source &source)
Definition:
bit_cast.h:68
source
GLsizei GLsizei GLchar * source
Definition:
glext.h:4082
value
GLsizei const GLfloat * value
Definition:
glext.h:4117
mrpt::system::os::memcpy
void memcpy(void *dest, size_t destSize, const void *src, size_t copyCount) noexcept
An OS and compiler independent version of "memcpy".
Definition:
os.cpp:356
Page generated by
Doxygen 1.8.17
for MRPT 1.9.9 Git: ad3a9d8ae Tue May 1 23:10:22 2018 -0700 at miƩ 12 jul 2023 10:03:34 CEST