-
-
Notifications
You must be signed in to change notification settings - Fork 46
/
xorstr.hpp
157 lines (138 loc) · 4.35 KB
/
xorstr.hpp
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
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
#pragma once
#include <string>
#include <utility>
namespace
{
constexpr int const_atoi(char c)
{
return c - '0';
}
}
#ifdef _MSC_VER
#define ALWAYS_INLINE __forceinline
#else
#define ALWAYS_INLINE __attribute__((always_inline))
#endif
template<typename _string_type, size_t _length>
class _Basic_XorStr
{
using value_type = typename _string_type::value_type;
static constexpr auto _length_minus_one = _length - 1;
public:
constexpr ALWAYS_INLINE _Basic_XorStr(value_type const (&str)[_length])
: _Basic_XorStr(str, std::make_index_sequence<_length_minus_one>())
{
}
inline auto c_str() const
{
decrypt();
return data;
}
inline auto str() const
{
decrypt();
return _string_type(data, data + _length_minus_one);
}
inline operator _string_type() const
{
return str();
}
private:
template<size_t... indices>
constexpr ALWAYS_INLINE _Basic_XorStr(value_type const (&str)[_length], std::index_sequence<indices...>)
: data{ crypt(str[indices], indices)..., '\0' },
encrypted(true)
{
}
static constexpr auto XOR_KEY = static_cast<value_type>(
const_atoi(__TIME__[7]) +
const_atoi(__TIME__[6]) * 10 +
const_atoi(__TIME__[4]) * 60 +
const_atoi(__TIME__[3]) * 600 +
const_atoi(__TIME__[1]) * 3600 +
const_atoi(__TIME__[0]) * 36000
);
static ALWAYS_INLINE constexpr auto crypt(value_type c, size_t i)
{
return static_cast<value_type>(c ^ (XOR_KEY + i));
}
inline void decrypt() const
{
if (encrypted)
{
for (size_t t = 0; t < _length_minus_one; t++)
{
data[t] = crypt(data[t], t);
}
encrypted = false;
}
}
mutable value_type data[_length];
mutable bool encrypted;
};
//---------------------------------------------------------------------------
template<size_t _length>
using XorStrA = _Basic_XorStr<std::string, _length>;
template<size_t _length>
using XorStrW = _Basic_XorStr<std::wstring, _length>;
template<size_t _length>
using XorStrU16 = _Basic_XorStr<std::u16string, _length>;
template<size_t _length>
using XorStrU32 = _Basic_XorStr<std::u32string, _length>;
//---------------------------------------------------------------------------
template<typename _string_type, size_t _length, size_t _length2>
inline auto operator==(const _Basic_XorStr<_string_type, _length>& lhs, const _Basic_XorStr<_string_type, _length2>& rhs)
{
static_assert(_length == _length2, "XorStr== different length");
return _length == _length2 && lhs.str() == rhs.str();
}
//---------------------------------------------------------------------------
template<typename _string_type, size_t _length>
inline auto operator==(const _string_type& lhs, const _Basic_XorStr<_string_type, _length>& rhs)
{
return lhs.size() == _length && lhs == rhs.str();
}
//---------------------------------------------------------------------------
template<typename _stream_type, typename _string_type, size_t _length>
inline auto& operator<<(_stream_type& lhs, const _Basic_XorStr<_string_type, _length>& rhs)
{
lhs << rhs.c_str();
return lhs;
}
//---------------------------------------------------------------------------
template<typename _string_type, size_t _length, size_t _length2>
inline auto operator+(const _Basic_XorStr<_string_type, _length>& lhs, const _Basic_XorStr<_string_type, _length2>& rhs)
{
return lhs.str() + rhs.str();
}
//---------------------------------------------------------------------------
template<typename _string_type, size_t _length>
inline auto operator+(const _string_type& lhs, const _Basic_XorStr<_string_type, _length>& rhs)
{
return lhs + rhs.str();
}
//---------------------------------------------------------------------------
template<size_t _length>
constexpr ALWAYS_INLINE auto XorStr(char const (&str)[_length])
{
return XorStrA<_length>(str);
}
//---------------------------------------------------------------------------
template<size_t _length>
constexpr ALWAYS_INLINE auto XorStr(wchar_t const (&str)[_length])
{
return XorStrW<_length>(str);
}
//---------------------------------------------------------------------------
template<size_t _length>
constexpr ALWAYS_INLINE auto XorStr(char16_t const (&str)[_length])
{
return XorStrU16<_length>(str);
}
//---------------------------------------------------------------------------
template<size_t _length>
constexpr ALWAYS_INLINE auto XorStr(char32_t const (&str)[_length])
{
return XorStrU32<_length>(str);
}
//---------------------------------------------------------------------------