• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.tools.metalava.model
18 
19 open class DefaultModifierList(
20     override val codebase: Codebase,
21     protected var flags: Int = PACKAGE_PRIVATE,
22     protected open var annotations: MutableList<AnnotationItem>? = null
23 ) : MutableModifierList {
24     private lateinit var owner: Item
25 
setnull26     private operator fun set(mask: Int, set: Boolean) {
27         flags = if (set) {
28             flags or mask
29         } else {
30             flags and mask.inv()
31         }
32     }
33 
isSetnull34     private fun isSet(mask: Int): Boolean {
35         return flags and mask != 0
36     }
37 
annotationsnull38     override fun annotations(): List<AnnotationItem> {
39         return annotations ?: emptyList()
40     }
41 
ownernull42     override fun owner(): Item {
43         return owner
44     }
45 
setOwnernull46     fun setOwner(owner: Item) {
47         this.owner = owner
48     }
49 
getVisibilityLevelnull50     override fun getVisibilityLevel(): VisibilityLevel {
51         val visibilityFlags = flags and VISIBILITY_MASK
52         val levels = VISIBILITY_LEVEL_ENUMS
53         if (visibilityFlags >= levels.size) {
54             throw IllegalStateException(
55                 "Visibility flags are invalid, expected value in range [0, " + levels.size + ") got " + visibilityFlags
56             )
57         }
58         return levels[visibilityFlags]
59     }
60 
isPublicnull61     override fun isPublic(): Boolean {
62         return getVisibilityLevel() == VisibilityLevel.PUBLIC
63     }
64 
isProtectednull65     override fun isProtected(): Boolean {
66         return getVisibilityLevel() == VisibilityLevel.PROTECTED
67     }
68 
isPrivatenull69     override fun isPrivate(): Boolean {
70         return getVisibilityLevel() == VisibilityLevel.PRIVATE
71     }
72 
isStaticnull73     override fun isStatic(): Boolean {
74         return isSet(STATIC)
75     }
76 
isAbstractnull77     override fun isAbstract(): Boolean {
78         return isSet(ABSTRACT)
79     }
80 
isFinalnull81     override fun isFinal(): Boolean {
82         return isSet(FINAL)
83     }
84 
isNativenull85     override fun isNative(): Boolean {
86         return isSet(NATIVE)
87     }
88 
isSynchronizednull89     override fun isSynchronized(): Boolean {
90         return isSet(SYNCHRONIZED)
91     }
92 
isStrictFpnull93     override fun isStrictFp(): Boolean {
94         return isSet(STRICT_FP)
95     }
96 
isTransientnull97     override fun isTransient(): Boolean {
98         return isSet(TRANSIENT)
99     }
100 
isVolatilenull101     override fun isVolatile(): Boolean {
102         return isSet(VOLATILE)
103     }
104 
isDefaultnull105     override fun isDefault(): Boolean {
106         return isSet(DEFAULT)
107     }
108 
isDeprecatednull109     fun isDeprecated(): Boolean {
110         return isSet(DEPRECATED)
111     }
112 
isVarArgnull113     override fun isVarArg(): Boolean {
114         return isSet(VARARG)
115     }
116 
isSealednull117     override fun isSealed(): Boolean {
118         return isSet(SEALED)
119     }
120 
isFunctionalnull121     override fun isFunctional(): Boolean {
122         return isSet(FUN)
123     }
124 
isInfixnull125     override fun isInfix(): Boolean {
126         return isSet(INFIX)
127     }
128 
isConstnull129     override fun isConst(): Boolean {
130         return isSet(CONST)
131     }
132 
isSuspendnull133     override fun isSuspend(): Boolean {
134         return isSet(SUSPEND)
135     }
136 
isCompanionnull137     override fun isCompanion(): Boolean {
138         return isSet(COMPANION)
139     }
140 
isOperatornull141     override fun isOperator(): Boolean {
142         return isSet(OPERATOR)
143     }
144 
isInlinenull145     override fun isInline(): Boolean {
146         return isSet(INLINE)
147     }
148 
isValuenull149     override fun isValue(): Boolean {
150         return isSet(VALUE)
151     }
152 
isDatanull153     override fun isData(): Boolean {
154         return isSet(DATA)
155     }
156 
setVisibilityLevelnull157     override fun setVisibilityLevel(level: VisibilityLevel) {
158         flags = (flags and VISIBILITY_MASK.inv()) or level.visibilityFlagValue
159     }
160 
setStaticnull161     override fun setStatic(static: Boolean) {
162         set(STATIC, static)
163     }
164 
setAbstractnull165     override fun setAbstract(abstract: Boolean) {
166         set(ABSTRACT, abstract)
167     }
168 
setFinalnull169     override fun setFinal(final: Boolean) {
170         set(FINAL, final)
171     }
172 
setNativenull173     override fun setNative(native: Boolean) {
174         set(NATIVE, native)
175     }
176 
setSynchronizednull177     override fun setSynchronized(synchronized: Boolean) {
178         set(SYNCHRONIZED, synchronized)
179     }
180 
setStrictFpnull181     override fun setStrictFp(strictfp: Boolean) {
182         set(STRICT_FP, strictfp)
183     }
184 
setTransientnull185     override fun setTransient(transient: Boolean) {
186         set(TRANSIENT, transient)
187     }
188 
setVolatilenull189     override fun setVolatile(volatile: Boolean) {
190         set(VOLATILE, volatile)
191     }
192 
setDefaultnull193     override fun setDefault(default: Boolean) {
194         set(DEFAULT, default)
195     }
196 
setSealednull197     override fun setSealed(sealed: Boolean) {
198         set(SEALED, sealed)
199     }
200 
setFunctionalnull201     override fun setFunctional(functional: Boolean) {
202         set(FUN, functional)
203     }
204 
setInfixnull205     override fun setInfix(infix: Boolean) {
206         set(INFIX, infix)
207     }
208 
setOperatornull209     override fun setOperator(operator: Boolean) {
210         set(OPERATOR, operator)
211     }
212 
setInlinenull213     override fun setInline(inline: Boolean) {
214         set(INLINE, inline)
215     }
216 
setValuenull217     override fun setValue(value: Boolean) {
218         set(VALUE, value)
219     }
220 
setDatanull221     override fun setData(data: Boolean) {
222         set(DATA, data)
223     }
224 
225     override fun setVarArg(vararg: Boolean) {
226         set(VARARG, vararg)
227     }
228 
setDeprecatednull229     fun setDeprecated(deprecated: Boolean) {
230         set(DEPRECATED, deprecated)
231     }
232 
setSuspendnull233     fun setSuspend(suspend: Boolean) {
234         set(SUSPEND, suspend)
235     }
236 
setCompanionnull237     fun setCompanion(companion: Boolean) {
238         set(COMPANION, companion)
239     }
240 
addAnnotationnull241     override fun addAnnotation(annotation: AnnotationItem) {
242         if (annotations == null) {
243             annotations = mutableListOf()
244         }
245         annotations?.add(annotation)
246     }
247 
removeAnnotationnull248     override fun removeAnnotation(annotation: AnnotationItem) {
249         annotations?.remove(annotation)
250     }
251 
clearAnnotationsnull252     override fun clearAnnotations(annotation: AnnotationItem) {
253         annotations?.clear()
254     }
255 
isEmptynull256     override fun isEmpty(): Boolean {
257         return flags and DEPRECATED.inv() == 0 // deprecated isn't a real modifier
258     }
259 
isPackagePrivatenull260     override fun isPackagePrivate(): Boolean {
261         return flags and VISIBILITY_MASK == PACKAGE_PRIVATE
262     }
263 
264     // Rename? It's not a full equality, it's whether an override's modifier set is significant
equivalentTonull265     override fun equivalentTo(other: ModifierList): Boolean {
266         if (other is DefaultModifierList) {
267             val flags2 = other.flags
268             val mask = EQUIVALENCE_MASK
269 
270             val masked1 = flags and mask
271             val masked2 = flags2 and mask
272             val same = masked1 xor masked2
273             if (same == 0) {
274                 return true
275             } else {
276                 if (same == FINAL &&
277                     // Only differ in final: not significant if implied by containing class
278                     isFinal() && (owner as? MethodItem)?.containingClass()?.modifiers?.isFinal() == true
279                 ) {
280                     return true
281                 } else if (same == DEPRECATED &&
282                     // Only differ in deprecated: not significant if implied by containing class
283                     isDeprecated() && (owner as? MethodItem)?.containingClass()?.deprecated == true
284                 ) {
285                     return true
286                 }
287             }
288         }
289         return false
290     }
291 
292     companion object {
293         const val PRIVATE = 0
294         const val INTERNAL = 1
295         const val PACKAGE_PRIVATE = 2
296         const val PROTECTED = 3
297         const val PUBLIC = 4
298         const val VISIBILITY_MASK = 0b111
299 
300         /**
301          * An internal copy of VisibilityLevel.values() to avoid paying the cost of duplicating the array on every
302          * call.
303          */
304         private val VISIBILITY_LEVEL_ENUMS = VisibilityLevel.values()
305 
306         // Check that the constants above are consistent with the VisibilityLevel enum, i.e. the mask is large enough
307         // to include all allowable values and that each visibility level value is the same as the corresponding enum
308         // constant's ordinal.
<lambda>null309         init {
310             check(PRIVATE == VisibilityLevel.PRIVATE.ordinal)
311             check(INTERNAL == VisibilityLevel.INTERNAL.ordinal)
312             check(PACKAGE_PRIVATE == VisibilityLevel.PACKAGE_PRIVATE.ordinal)
313             check(PROTECTED == VisibilityLevel.PROTECTED.ordinal)
314             check(PUBLIC == VisibilityLevel.PUBLIC.ordinal)
315             // Calculate the mask required to hold as many different values as there are VisibilityLevel values.
316             // Given N visibility levels, the required mask is constructed by determining the MSB in the number N - 1
317             // and then setting all bits to the right.
318             // e.g. when N is 5 then N - 1 is 4, the MSB is bit 2, and so the mask is what you get when you set bits 2,
319             // 1 and 0, i.e. 0b111.
320             val expectedMask = (1 shl (32 - Integer.numberOfLeadingZeros(VISIBILITY_LEVEL_ENUMS.size - 1))) - 1
321             check(VISIBILITY_MASK == expectedMask)
322         }
323 
324         const val STATIC = 1 shl 3
325         const val ABSTRACT = 1 shl 4
326         const val FINAL = 1 shl 5
327         const val NATIVE = 1 shl 6
328         const val SYNCHRONIZED = 1 shl 7
329         const val STRICT_FP = 1 shl 8
330         const val TRANSIENT = 1 shl 9
331         const val VOLATILE = 1 shl 10
332         const val DEFAULT = 1 shl 11
333         const val DEPRECATED = 1 shl 12
334         const val VARARG = 1 shl 13
335         const val SEALED = 1 shl 14
336         const val FUN = 1 shl 15
337         const val INFIX = 1 shl 16
338         const val OPERATOR = 1 shl 17
339         const val INLINE = 1 shl 18
340         const val SUSPEND = 1 shl 19
341         const val COMPANION = 1 shl 20
342         const val CONST = 1 shl 21
343         const val DATA = 1 shl 22
344         const val VALUE = 1 shl 23
345 
346         /**
347          * Modifiers considered significant to include signature files (and similarly
348          * to consider whether an override of a method is different from its super implementation
349          */
350         private const val EQUIVALENCE_MASK = VISIBILITY_MASK or STATIC or ABSTRACT or
351             FINAL or TRANSIENT or VOLATILE or DEPRECATED or VARARG or
352             SEALED or FUN or INFIX or OPERATOR or SUSPEND or COMPANION
353     }
354 }
355