1 /******************************************************************************* 2 * Copyright (c) 2013 Jesper Steen Moeller and others. 3 * 4 * This program and the accompanying materials 5 * are made available under the terms of the Eclipse Public License 2.0 6 * which accompanies this distribution, and is available at 7 * https://www.eclipse.org/legal/epl-2.0/ 8 * 9 * SPDX-License-Identifier: EPL-2.0 10 * 11 * Contributors: 12 * Jesper Steen Moeller - initial API and implementation 13 *******************************************************************************/ 14 15 package org.eclipse.jdt.internal.core.util; 16 17 import org.eclipse.jdt.core.util.ClassFormatException; 18 import org.eclipse.jdt.core.util.IConstantPool; 19 import org.eclipse.jdt.core.util.IConstantPoolConstant; 20 import org.eclipse.jdt.core.util.IConstantPoolEntry; 21 import org.eclipse.jdt.core.util.IMethodParametersAttribute; 22 23 /** 24 * @since 3.10 25 */ 26 public class MethodParametersAttribute extends ClassFileAttribute implements IMethodParametersAttribute { 27 28 private static final char[][] NO_NAMES = new char[0][]; 29 private static final short[] NO_ACCES_FLAGS = new short[0]; 30 31 private final int numberOfEntries; 32 private final char[][] names; 33 private final short[] accessFlags; 34 35 MethodParametersAttribute(byte[] classFileBytes, IConstantPool constantPool, int offset)36 MethodParametersAttribute(byte[] classFileBytes, IConstantPool constantPool, int offset) throws ClassFormatException { 37 super(classFileBytes, constantPool, offset); 38 39 final int length = u1At(classFileBytes, 6, offset); 40 this.numberOfEntries = length; 41 if (length != 0) { 42 int readOffset = offset + 7; 43 this.names = new char[length][]; 44 this.accessFlags = new short[length]; 45 for (int i = 0; i < length; i++) { 46 int nameIndex = u2At(classFileBytes, 0, readOffset); 47 int mask = u2At(classFileBytes, 2, readOffset); 48 readOffset += 4; 49 if (nameIndex != 0) { 50 IConstantPoolEntry constantPoolEntry = constantPool.decodeEntry(nameIndex); 51 if (constantPoolEntry.getKind() != IConstantPoolConstant.CONSTANT_Utf8) { 52 throw new ClassFormatException(ClassFormatException.INVALID_CONSTANT_POOL_ENTRY); 53 } 54 this.names[i] = constantPoolEntry.getUtf8Value(); 55 } else { 56 this.names[i] = null; 57 } 58 this.accessFlags[i] = (short) (mask & 0xFFFF); 59 } 60 } else { 61 this.names = NO_NAMES; 62 this.accessFlags = NO_ACCES_FLAGS; 63 } 64 } 65 66 @Override getMethodParameterLength()67 public int getMethodParameterLength() { 68 return this.numberOfEntries; 69 } 70 71 @Override getParameterName(int i)72 public char[] getParameterName(int i) { 73 return this.names[i]; 74 } 75 76 @Override getAccessFlags(int i)77 public short getAccessFlags(int i) { 78 return this.accessFlags[i]; 79 } 80 } 81