001/*
002 * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
003 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
004 *
005 * This code is free software; you can redistribute it and/or modify it
006 * under the terms of the GNU General Public License version 2 only, as
007 * published by the Free Software Foundation.
008 *
009 * This code is distributed in the hope that it will be useful, but WITHOUT
010 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
011 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
012 * version 2 for more details (a copy is included in the LICENSE file that
013 * accompanied this code).
014 *
015 * You should have received a copy of the GNU General Public License version
016 * 2 along with this work; if not, write to the Free Software Foundation,
017 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
018 *
019 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
020 * or visit www.oracle.com if you need additional information or have any
021 * questions.
022 */
023package jdk.internal.jvmci.meta;
024
025import static java.lang.reflect.Modifier.*;
026
027import java.lang.reflect.*;
028
029/**
030 * A Java element (i.e., a class, interface, field or method) that is described by a set of Java
031 * language {@linkplain #getModifiers() modifiers}.
032 */
033public interface ModifiersProvider {
034    int BRIDGE = MetaUtil.getNonPublicModifierStaticField("BRIDGE");
035    int VARARGS = MetaUtil.getNonPublicModifierStaticField("VARARGS");
036    int SYNTHETIC = MetaUtil.getNonPublicModifierStaticField("SYNTHETIC");
037    int ANNOTATION = MetaUtil.getNonPublicModifierStaticField("ANNOTATION");
038    int ENUM = MetaUtil.getNonPublicModifierStaticField("ENUM");
039    int MANDATED = MetaUtil.getNonPublicModifierStaticField("MANDATED");
040
041    /**
042     * Returns the Java Virtual Machine modifiers for this element. Note that this can differ from
043     * standard Java Reflection modifiers. For example at the JVM level, classes (
044     * {@link ResolvedJavaType}) can not be private or protected.
045     */
046    int getModifiers();
047
048    /**
049     * @see Modifier#isInterface(int)
050     */
051    default boolean isInterface() {
052        return Modifier.isInterface(getModifiers());
053    }
054
055    /**
056     * @see Modifier#isSynchronized(int)
057     */
058    default boolean isSynchronized() {
059        return Modifier.isSynchronized(getModifiers());
060    }
061
062    /**
063     * @see Modifier#isStatic(int)
064     */
065    default boolean isStatic() {
066        return Modifier.isStatic(getModifiers());
067    }
068
069    /**
070     * The setting of the final modifier bit for types is somewhat confusing, so don't export
071     * isFinal by default. Subclasses like {@link ResolvedJavaField} and {@link ResolvedJavaMethod}
072     * can export it as isFinal, but {@link ResolvedJavaType} can provide a more sensible equivalent
073     * like {@link ResolvedJavaType#isLeaf}.
074     *
075     * @see Modifier#isFinal(int)
076     */
077    default boolean isFinalFlagSet() {
078        return Modifier.isFinal(getModifiers());
079    }
080
081    /**
082     * @see Modifier#isPublic(int)
083     */
084    default boolean isPublic() {
085        return Modifier.isPublic(getModifiers());
086    }
087
088    /**
089     * Determines if this element is neither {@linkplain #isPublic() public},
090     * {@linkplain #isProtected() protected} nor {@linkplain #isPrivate() private}.
091     */
092    default boolean isPackagePrivate() {
093        return ((PUBLIC | PROTECTED | PRIVATE) & getModifiers()) == 0;
094    }
095
096    /**
097     * @see Modifier#isPrivate(int)
098     */
099    default boolean isPrivate() {
100        return Modifier.isPrivate(getModifiers());
101    }
102
103    /**
104     * @see Modifier#isProtected(int)
105     */
106    default boolean isProtected() {
107        return Modifier.isProtected(getModifiers());
108    }
109
110    /**
111     * @see Modifier#isTransient(int)
112     */
113    default boolean isTransient() {
114        return Modifier.isTransient(getModifiers());
115    }
116
117    /**
118     * @see Modifier#isStrict(int)
119     */
120    default boolean isStrict() {
121        return Modifier.isStrict(getModifiers());
122    }
123
124    /**
125     * @see Modifier#isVolatile(int)
126     */
127    default boolean isVolatile() {
128        return Modifier.isVolatile(getModifiers());
129    }
130
131    /**
132     * @see Modifier#isNative(int)
133     */
134    default boolean isNative() {
135        return Modifier.isNative(getModifiers());
136    }
137
138    /**
139     * @see Modifier#isAbstract(int)
140     */
141    default boolean isAbstract() {
142        return Modifier.isAbstract(getModifiers());
143    }
144
145    /**
146     * Checks that the method is concrete and not abstract.
147     *
148     * @return whether the method is a concrete method
149     */
150    default boolean isConcrete() {
151        return !isAbstract();
152    }
153
154    static int jvmClassModifiers() {
155        // no SUPER
156        return PUBLIC | FINAL | INTERFACE | ABSTRACT | ANNOTATION | ENUM | SYNTHETIC;
157    }
158
159    static int jvmMethodModifiers() {
160        return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | SYNCHRONIZED | BRIDGE | VARARGS | NATIVE | ABSTRACT | STRICT | SYNTHETIC;
161    }
162
163    static int jvmFieldModifiers() {
164        return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | VOLATILE | TRANSIENT | ENUM | SYNTHETIC;
165    }
166}