Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/openjdk-multiarch-jdk8u
Path: blob/aarch64-shenandoah-jdk8u272-b10/hotspot/src/share/vm/jfr/writers/jfrEncoders.hpp
38920 views
1
/*
2
* Copyright (c) 2015, 2018, Oracle and/or its affiliates. All rights reserved.
3
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4
*
5
* This code is free software; you can redistribute it and/or modify it
6
* under the terms of the GNU General Public License version 2 only, as
7
* published by the Free Software Foundation.
8
*
9
* This code is distributed in the hope that it will be useful, but WITHOUT
10
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12
* version 2 for more details (a copy is included in the LICENSE file that
13
* accompanied this code).
14
*
15
* You should have received a copy of the GNU General Public License version
16
* 2 along with this work; if not, write to the Free Software Foundation,
17
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18
*
19
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20
* or visit www.oracle.com if you need additional information or have any
21
* questions.
22
*
23
*/
24
25
#ifndef SHARE_VM_JFR_WRITERS_JFRENCODERS_HPP
26
#define SHARE_VM_JFR_WRITERS_JFRENCODERS_HPP
27
28
#include "memory/allocation.hpp"
29
#include "utilities/debug.hpp"
30
#include "utilities/globalDefinitions.hpp"
31
#ifdef TARGET_ARCH_x86
32
# include "bytes_x86.hpp"
33
#endif
34
#ifdef TARGET_ARCH_sparc
35
# include "bytes_sparc.hpp"
36
#endif
37
#ifdef TARGET_ARCH_zero
38
# include "bytes_zero.hpp"
39
#endif
40
#ifdef TARGET_ARCH_arm
41
# include "bytes_arm.hpp"
42
#endif
43
#ifdef TARGET_ARCH_ppc
44
# include "bytes_ppc.hpp"
45
#endif
46
#ifdef TARGET_ARCH_aarch32
47
# include "bytes_aarch32.hpp"
48
#endif
49
#ifdef TARGET_ARCH_aarch64
50
# include "bytes_aarch64.hpp"
51
#endif
52
53
//
54
// The Encoding policy prescribes a template
55
// method taking a first parameter of type T.
56
// This is the value to be encoded. The second
57
// parameter is a memory address - where to write
58
// the encoded value.
59
// The encoder method(s) should return the
60
// number of bytes encoded into that memory address.
61
//
62
// template <typename T>
63
// size_t encoder(T value, u1* dest);
64
//
65
// The caller ensures the destination
66
// address is not null and that T can be fitted
67
// in encoded form.
68
//
69
70
// Encoding policy classes
71
72
class BigEndianEncoderImpl {
73
public:
74
template <typename T>
75
static size_t encode(T value, u1* dest);
76
77
template <typename T>
78
static size_t encode(const T* src, size_t len, u1* dest);
79
80
template <typename T>
81
static size_t encode_padded(T value, u1* dest);
82
83
template <typename T>
84
static size_t encode_padded(const T* src, size_t len, u1* dest);
85
86
};
87
88
template <typename T>
89
inline size_t BigEndianEncoderImpl::encode(T value, u1* dest) {
90
assert(dest != NULL, "invariant");
91
switch (sizeof(T)) {
92
case 1: {
93
ShouldNotReachHere();
94
return 0;
95
}
96
case 2: {
97
Bytes::put_Java_u2(dest, value);
98
return 2;
99
}
100
case 4: {
101
Bytes::put_Java_u4(dest, value);
102
return 4;
103
}
104
case 8: {
105
Bytes::put_Java_u8(dest, value);
106
return 8;
107
}
108
}
109
ShouldNotReachHere();
110
return 0;
111
}
112
113
template <typename T>
114
inline size_t BigEndianEncoderImpl::encode(const T* src, size_t len, u1* dest) {
115
assert(dest != NULL, "invariant");
116
assert(len >= 1, "invariant");
117
if (1 == sizeof(T)) {
118
memcpy(dest, src, len);
119
return len;
120
}
121
size_t size = encode(*src, dest);
122
if (len > 1) {
123
for (size_t i = 1; i < len; ++i) {
124
size += encode(*(src + i), dest + size);
125
}
126
}
127
return size;
128
}
129
130
template <typename T>
131
inline size_t BigEndianEncoderImpl::encode_padded(T value, u1* dest) {
132
return encode(value, dest);
133
}
134
135
template <typename T>
136
inline size_t BigEndianEncoderImpl::encode_padded(const T* src, size_t len, u1* dest) {
137
assert(dest != NULL, "invariant");
138
assert(len >= 1, "invariant");
139
if (1 == sizeof(T)) {
140
memcpy(dest, src, len);
141
return len;
142
}
143
size_t size = encode_padded(*src, dest);
144
if (len > 1) {
145
for (size_t i = 1; i < len; ++i) {
146
size += encode_padded(*(src + i), dest + size);
147
}
148
}
149
return size;
150
}
151
152
153
// The Varint128 encoder implements encoding according to
154
// msb(it) 128bit encoding (1 encode bit | 7 value bits),
155
// using least significant byte order.
156
//
157
// Example (little endian platform):
158
// Value: 25674
159
// Binary: 00000000 0000000 01100100 01001010
160
// Varint encoded (3 bytes):
161
// Value: 13289473
162
// Varint encoded: 11001010 11001000 00000001
163
//
164
165
class Varint128EncoderImpl {
166
private:
167
template <typename T>
168
static u8 to_u8(T value);
169
170
public:
171
template <typename T>
172
static size_t encode(T value, u1* dest);
173
174
template <typename T>
175
static size_t encode(const T* src, size_t len, u1* dest);
176
177
template <typename T>
178
static size_t encode_padded(T value, u1* dest);
179
180
template <typename T>
181
static size_t encode_padded(const T* src, size_t len, u1* dest);
182
183
};
184
185
template <typename T>
186
inline u8 Varint128EncoderImpl::to_u8(T value) {
187
switch(sizeof(T)) {
188
case 1:
189
return static_cast<u8>(static_cast<u1>(value) & static_cast<u1>(0xff));
190
case 2:
191
return static_cast<u8>(static_cast<u2>(value) & static_cast<u2>(0xffff));
192
case 4:
193
return static_cast<u8>(static_cast<u4>(value) & static_cast<u4>(0xffffffff));
194
case 8:
195
return static_cast<u8>(value);
196
default:
197
fatal("unsupported type");
198
}
199
return 0;
200
}
201
202
static const u1 ext_bit = 0x80;
203
#define GREATER_THAN_OR_EQUAL_TO_128(v) (((u8)(~(ext_bit - 1)) & (v)))
204
#define LESS_THAN_128(v) !GREATER_THAN_OR_EQUAL_TO_128(v)
205
206
template <typename T>
207
inline size_t Varint128EncoderImpl::encode(T value, u1* dest) {
208
assert(dest != NULL, "invariant");
209
210
const u8 v = to_u8(value);
211
212
if (LESS_THAN_128(v)) {
213
*dest = static_cast<u1>(v); // set bit 0-6, no extension
214
return 1;
215
}
216
*dest = static_cast<u1>(v | ext_bit); // set bit 0-6, with extension
217
if (LESS_THAN_128(v >> 7)) {
218
*(dest + 1) = static_cast<u1>(v >> 7); // set bit 7-13, no extension
219
return 2;
220
}
221
*(dest + 1) = static_cast<u1>((v >> 7) | ext_bit); // set bit 7-13, with extension
222
if (LESS_THAN_128(v >> 14)) {
223
*(dest + 2) = static_cast<u1>(v >> 14); // set bit 14-20, no extension
224
return 3;
225
}
226
*(dest + 2) = static_cast<u1>((v >> 14) | ext_bit); // set bit 14-20, with extension
227
if (LESS_THAN_128(v >> 21)) {
228
*(dest + 3) = static_cast<u1>(v >> 21); // set bit 21-27, no extension
229
return 4;
230
}
231
*(dest + 3) = static_cast<u1>((v >> 21) | ext_bit); // set bit 21-27, with extension
232
if (LESS_THAN_128(v >> 28)) {
233
*(dest + 4) = static_cast<u1>(v >> 28); // set bit 28-34, no extension
234
return 5;
235
}
236
*(dest + 4) = static_cast<u1>((v >> 28) | ext_bit); // set bit 28-34, with extension
237
if (LESS_THAN_128(v >> 35)) {
238
*(dest + 5) = static_cast<u1>(v >> 35); // set bit 35-41, no extension
239
return 6;
240
}
241
*(dest + 5) = static_cast<u1>((v >> 35) | ext_bit); // set bit 35-41, with extension
242
if (LESS_THAN_128(v >> 42)) {
243
*(dest + 6) = static_cast<u1>(v >> 42); // set bit 42-48, no extension
244
return 7;
245
}
246
*(dest + 6) = static_cast<u1>((v >> 42) | ext_bit); // set bit 42-48, with extension
247
if (LESS_THAN_128(v >> 49)) {
248
*(dest + 7) = static_cast<u1>(v >> 49); // set bit 49-55, no extension
249
return 8;
250
}
251
*(dest + 7) = static_cast<u1>((v >> 49) | ext_bit); // set bit 49-55, with extension
252
// no need to extend since only 64 bits allowed.
253
*(dest + 8) = static_cast<u1>(v >> 56); // set bit 56-63
254
return 9;
255
}
256
257
template <typename T>
258
inline size_t Varint128EncoderImpl::encode(const T* src, size_t len, u1* dest) {
259
assert(dest != NULL, "invariant");
260
assert(len >= 1, "invariant");
261
size_t size = encode(*src, dest);
262
if (len > 1) {
263
for (size_t i = 1; i < len; ++i) {
264
size += encode(*(src + i), dest + size);
265
}
266
}
267
return size;
268
}
269
270
template <typename T>
271
inline size_t Varint128EncoderImpl::encode_padded(T value, u1* dest) {
272
assert(dest != NULL, "invariant");
273
const u8 v = to_u8(value);
274
switch (sizeof(T)) {
275
case 1:
276
dest[0] = static_cast<u1>(v);
277
return 1;
278
case 2:
279
dest[0] = static_cast<u1>(v | 0x80);
280
dest[1] = static_cast<u1>(v >> 7);
281
return 2;
282
case 4:
283
dest[0] = static_cast<u1>(v | 0x80);
284
dest[1] = static_cast<u1>(v >> 7 | 0x80);
285
dest[2] = static_cast<u1>(v >> 14 | 0x80);
286
dest[3] = static_cast<u1>(v >> 21);
287
return 4;
288
case 8:
289
dest[0] = static_cast<u1>(v | 0x80);
290
dest[1] = static_cast<u1>(v >> 7 | 0x80);
291
dest[2] = static_cast<u1>(v >> 14 | 0x80);
292
dest[3] = static_cast<u1>(v >> 21 | 0x80);
293
dest[4] = static_cast<u1>(v >> 28 | 0x80);
294
dest[5] = static_cast<u1>(v >> 35 | 0x80);
295
dest[6] = static_cast<u1>(v >> 42 | 0x80);
296
dest[7] = static_cast<u1>(v >> 49);
297
return 8;
298
default:
299
ShouldNotReachHere();
300
}
301
return 0;
302
}
303
304
305
template <typename T>
306
inline size_t Varint128EncoderImpl::encode_padded(const T* src, size_t len, u1* dest) {
307
assert(dest != NULL, "invariant");
308
assert(len >= 1, "invariant");
309
size_t size = encode_padded(*src, dest);
310
if (len > 1) {
311
for (size_t i = 1; i < len; ++i) {
312
size += encode_padded(*(src + i), dest + size);
313
}
314
}
315
return size;
316
}
317
318
#endif // SHARE_VM_JFR_WRITERS_JFRENCODERS_HPP
319
320