diff --git a/src/main/java/net/neoforged/jarcompatibilitychecker/core/ClassInfoComparer.java b/src/main/java/net/neoforged/jarcompatibilitychecker/core/ClassInfoComparer.java index 0eb2d70..4a62b4b 100644 --- a/src/main/java/net/neoforged/jarcompatibilitychecker/core/ClassInfoComparer.java +++ b/src/main/java/net/neoforged/jarcompatibilitychecker/core/ClassInfoComparer.java @@ -44,7 +44,11 @@ public static ClassInfoComparisonResults compare(boolean checkBinary, @Nullable List internalAnnotations, InternalAnnotationCheckMode internalAnnotationCheckMode, ClassInfoCache baseCache, ClassInfo baseClassInfo, ClassInfoCache concreteCache, @Nullable ClassInfo concreteClassInfo) { ClassInfoComparisonResults results = new ClassInfoComparisonResults(baseClassInfo); - boolean classInternal = isInternalApi(baseClassInfo, internalAnnotations, internalAnnotationCheckMode); + String name = baseClassInfo.getName(); + int idx = name.lastIndexOf('/'); + String packageInfoName = name.substring(0, idx + 1) + "package-info"; + ClassInfo packageInfo = baseCache.getMainClassInfo(packageInfoName); + boolean classInternal = isInternalApi(baseClassInfo, internalAnnotations, internalAnnotationCheckMode, packageInfo); if (classInternal && internalAnnotationCheckMode == InternalAnnotationCheckMode.SKIP) return results; @@ -117,7 +121,7 @@ public static ClassInfoComparisonResults compare(boolean checkBinary, @Nullable boolean isStatic = (baseInfo.access & Opcodes.ACC_STATIC) != 0; MethodInfo inputInfo = getMethodInfo(concreteClassInfo, concreteParents, isStatic, baseInfo.name, baseInfo.desc); - boolean methodInternal = isInternalApi(baseInfo, internalAnnotations, internalAnnotationCheckMode); + boolean methodInternal = classInternal || isInternalApi(baseInfo, internalAnnotations, internalAnnotationCheckMode, packageInfo); if (methodInternal && internalAnnotationCheckMode == InternalAnnotationCheckMode.SKIP) continue; @@ -165,7 +169,7 @@ public static ClassInfoComparisonResults compare(boolean checkBinary, @Nullable for (FieldInfo baseInfo : baseClassInfo.getFields().values()) { boolean isStatic = (baseInfo.access & Opcodes.ACC_STATIC) != 0; FieldInfo inputInfo = getFieldInfo(concreteClassInfo, concreteParents, isStatic, baseInfo.name); - boolean fieldInternal = isInternalApi(baseInfo, internalAnnotations, internalAnnotationCheckMode); + boolean fieldInternal = classInternal || isInternalApi(baseInfo, internalAnnotations, internalAnnotationCheckMode, packageInfo); if (fieldInternal && internalAnnotationCheckMode == InternalAnnotationCheckMode.SKIP) continue; @@ -223,11 +227,15 @@ public static boolean isMadeFinal(boolean checkBinary, int baseAccess, int input } public static boolean isInternalApi(MemberInfo memberInfo, List internalAnnotations, InternalAnnotationCheckMode checkMode) { + return isInternalApi(memberInfo, internalAnnotations, checkMode, null); + } + + public static boolean isInternalApi(MemberInfo memberInfo, List internalAnnotations, InternalAnnotationCheckMode checkMode, @Nullable ClassInfo packageInfo) { if (checkMode == InternalAnnotationCheckMode.ERROR) return false; // Even if internal, we want to handle internal members like normal for ERROR check mode for (String internalAnnotation : internalAnnotations) { - if (memberInfo.hasAnnotation(internalAnnotation)) + if (memberInfo.hasAnnotation(internalAnnotation) || packageInfo != null && packageInfo.hasAnnotation(internalAnnotation)) return true; }