1 /*
2 * Copyright (c) 2022, 2024, 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. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25 package jdk.internal.classfile.impl;
26
27 import java.lang.classfile.Annotation;
28 import java.lang.classfile.Attribute;
29 import java.lang.classfile.AttributeMapper;
30 import java.lang.classfile.AttributedElement;
31 import java.lang.classfile.BufWriter;
32 import java.lang.classfile.ClassReader;
33 import java.lang.classfile.attribute.*;
34 import java.util.List;
35
36 import static java.lang.classfile.Attributes.*;
37
38 public sealed abstract class AbstractAttributeMapper<T extends Attribute<T>>
39 implements AttributeMapper<T> {
40
41 private final String name;
42 private final AttributeMapper.AttributeStability stability;
43 private final boolean allowMultiple;
44
45 protected abstract void writeBody(BufWriter buf, T attr);
46
47 public AbstractAttributeMapper(String name, AttributeMapper.AttributeStability stability) {
48 this(name, stability, false);
49 }
50
51 public AbstractAttributeMapper(String name,
52 AttributeMapper.AttributeStability stability,
53 boolean allowMultiple) {
54 this.name = name;
55 this.stability = stability;
56 this.allowMultiple = allowMultiple;
57 }
58
59 @Override
60 public final String name() {
61 return name;
62 }
63
64 @Override
65 public final void writeAttribute(BufWriter writer, T attr) {
66 BufWriterImpl buf = (BufWriterImpl) writer;
67 buf.writeIndex(attr.attributeName());
68 int lengthIndex = buf.skip(4);
69 writeBody(buf, attr);
70 int written = buf.size() - lengthIndex - 4;
71 buf.patchInt(lengthIndex, written);
72 }
73
74 @Override
75 public AttributeMapper.AttributeStability stability() {
76 return stability;
77 }
78
79 @Override
80 public boolean allowMultiple() {
81 return allowMultiple;
82 }
83
84 @Override
85 public String toString() {
86 return String.format("AttributeMapper[name=%s, allowMultiple=%b, stability=%s]",
87 name, allowMultiple, stability());
88 }
89
90 public static final class AnnotationDefaultMapper extends AbstractAttributeMapper<AnnotationDefaultAttribute> {
91 public static final AnnotationDefaultMapper INSTANCE = new AnnotationDefaultMapper();
92
93 private AnnotationDefaultMapper() {
94 super(NAME_ANNOTATION_DEFAULT, AttributeStability.CP_REFS);
95 }
96
97 @Override
98 public AnnotationDefaultAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
99 return new BoundAttribute.BoundAnnotationDefaultAttr(cf, this, p);
100 }
101
102 @Override
103 protected void writeBody(BufWriter buf, AnnotationDefaultAttribute attr) {
104 AnnotationReader.writeAnnotationValue((BufWriterImpl) buf, attr.defaultValue());
105 }
106 }
107
108 public static final class BootstrapMethodsMapper extends AbstractAttributeMapper<BootstrapMethodsAttribute> {
109 public static final BootstrapMethodsMapper INSTANCE = new BootstrapMethodsMapper();
110
111 private BootstrapMethodsMapper() {
112 super(NAME_BOOTSTRAP_METHODS, AttributeStability.CP_REFS);
113 }
114
115 @Override
116 public BootstrapMethodsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
117 return new BoundAttribute.BoundBootstrapMethodsAttribute(cf, this, p);
118 }
119
120 @Override
121 protected void writeBody(BufWriter buf, BootstrapMethodsAttribute attr) {
122 var b = (BufWriterImpl) buf;
123 b.writeU2(attr.bootstrapMethodsSize());
124 for (var bsm : attr.bootstrapMethods()) {
125 ((BootstrapMethodEntryImpl) bsm).writeTo(b);
126 }
127 }
128 }
129
130 public static final class CharacterRangeTableMapper extends AbstractAttributeMapper<CharacterRangeTableAttribute> {
131 public static final CharacterRangeTableMapper INSTANCE = new CharacterRangeTableMapper();
132
133 private CharacterRangeTableMapper() {
134 super(NAME_CHARACTER_RANGE_TABLE, AttributeStability.LABELS, true);
135 }
136
137 @Override
138 public CharacterRangeTableAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
139 return new BoundAttribute.BoundCharacterRangeTableAttribute(cf, this, p);
140 }
141
142 @Override
143 protected void writeBody(BufWriter bufWriter, CharacterRangeTableAttribute attr) {
144 List<CharacterRangeInfo> ranges = attr.characterRangeTable();
145 BufWriterImpl buf = (BufWriterImpl) bufWriter;
146 buf.writeU2(ranges.size());
147 for (CharacterRangeInfo info : ranges) {
148 buf.writeU2U2(info.startPc(), info.endPc());
149 buf.writeIntInt(info.characterRangeStart(), info.characterRangeEnd());
150 buf.writeU2(info.flags());
151 }
152 }
153 }
154
155 public static final class CodeMapper extends AbstractAttributeMapper<CodeAttribute> {
156 public static final CodeMapper INSTANCE = new CodeMapper();
157
158 private CodeMapper() {
159 super(NAME_CODE, AttributeStability.CP_REFS);
160 }
161
162 @Override
163 public CodeAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
164 return new CodeImpl(e, cf, this, p);
165 }
166
167 @Override
168 protected void writeBody(BufWriter buf, CodeAttribute attr) {
169 throw new UnsupportedOperationException("Code attribute does not support direct write");
170 }
171 }
172
173 public static final class CompilationIDMapper extends AbstractAttributeMapper<CompilationIDAttribute> {
174 public static final CompilationIDMapper INSTANCE = new CompilationIDMapper();
175
176 private CompilationIDMapper() {
177 super(NAME_COMPILATION_ID, AttributeStability.CP_REFS);
178 }
179
180 @Override
181 public CompilationIDAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
182 return new BoundAttribute.BoundCompilationIDAttribute(cf, this, p);
183 }
184
185 @Override
186 protected void writeBody(BufWriter buf, CompilationIDAttribute attr) {
187 buf.writeIndex(attr.compilationId());
188 }
189 }
190
191 public static final class ConstantValueMapper extends AbstractAttributeMapper<ConstantValueAttribute> {
192 public static final ConstantValueMapper INSTANCE = new ConstantValueMapper();
193
194 private ConstantValueMapper() {
195 super(NAME_CONSTANT_VALUE, AttributeStability.CP_REFS);
196 }
197
198 @Override
199 public ConstantValueAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
200 return new BoundAttribute.BoundConstantValueAttribute(cf, this, p);
201 }
202
203 @Override
204 protected void writeBody(BufWriter buf, ConstantValueAttribute attr) {
205 buf.writeIndex(attr.constant());
206 }
207 }
208
209 public static final class DeprecatedMapper extends AbstractAttributeMapper<DeprecatedAttribute> {
210 public static final DeprecatedMapper INSTANCE = new DeprecatedMapper();
211
212 private DeprecatedMapper() {
213 super(NAME_DEPRECATED, AttributeStability.STATELESS, true);
214 }
215
216 @Override
217 public DeprecatedAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
218 return new BoundAttribute.BoundDeprecatedAttribute(cf, this, p);
219 }
220
221 @Override
222 protected void writeBody(BufWriter buf, DeprecatedAttribute attr) {
223 // empty
224 }
225 }
226
227 public static final class EnclosingMethodMapper extends AbstractAttributeMapper<EnclosingMethodAttribute> {
228 public static final EnclosingMethodMapper INSTANCE = new EnclosingMethodMapper();
229
230 private EnclosingMethodMapper() {
231 super(NAME_ENCLOSING_METHOD, AttributeStability.CP_REFS);
232 }
233
234 @Override
235 public EnclosingMethodAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
236 return new BoundAttribute.BoundEnclosingMethodAttribute(cf, this, p);
237 }
238
239 @Override
240 protected void writeBody(BufWriter bufWriter, EnclosingMethodAttribute attr) {
241 BufWriterImpl buf = (BufWriterImpl) bufWriter;
242 buf.writeU2U2(buf.cpIndex(attr.enclosingClass()),
243 buf.cpIndexOrZero(attr.enclosingMethod().orElse(null)));
244 }
245 }
246
247 public static final class ExceptionsMapper extends AbstractAttributeMapper<ExceptionsAttribute> {
248 public static final ExceptionsMapper INSTANCE = new ExceptionsMapper();
249
250 private ExceptionsMapper() {
251 super(NAME_EXCEPTIONS, AttributeStability.CP_REFS);
252 }
253
254 @Override
255 public ExceptionsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
256 return new BoundAttribute.BoundExceptionsAttribute(cf, this, p);
257 }
258
259 @Override
260 protected void writeBody(BufWriter buf, ExceptionsAttribute attr) {
261 Util.writeListIndices(buf, attr.exceptions());
262 }
263 }
264
265 public static final class InnerClassesMapper extends AbstractAttributeMapper<InnerClassesAttribute> {
266 public static final InnerClassesMapper INSTANCE = new InnerClassesMapper();
267
268 private InnerClassesMapper() {
269 super(NAME_INNER_CLASSES, AttributeStability.CP_REFS);
270 }
271
272 @Override
273 public InnerClassesAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
274 return new BoundAttribute.BoundInnerClassesAttribute(cf, this, p);
275 }
276
277 @Override
278 protected void writeBody(BufWriter bufWriter, InnerClassesAttribute attr) {
279 List<InnerClassInfo> classes = attr.classes();
280 BufWriterImpl buf = (BufWriterImpl) bufWriter;
281 buf.writeU2(classes.size());
282 for (InnerClassInfo ic : classes) {
283 buf.writeU2U2U2(buf.cpIndex(ic.innerClass()),
284 buf.cpIndexOrZero(ic.outerClass().orElse(null)),
285 buf.cpIndexOrZero(ic.innerName().orElse(null)));
286 buf.writeU2(ic.flagsMask());
287 }
288 }
289 }
290
291 public static final class LineNumberTableMapper extends AbstractAttributeMapper<LineNumberTableAttribute> {
292 public static final LineNumberTableMapper INSTANCE = new LineNumberTableMapper();
293
294 private LineNumberTableMapper() {
295 super(NAME_LINE_NUMBER_TABLE, AttributeStability.LABELS, true);
296 }
297
298 @Override
299 public LineNumberTableAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
300 return new BoundAttribute.BoundLineNumberTableAttribute(cf, this, p);
301 }
302
303 @Override
304 protected void writeBody(BufWriter bufWriter, LineNumberTableAttribute attr) {
305 List<LineNumberInfo> lines = attr.lineNumbers();
306 BufWriterImpl buf = (BufWriterImpl) bufWriter;
307 buf.writeU2(lines.size());
308 for (LineNumberInfo line : lines) {
309 buf.writeU2U2(line.startPc(), line.lineNumber());
310 }
311 }
312 }
313
314 public static final class LocalVariableTableMapper extends AbstractAttributeMapper<LocalVariableTableAttribute> {
315 public static final LocalVariableTableMapper INSTANCE = new LocalVariableTableMapper();
316
317 private LocalVariableTableMapper() {
318 super(NAME_LOCAL_VARIABLE_TABLE, AttributeStability.LABELS, true);
319 }
320
321 @Override
322 public LocalVariableTableAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
323 return new BoundAttribute.BoundLocalVariableTableAttribute(e, cf, this, p);
324 }
325
326 @Override
327 protected void writeBody(BufWriter bufWriter, LocalVariableTableAttribute attr) {
328 List<LocalVariableInfo> infos = attr.localVariables();
329 BufWriterImpl buf = (BufWriterImpl) bufWriter;
330 buf.writeU2(infos.size());
331 for (LocalVariableInfo info : infos) {
332 buf.writeU2U2(info.startPc(), info.length());
333 buf.writeU2U2U2(buf.cpIndex(info.name()), buf.cpIndex(info.type()), info.slot());
334 }
335 }
336 }
337
338 public static final class LocalVariableTypeTableMapper extends AbstractAttributeMapper<LocalVariableTypeTableAttribute> {
339 public static final LocalVariableTypeTableMapper INSTANCE = new LocalVariableTypeTableMapper();
340
341 private LocalVariableTypeTableMapper() {
342 super(NAME_LOCAL_VARIABLE_TYPE_TABLE, AttributeStability.LABELS, true);
343 }
344
345 @Override
346 public LocalVariableTypeTableAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
347 return new BoundAttribute.BoundLocalVariableTypeTableAttribute(e, cf, this, p);
348 }
349
350 @Override
351 protected void writeBody(BufWriter bufWriter, LocalVariableTypeTableAttribute attr) {
352 List<LocalVariableTypeInfo> infos = attr.localVariableTypes();
353 BufWriterImpl buf = (BufWriterImpl) bufWriter;
354 buf.writeU2(infos.size());
355 for (LocalVariableTypeInfo info : infos) {
356 buf.writeU2U2(info.startPc(), info.length());
357 buf.writeU2U2U2(buf.cpIndex(info.name()), buf.cpIndex(info.signature()), info.slot());
358 }
359 }
360 }
361
362 public static final class MethodParametersMapper extends AbstractAttributeMapper<MethodParametersAttribute> {
363 public static final MethodParametersMapper INSTANCE = new MethodParametersMapper();
364
365 private MethodParametersMapper() {
366 super(NAME_METHOD_PARAMETERS, AttributeStability.CP_REFS);
367 }
368
369 @Override
370 public MethodParametersAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
371 return new BoundAttribute.BoundMethodParametersAttribute(cf, this, p);
372 }
373
374 @Override
375 protected void writeBody(BufWriter bufWriter, MethodParametersAttribute attr) {
376 List<MethodParameterInfo> parameters = attr.parameters();
377 BufWriterImpl buf = (BufWriterImpl) bufWriter;
378 buf.writeU1(parameters.size());
379 for (MethodParameterInfo info : parameters) {
380 buf.writeU2U2(buf.cpIndexOrZero(info.name().orElse(null)),
381 info.flagsMask());
382 }
383 }
384 }
385
386 public static final class ModuleMapper extends AbstractAttributeMapper<ModuleAttribute> {
387 public static final ModuleMapper INSTANCE = new ModuleMapper();
388
389 private ModuleMapper() {
390 super(NAME_MODULE, AttributeStability.CP_REFS);
391 }
392
393 @Override
394 public ModuleAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
395 return new BoundAttribute.BoundModuleAttribute(cf, this, p);
396 }
397
398 @Override
399 protected void writeBody(BufWriter bufWriter, ModuleAttribute attr) {
400 BufWriterImpl buf = (BufWriterImpl) bufWriter;
401 buf.writeU2U2U2(buf.cpIndex(attr.moduleName()),
402 attr.moduleFlagsMask(),
403 buf.cpIndexOrZero(attr.moduleVersion().orElse(null)));
404 buf.writeU2(attr.requires().size());
405 for (ModuleRequireInfo require : attr.requires()) {
406 buf.writeU2U2U2(buf.cpIndex(require.requires()),
407 require.requiresFlagsMask(),
408 buf.cpIndexOrZero(require.requiresVersion().orElse(null)));
409 }
410 buf.writeU2(attr.exports().size());
411 for (ModuleExportInfo export : attr.exports()) {
412 buf.writeU2U2(buf.cpIndex(export.exportedPackage()),
413 export.exportsFlagsMask());
414 Util.writeListIndices(buf, export.exportsTo());
415 }
416 buf.writeU2(attr.opens().size());
417 for (ModuleOpenInfo open : attr.opens()) {
418 buf.writeU2U2(buf.cpIndex(open.openedPackage()),
419 open.opensFlagsMask());
420 Util.writeListIndices(buf, open.opensTo());
421 }
422 Util.writeListIndices(buf, attr.uses());
423 buf.writeU2(attr.provides().size());
424 for (ModuleProvideInfo provide : attr.provides()) {
425 buf.writeIndex(provide.provides());
426 Util.writeListIndices(buf, provide.providesWith());
427 }
428 }
429 }
430
431 public static final class ModuleHashesMapper extends AbstractAttributeMapper<ModuleHashesAttribute> {
432 public static final ModuleHashesMapper INSTANCE = new ModuleHashesMapper();
433
434 private ModuleHashesMapper() {
435 super(NAME_MODULE_HASHES, AttributeStability.CP_REFS);
436 }
437
438 @Override
439 public ModuleHashesAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
440 return new BoundAttribute.BoundModuleHashesAttribute(cf, this, p);
441 }
442
443 @Override
444 protected void writeBody(BufWriter bufWriter, ModuleHashesAttribute attr) {
445 List<ModuleHashInfo> hashes = attr.hashes();
446 BufWriterImpl buf = (BufWriterImpl) bufWriter;
447 buf.writeU2U2(buf.cpIndex(attr.algorithm()), hashes.size());
448 for (ModuleHashInfo hash : hashes) {
449 buf.writeU2U2(buf.cpIndex(hash.moduleName()),
450 hash.hash().length);
451 buf.writeBytes(hash.hash());
452 }
453 }
454 }
455
456 public static final class ModuleMainClassMapper extends AbstractAttributeMapper<ModuleMainClassAttribute> {
457 public static final ModuleMainClassMapper INSTANCE = new ModuleMainClassMapper();
458
459 private ModuleMainClassMapper() {
460 super(NAME_MODULE_MAIN_CLASS, AttributeStability.CP_REFS);
461 }
462
463 @Override
464 public ModuleMainClassAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
465 return new BoundAttribute.BoundModuleMainClassAttribute(cf, this, p);
466 }
467
468 @Override
469 protected void writeBody(BufWriter buf, ModuleMainClassAttribute attr) {
470 buf.writeIndex(attr.mainClass());
471 }
472 }
473
474 public static final class ModulePackagesMapper extends AbstractAttributeMapper<ModulePackagesAttribute> {
475 public static final ModulePackagesMapper INSTANCE = new ModulePackagesMapper();
476
477 private ModulePackagesMapper() {
478 super(NAME_MODULE_PACKAGES, AttributeStability.CP_REFS);
479 }
480
481 @Override
482 public ModulePackagesAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
483 return new BoundAttribute.BoundModulePackagesAttribute(cf, this, p);
484 }
485
486 @Override
487 protected void writeBody(BufWriter buf, ModulePackagesAttribute attr) {
488 Util.writeListIndices(buf, attr.packages());
489 }
490 }
491
492 public static final class ModuleResolutionMapper extends AbstractAttributeMapper<ModuleResolutionAttribute> {
493 public static final ModuleResolutionMapper INSTANCE = new ModuleResolutionMapper();
494
495 private ModuleResolutionMapper() {
496 super(NAME_MODULE_RESOLUTION, AttributeStability.STATELESS);
497 }
498
499 @Override
500 public ModuleResolutionAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
501 return new BoundAttribute.BoundModuleResolutionAttribute(cf, this, p);
502 }
503
504 @Override
505 protected void writeBody(BufWriter buf, ModuleResolutionAttribute attr) {
506 buf.writeU2(attr.resolutionFlags());
507 }
508 }
509
510 public static final class ModuleTargetMapper extends AbstractAttributeMapper<ModuleTargetAttribute> {
511 public static final ModuleTargetMapper INSTANCE = new ModuleTargetMapper();
512
513 private ModuleTargetMapper() {
514 super(NAME_MODULE_TARGET, AttributeStability.CP_REFS);
515 }
516
517 @Override
518 public ModuleTargetAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
519 return new BoundAttribute.BoundModuleTargetAttribute(cf, this, p);
520 }
521
522 @Override
523 protected void writeBody(BufWriter buf, ModuleTargetAttribute attr) {
524 buf.writeIndex(attr.targetPlatform());
525 }
526 }
527
528 public static final class NestHostMapper extends AbstractAttributeMapper<NestHostAttribute> {
529 public static final NestHostMapper INSTANCE = new NestHostMapper();
530
531 private NestHostMapper() {
532 super(NAME_NEST_HOST, AttributeStability.CP_REFS);
533 }
534
535 @Override
536 public NestHostAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
537 return new BoundAttribute.BoundNestHostAttribute(cf, this, p);
538 }
539
540 @Override
541 protected void writeBody(BufWriter buf, NestHostAttribute attr) {
542 buf.writeIndex(attr.nestHost());
543 }
544 }
545
546 public static final class NestMembersMapper extends AbstractAttributeMapper<NestMembersAttribute> {
547 public static final NestMembersMapper INSTANCE = new NestMembersMapper();
548
549 private NestMembersMapper() {
550 super(NAME_NEST_MEMBERS, AttributeStability.CP_REFS);
551 }
552
553 @Override
554 public NestMembersAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
555 return new BoundAttribute.BoundNestMembersAttribute(cf, this, p);
556 }
557
558 @Override
559 protected void writeBody(BufWriter buf, NestMembersAttribute attr) {
560 Util.writeListIndices(buf, attr.nestMembers());
561 }
562 }
563
564 public static final class PermittedSubclassesMapper extends AbstractAttributeMapper<PermittedSubclassesAttribute> {
565 public static final PermittedSubclassesMapper INSTANCE = new PermittedSubclassesMapper();
566
567 private PermittedSubclassesMapper() {
568 super(NAME_PERMITTED_SUBCLASSES, AttributeStability.CP_REFS);
569 }
570
571 @Override
572 public PermittedSubclassesAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
573 return new BoundAttribute.BoundPermittedSubclassesAttribute(cf, this, p);
574 }
575
576 @Override
577 protected void writeBody(BufWriter buf, PermittedSubclassesAttribute attr) {
578 Util.writeListIndices(buf, attr.permittedSubclasses());
579 }
580 }
581
582 public static final class RecordMapper extends AbstractAttributeMapper<RecordAttribute> {
583 public static final RecordMapper INSTANCE = new RecordMapper();
584
585 private RecordMapper() {
586 super(NAME_RECORD, AttributeStability.CP_REFS);
587 }
588
589 @Override
590 public RecordAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
591 return new BoundAttribute.BoundRecordAttribute(cf, this, p);
592 }
593
594 @Override
595 protected void writeBody(BufWriter bufWriter, RecordAttribute attr) {
596 List<RecordComponentInfo> components = attr.components();
597 BufWriterImpl buf = (BufWriterImpl) bufWriter;
598 buf.writeU2(components.size());
599 for (RecordComponentInfo info : components) {
600 buf.writeU2U2(buf.cpIndex(info.name()),
601 buf.cpIndex(info.descriptor()));
602 Util.writeAttributes(buf, info.attributes());
603 }
604 }
605 }
606
607 public static final class RuntimeInvisibleAnnotationsMapper extends AbstractAttributeMapper<RuntimeInvisibleAnnotationsAttribute> {
608 public static final RuntimeInvisibleAnnotationsMapper INSTANCE = new RuntimeInvisibleAnnotationsMapper();
609
610 private RuntimeInvisibleAnnotationsMapper() {
611 super(NAME_RUNTIME_INVISIBLE_ANNOTATIONS, AttributeStability.CP_REFS);
612 }
613
614 @Override
615 public RuntimeInvisibleAnnotationsAttribute readAttribute(AttributedElement enclosing, ClassReader cf, int pos) {
616 return new BoundAttribute.BoundRuntimeInvisibleAnnotationsAttribute(cf, pos);
617 }
618
619 @Override
620 protected void writeBody(BufWriter buf, RuntimeInvisibleAnnotationsAttribute attr) {
621 AnnotationReader.writeAnnotations(buf, attr.annotations());
622 }
623 }
624
625 public static final class RuntimeInvisibleParameterAnnotationsMapper extends AbstractAttributeMapper<RuntimeInvisibleParameterAnnotationsAttribute> {
626 public static final RuntimeInvisibleParameterAnnotationsMapper INSTANCE = new RuntimeInvisibleParameterAnnotationsMapper();
627
628 private RuntimeInvisibleParameterAnnotationsMapper() {
629 super(NAME_RUNTIME_INVISIBLE_PARAMETER_ANNOTATIONS, AttributeStability.CP_REFS);
630 }
631
632 @Override
633 public RuntimeInvisibleParameterAnnotationsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
634 return new BoundAttribute.BoundRuntimeInvisibleParameterAnnotationsAttribute(cf, this, p);
635 }
636
637 @Override
638 protected void writeBody(BufWriter buf, RuntimeInvisibleParameterAnnotationsAttribute attr) {
639 List<List<Annotation>> lists = attr.parameterAnnotations();
640 buf.writeU1(lists.size());
641 for (List<Annotation> list : lists)
642 AnnotationReader.writeAnnotations(buf, list);
643 }
644 }
645
646 public static final class RuntimeInvisibleTypeAnnotationsMapper extends AbstractAttributeMapper<RuntimeInvisibleTypeAnnotationsAttribute> {
647 public static final RuntimeInvisibleTypeAnnotationsMapper INSTANCE = new RuntimeInvisibleTypeAnnotationsMapper();
648
649 private RuntimeInvisibleTypeAnnotationsMapper() {
650 super(NAME_RUNTIME_INVISIBLE_TYPE_ANNOTATIONS, AttributeStability.UNSTABLE);
651 }
652
653 @Override
654 public RuntimeInvisibleTypeAnnotationsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
655 return new BoundAttribute.BoundRuntimeInvisibleTypeAnnotationsAttribute(e, cf, this, p);
656 }
657
658 @Override
659 protected void writeBody(BufWriter buf, RuntimeInvisibleTypeAnnotationsAttribute attr) {
660 AnnotationReader.writeTypeAnnotations(buf, attr.annotations());
661 }
662 }
663
664 public static final class RuntimeVisibleAnnotationsMapper extends AbstractAttributeMapper<RuntimeVisibleAnnotationsAttribute> {
665 public static final RuntimeVisibleAnnotationsMapper INSTANCE = new RuntimeVisibleAnnotationsMapper();
666
667 private RuntimeVisibleAnnotationsMapper() {
668 super(NAME_RUNTIME_VISIBLE_ANNOTATIONS, AttributeStability.CP_REFS);
669 }
670
671 @Override
672 public RuntimeVisibleAnnotationsAttribute readAttribute(AttributedElement enclosing, ClassReader cf, int pos) {
673 return new BoundAttribute.BoundRuntimeVisibleAnnotationsAttribute(cf, pos);
674 }
675
676 @Override
677 protected void writeBody(BufWriter buf, RuntimeVisibleAnnotationsAttribute attr) {
678 AnnotationReader.writeAnnotations(buf, attr.annotations());
679 }
680 }
681
682 public static final class RuntimeVisibleParameterAnnotationsMapper extends AbstractAttributeMapper<RuntimeVisibleParameterAnnotationsAttribute> {
683 public static final RuntimeVisibleParameterAnnotationsMapper INSTANCE = new RuntimeVisibleParameterAnnotationsMapper();
684
685 private RuntimeVisibleParameterAnnotationsMapper() {
686 super(NAME_RUNTIME_VISIBLE_PARAMETER_ANNOTATIONS, AttributeStability.CP_REFS);
687 }
688
689 @Override
690 public RuntimeVisibleParameterAnnotationsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
691 return new BoundAttribute.BoundRuntimeVisibleParameterAnnotationsAttribute(cf, this, p);
692 }
693
694 @Override
695 protected void writeBody(BufWriter buf, RuntimeVisibleParameterAnnotationsAttribute attr) {
696 List<List<Annotation>> lists = attr.parameterAnnotations();
697 buf.writeU1(lists.size());
698 for (List<Annotation> list : lists)
699 AnnotationReader.writeAnnotations(buf, list);
700 }
701 }
702
703 public static final class RuntimeVisibleTypeAnnotationsMapper extends AbstractAttributeMapper<RuntimeVisibleTypeAnnotationsAttribute> {
704 public static final RuntimeVisibleTypeAnnotationsMapper INSTANCE = new RuntimeVisibleTypeAnnotationsMapper();
705
706 private RuntimeVisibleTypeAnnotationsMapper() {
707 super(NAME_RUNTIME_VISIBLE_TYPE_ANNOTATIONS, AttributeStability.UNSTABLE);
708 }
709
710 @Override
711 public RuntimeVisibleTypeAnnotationsAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
712 return new BoundAttribute.BoundRuntimeVisibleTypeAnnotationsAttribute(e, cf, this, p);
713 }
714
715 @Override
716 protected void writeBody(BufWriter buf, RuntimeVisibleTypeAnnotationsAttribute attr) {
717 AnnotationReader.writeTypeAnnotations(buf, attr.annotations());
718 }
719 }
720
721 public static final class SignatureMapper extends AbstractAttributeMapper<SignatureAttribute> {
722 public static final SignatureMapper INSTANCE = new SignatureMapper();
723
724 private SignatureMapper() {
725 super(NAME_SIGNATURE, AttributeStability.CP_REFS);
726 }
727
728 @Override
729 public SignatureAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
730 return new BoundAttribute.BoundSignatureAttribute(cf, this, p);
731 }
732
733 @Override
734 protected void writeBody(BufWriter buf, SignatureAttribute attr) {
735 buf.writeIndex(attr.signature());
736 }
737 }
738
739 public static final class SourceDebugExtensionMapper extends AbstractAttributeMapper<SourceDebugExtensionAttribute> {
740 public static final SourceDebugExtensionMapper INSTANCE = new SourceDebugExtensionMapper();
741
742 private SourceDebugExtensionMapper() {
743 super(NAME_SOURCE_DEBUG_EXTENSION, AttributeStability.STATELESS);
744 }
745
746 @Override
747 public SourceDebugExtensionAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
748 return new BoundAttribute.BoundSourceDebugExtensionAttribute(cf, this, p);
749 }
750
751 @Override
752 protected void writeBody(BufWriter buf, SourceDebugExtensionAttribute attr) {
753 buf.writeBytes(attr.contents());
754 }
755 }
756
757 public static final class SourceFileMapper extends AbstractAttributeMapper<SourceFileAttribute> {
758 public static final SourceFileMapper INSTANCE = new SourceFileMapper();
759
760 private SourceFileMapper() {
761 super(NAME_SOURCE_FILE, AttributeStability.CP_REFS);
762 }
763
764 @Override
765 public SourceFileAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
766 return new BoundAttribute.BoundSourceFileAttribute(cf, this, p);
767 }
768
769 @Override
770 protected void writeBody(BufWriter buf, SourceFileAttribute attr) {
771 buf.writeIndex(attr.sourceFile());
772 }
773 }
774
775 public static final class SourceIDMapper extends AbstractAttributeMapper<SourceIDAttribute> {
776 public static final SourceIDMapper INSTANCE = new SourceIDMapper();
777
778 private SourceIDMapper() {
779 super(NAME_SOURCE_ID, AttributeStability.CP_REFS);
780 }
781
782 @Override
783 public SourceIDAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
784 return new BoundAttribute.BoundSourceIDAttribute(cf, this, p);
785 }
786
787 @Override
788 protected void writeBody(BufWriter buf, SourceIDAttribute attr) {
789 buf.writeIndex(attr.sourceId());
790 }
791 }
792
793 public static final class StackMapTableMapper extends AbstractAttributeMapper<StackMapTableAttribute> {
794 public static final StackMapTableMapper INSTANCE = new StackMapTableMapper();
795
796 private StackMapTableMapper() {
797 super(NAME_STACK_MAP_TABLE, AttributeStability.LABELS);
798 }
799
800 @Override
801 public StackMapTableAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
802 return new BoundAttribute.BoundStackMapTableAttribute((CodeImpl)e, cf, this, p);
803 }
804
805 @Override
806 protected void writeBody(BufWriter b, StackMapTableAttribute attr) {
807 StackMapDecoder.writeFrames(b, attr.entries());
808 }
809 }
810
811 public static final class SyntheticMapper extends AbstractAttributeMapper<SyntheticAttribute> {
812 public static final SyntheticMapper INSTANCE = new SyntheticMapper();
813
814 private SyntheticMapper() {
815 super(NAME_SYNTHETIC, AttributeStability.STATELESS, true);
816 }
817
818 @Override
819 public SyntheticAttribute readAttribute(AttributedElement e, ClassReader cf, int p) {
820 return new BoundAttribute.BoundSyntheticAttribute(cf, this, p);
821 }
822
823 @Override
824 protected void writeBody(BufWriter buf, SyntheticAttribute attr) {
825 // empty
826 }
827 }
828 }