forked from Begun/libslave
-
Notifications
You must be signed in to change notification settings - Fork 13
/
Copy pathdecimal_supp.cpp
65 lines (57 loc) · 1.54 KB
/
decimal_supp.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
#include "decimal_supp.h"
#include <cstring>
#include "decimal_internal.h"
using namespace slave;
namespace
{
inline uint8_t round_up(uint8_t v)
{
return (v + decimal::MAX_DIGITS_PER_WORD - 1) / decimal::MAX_DIGITS_PER_WORD;
}
}
decimal::digit_and_count_t decimal::IntegerDigitsTrait::read(const Decimal& d, size_t pos)
{
digit_t v = 0;
uint8_t count = MAX_DIGITS_PER_WORD;
size_t offset = 0;
if (0 != (d.intg % MAX_DIGITS_PER_WORD))
{
if (0 == pos)
{
count = d.intg % MAX_DIGITS_PER_WORD;
offset = sizeof(Decimal::storage) - digits2bytes[count];
}
else
{
offset = (pos - 1) * sizeof(v);
}
}
else
{
offset = pos * sizeof(v);
}
std::memcpy(&v, d.storage + offset, digits2bytes[count]);
return decimal::digit_and_count_t(v, count);
}
size_t decimal::IntegerDigitsTrait::size(const Decimal& d)
{
return round_up(d.intg);
}
decimal::digit_and_count_t decimal::FractionalDigitsTrait::read(const Decimal& d, size_t pos)
{
digit_t v = 0;
size_t offset = ((d.intg / MAX_DIGITS_PER_WORD) + pos) * sizeof(v);
uint8_t count = MAX_DIGITS_PER_WORD;
if (pos == (size(d) - 1))
{
count = d.frac % MAX_DIGITS_PER_WORD;
if (0 == count)
count = MAX_DIGITS_PER_WORD;
}
std::memcpy(&v, d.storage + offset, digits2bytes[count]);
return decimal::digit_and_count_t(v, count);
}
size_t decimal::FractionalDigitsTrait::size(const Decimal& d)
{
return round_up(d.frac);
}