blob: ead8a4e96b241c81cf4098c9c1bb7041525bc440 [file] [log] [blame]
Paul Duffin428c6512021-07-21 15:33:22 +01001#!/usr/bin/env python
2#
3# Copyright (C) 2021 The Android Open Source Project
4#
5# Licensed under the Apache License, Version 2.0 (the 'License');
6# you may not use this file except in compliance with the License.
7# You may obtain a copy of the License at
8#
9# http://www.apache.org/licenses/LICENSE-2.0
10#
11# Unless required by applicable law or agreed to in writing, software
12# distributed under the License is distributed on an 'AS IS' BASIS,
13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14# See the License for the specific language governing permissions and
15# limitations under the License.
Paul Duffin428c6512021-07-21 15:33:22 +010016"""Unit tests for verify_overlaps_test.py."""
17import io
18import unittest
19
Paul Duffin181b56c2022-04-08 00:03:32 +010020import verify_overlaps as vo
Spandan Das559132f2021-08-25 18:17:33 +000021
Paul Duffin428c6512021-07-21 15:33:22 +010022
23class TestDetectOverlaps(unittest.TestCase):
24
Paul Duffin181b56c2022-04-08 00:03:32 +010025 @staticmethod
26 def read_flag_trie_from_string(csvdata):
Spandan Das559132f2021-08-25 18:17:33 +000027 with io.StringIO(csvdata) as f:
Paul Duffin181b56c2022-04-08 00:03:32 +010028 return vo.read_flag_trie_from_stream(f)
Paul Duffinc11f6672021-07-20 00:04:21 +010029
Paul Duffin181b56c2022-04-08 00:03:32 +010030 @staticmethod
31 def read_signature_csv_from_string_as_dict(csvdata):
Spandan Das559132f2021-08-25 18:17:33 +000032 with io.StringIO(csvdata) as f:
Paul Duffin181b56c2022-04-08 00:03:32 +010033 return vo.read_signature_csv_from_stream_as_dict(f)
Paul Duffin428c6512021-07-21 15:33:22 +010034
Paul Duffin181b56c2022-04-08 00:03:32 +010035 @staticmethod
Spandan Das559132f2021-08-25 18:17:33 +000036 def extract_subset_from_monolithic_flags_as_dict_from_string(
Paul Duffin181b56c2022-04-08 00:03:32 +010037 monolithic, patterns):
Paul Duffin67b9d612021-07-21 17:38:47 +010038 with io.StringIO(patterns) as f:
Paul Duffin181b56c2022-04-08 00:03:32 +010039 return vo.extract_subset_from_monolithic_flags_as_dict_from_stream(
Spandan Das559132f2021-08-25 18:17:33 +000040 monolithic, f)
Paul Duffin67b9d612021-07-21 17:38:47 +010041
Spandan Das559132f2021-08-25 18:17:33 +000042 extractInput = """
Paul Duffin53a76072021-07-21 17:27:09 +010043Ljava/lang/Object;->hashCode()I,public-api,system-api,test-api
44Ljava/lang/Object;->toString()Ljava/lang/String;,blocked
Paul Duffinc11f6672021-07-20 00:04:21 +010045Ljava/util/zip/ZipFile;-><clinit>()V,blocked
46Ljava/lang/Character$UnicodeScript;->of(I)Ljava/lang/Character$UnicodeScript;,blocked
47Ljava/lang/Character;->serialVersionUID:J,sdk
48Ljava/lang/ProcessBuilder$Redirect$1;-><init>()V,blocked
Spandan Das559132f2021-08-25 18:17:33 +000049"""
Paul Duffin53a76072021-07-21 17:27:09 +010050
Paul Duffinc11f6672021-07-20 00:04:21 +010051 def test_extract_subset_signature(self):
Spandan Das559132f2021-08-25 18:17:33 +000052 monolithic = self.read_flag_trie_from_string(
53 TestDetectOverlaps.extractInput)
Paul Duffin67b9d612021-07-21 17:38:47 +010054
Paul Duffin181b56c2022-04-08 00:03:32 +010055 patterns = "Ljava/lang/Object;->hashCode()I"
Paul Duffin67b9d612021-07-21 17:38:47 +010056
Spandan Das559132f2021-08-25 18:17:33 +000057 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
58 monolithic, patterns)
Paul Duffin53a76072021-07-21 17:27:09 +010059 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +010060 "Ljava/lang/Object;->hashCode()I": {
61 None: ["public-api", "system-api", "test-api"],
62 "signature": "Ljava/lang/Object;->hashCode()I",
Paul Duffin53a76072021-07-21 17:27:09 +010063 },
64 }
65 self.assertEqual(expected, subset)
66
Paul Duffinc11f6672021-07-20 00:04:21 +010067 def test_extract_subset_class(self):
Spandan Das559132f2021-08-25 18:17:33 +000068 monolithic = self.read_flag_trie_from_string(
69 TestDetectOverlaps.extractInput)
Paul Duffinc11f6672021-07-20 00:04:21 +010070
Paul Duffin181b56c2022-04-08 00:03:32 +010071 patterns = "java/lang/Object"
Paul Duffinc11f6672021-07-20 00:04:21 +010072
Spandan Das559132f2021-08-25 18:17:33 +000073 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
74 monolithic, patterns)
Paul Duffinc11f6672021-07-20 00:04:21 +010075 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +010076 "Ljava/lang/Object;->hashCode()I": {
77 None: ["public-api", "system-api", "test-api"],
78 "signature": "Ljava/lang/Object;->hashCode()I",
Paul Duffinc11f6672021-07-20 00:04:21 +010079 },
Paul Duffin181b56c2022-04-08 00:03:32 +010080 "Ljava/lang/Object;->toString()Ljava/lang/String;": {
81 None: ["blocked"],
82 "signature": "Ljava/lang/Object;->toString()Ljava/lang/String;",
Paul Duffinc11f6672021-07-20 00:04:21 +010083 },
84 }
85 self.assertEqual(expected, subset)
86
87 def test_extract_subset_outer_class(self):
Spandan Das559132f2021-08-25 18:17:33 +000088 monolithic = self.read_flag_trie_from_string(
89 TestDetectOverlaps.extractInput)
Paul Duffinc11f6672021-07-20 00:04:21 +010090
Paul Duffin181b56c2022-04-08 00:03:32 +010091 patterns = "java/lang/Character"
Paul Duffinc11f6672021-07-20 00:04:21 +010092
Spandan Das559132f2021-08-25 18:17:33 +000093 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
94 monolithic, patterns)
Paul Duffinc11f6672021-07-20 00:04:21 +010095 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +010096 "Ljava/lang/Character$UnicodeScript;"
97 "->of(I)Ljava/lang/Character$UnicodeScript;": {
98 None: ["blocked"],
99 "signature": "Ljava/lang/Character$UnicodeScript;"
100 "->of(I)Ljava/lang/Character$UnicodeScript;",
101 },
102 "Ljava/lang/Character;->serialVersionUID:J": {
103 None: ["sdk"],
104 "signature": "Ljava/lang/Character;->serialVersionUID:J",
Paul Duffinc11f6672021-07-20 00:04:21 +0100105 },
106 }
107 self.assertEqual(expected, subset)
108
109 def test_extract_subset_nested_class(self):
Spandan Das559132f2021-08-25 18:17:33 +0000110 monolithic = self.read_flag_trie_from_string(
111 TestDetectOverlaps.extractInput)
Paul Duffinc11f6672021-07-20 00:04:21 +0100112
Paul Duffin181b56c2022-04-08 00:03:32 +0100113 patterns = "java/lang/Character$UnicodeScript"
Paul Duffinc11f6672021-07-20 00:04:21 +0100114
Spandan Das559132f2021-08-25 18:17:33 +0000115 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
116 monolithic, patterns)
Paul Duffinc11f6672021-07-20 00:04:21 +0100117 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +0100118 "Ljava/lang/Character$UnicodeScript;"
119 "->of(I)Ljava/lang/Character$UnicodeScript;": {
120 None: ["blocked"],
121 "signature": "Ljava/lang/Character$UnicodeScript;"
122 "->of(I)Ljava/lang/Character$UnicodeScript;",
123 },
Paul Duffinc11f6672021-07-20 00:04:21 +0100124 }
125 self.assertEqual(expected, subset)
126
127 def test_extract_subset_package(self):
Spandan Das559132f2021-08-25 18:17:33 +0000128 monolithic = self.read_flag_trie_from_string(
129 TestDetectOverlaps.extractInput)
Paul Duffinc11f6672021-07-20 00:04:21 +0100130
Paul Duffin181b56c2022-04-08 00:03:32 +0100131 patterns = "java/lang/*"
Paul Duffinc11f6672021-07-20 00:04:21 +0100132
Spandan Das559132f2021-08-25 18:17:33 +0000133 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
134 monolithic, patterns)
Paul Duffinc11f6672021-07-20 00:04:21 +0100135 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +0100136 "Ljava/lang/Character$UnicodeScript;"
137 "->of(I)Ljava/lang/Character$UnicodeScript;": {
138 None: ["blocked"],
139 "signature": "Ljava/lang/Character$UnicodeScript;"
140 "->of(I)Ljava/lang/Character$UnicodeScript;",
Paul Duffinc11f6672021-07-20 00:04:21 +0100141 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100142 "Ljava/lang/Character;->serialVersionUID:J": {
143 None: ["sdk"],
144 "signature": "Ljava/lang/Character;->serialVersionUID:J",
Paul Duffinc11f6672021-07-20 00:04:21 +0100145 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100146 "Ljava/lang/Object;->hashCode()I": {
147 None: ["public-api", "system-api", "test-api"],
148 "signature": "Ljava/lang/Object;->hashCode()I",
Paul Duffinc11f6672021-07-20 00:04:21 +0100149 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100150 "Ljava/lang/Object;->toString()Ljava/lang/String;": {
151 None: ["blocked"],
152 "signature": "Ljava/lang/Object;->toString()Ljava/lang/String;",
153 },
154 "Ljava/lang/ProcessBuilder$Redirect$1;-><init>()V": {
155 None: ["blocked"],
156 "signature": "Ljava/lang/ProcessBuilder$Redirect$1;-><init>()V",
Paul Duffinc11f6672021-07-20 00:04:21 +0100157 },
158 }
159 self.assertEqual(expected, subset)
160
161 def test_extract_subset_recursive_package(self):
Spandan Das559132f2021-08-25 18:17:33 +0000162 monolithic = self.read_flag_trie_from_string(
163 TestDetectOverlaps.extractInput)
Paul Duffinc11f6672021-07-20 00:04:21 +0100164
Paul Duffin181b56c2022-04-08 00:03:32 +0100165 patterns = "java/**"
Paul Duffinc11f6672021-07-20 00:04:21 +0100166
Spandan Das559132f2021-08-25 18:17:33 +0000167 subset = self.extract_subset_from_monolithic_flags_as_dict_from_string(
168 monolithic, patterns)
Paul Duffinc11f6672021-07-20 00:04:21 +0100169 expected = {
Paul Duffin181b56c2022-04-08 00:03:32 +0100170 "Ljava/lang/Character$UnicodeScript;"
171 "->of(I)Ljava/lang/Character$UnicodeScript;": {
172 None: ["blocked"],
173 "signature": "Ljava/lang/Character$UnicodeScript;"
174 "->of(I)Ljava/lang/Character$UnicodeScript;",
Paul Duffinc11f6672021-07-20 00:04:21 +0100175 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100176 "Ljava/lang/Character;->serialVersionUID:J": {
177 None: ["sdk"],
178 "signature": "Ljava/lang/Character;->serialVersionUID:J",
Paul Duffinc11f6672021-07-20 00:04:21 +0100179 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100180 "Ljava/lang/Object;->hashCode()I": {
181 None: ["public-api", "system-api", "test-api"],
182 "signature": "Ljava/lang/Object;->hashCode()I",
Paul Duffinc11f6672021-07-20 00:04:21 +0100183 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100184 "Ljava/lang/Object;->toString()Ljava/lang/String;": {
185 None: ["blocked"],
186 "signature": "Ljava/lang/Object;->toString()Ljava/lang/String;",
Paul Duffinc11f6672021-07-20 00:04:21 +0100187 },
Paul Duffin181b56c2022-04-08 00:03:32 +0100188 "Ljava/lang/ProcessBuilder$Redirect$1;-><init>()V": {
189 None: ["blocked"],
190 "signature": "Ljava/lang/ProcessBuilder$Redirect$1;-><init>()V",
191 },
192 "Ljava/util/zip/ZipFile;-><clinit>()V": {
193 None: ["blocked"],
194 "signature": "Ljava/util/zip/ZipFile;-><clinit>()V",
Paul Duffinc11f6672021-07-20 00:04:21 +0100195 },
196 }
197 self.assertEqual(expected, subset)
198
Paul Duffinc11f6672021-07-20 00:04:21 +0100199 def test_read_trie_duplicate(self):
200 with self.assertRaises(Exception) as context:
Spandan Das559132f2021-08-25 18:17:33 +0000201 self.read_flag_trie_from_string("""
Paul Duffinc11f6672021-07-20 00:04:21 +0100202Ljava/lang/Object;->hashCode()I,public-api,system-api,test-api
203Ljava/lang/Object;->hashCode()I,blocked
Spandan Das559132f2021-08-25 18:17:33 +0000204""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100205 self.assertTrue("Duplicate signature: Ljava/lang/Object;->hashCode()I"
Spandan Das559132f2021-08-25 18:17:33 +0000206 in str(context.exception))
Paul Duffinc11f6672021-07-20 00:04:21 +0100207
208 def test_read_trie_missing_member(self):
209 with self.assertRaises(Exception) as context:
Spandan Das559132f2021-08-25 18:17:33 +0000210 self.read_flag_trie_from_string("""
Paul Duffinc11f6672021-07-20 00:04:21 +0100211Ljava/lang/Object,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000212""")
213 self.assertTrue(
Paul Duffin181b56c2022-04-08 00:03:32 +0100214 "Invalid signature: Ljava/lang/Object, "
215 "does not identify a specific member" in str(context.exception))
Paul Duffinc11f6672021-07-20 00:04:21 +0100216
Paul Duffin428c6512021-07-21 15:33:22 +0100217 def test_match(self):
Spandan Das559132f2021-08-25 18:17:33 +0000218 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100219Ljava/lang/Object;->hashCode()I,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000220""")
221 modular = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100222Ljava/lang/Object;->hashCode()I,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000223""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100224 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin428c6512021-07-21 15:33:22 +0100225 expected = []
226 self.assertEqual(expected, mismatches)
227
228 def test_mismatch_overlapping_flags(self):
Spandan Das559132f2021-08-25 18:17:33 +0000229 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100230Ljava/lang/Object;->toString()Ljava/lang/String;,public-api
Spandan Das559132f2021-08-25 18:17:33 +0000231""")
232 modular = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100233Ljava/lang/Object;->toString()Ljava/lang/String;,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000234""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100235 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin428c6512021-07-21 15:33:22 +0100236 expected = [
237 (
Paul Duffin181b56c2022-04-08 00:03:32 +0100238 "Ljava/lang/Object;->toString()Ljava/lang/String;",
239 ["public-api", "system-api", "test-api"],
240 ["public-api"],
Paul Duffin428c6512021-07-21 15:33:22 +0100241 ),
242 ]
243 self.assertEqual(expected, mismatches)
244
Paul Duffin428c6512021-07-21 15:33:22 +0100245 def test_mismatch_monolithic_blocked(self):
Spandan Das559132f2021-08-25 18:17:33 +0000246 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100247Ljava/lang/Object;->toString()Ljava/lang/String;,blocked
Spandan Das559132f2021-08-25 18:17:33 +0000248""")
249 modular = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100250Ljava/lang/Object;->toString()Ljava/lang/String;,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000251""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100252 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin428c6512021-07-21 15:33:22 +0100253 expected = [
254 (
Paul Duffin181b56c2022-04-08 00:03:32 +0100255 "Ljava/lang/Object;->toString()Ljava/lang/String;",
256 ["public-api", "system-api", "test-api"],
257 ["blocked"],
Paul Duffin428c6512021-07-21 15:33:22 +0100258 ),
259 ]
260 self.assertEqual(expected, mismatches)
261
262 def test_mismatch_modular_blocked(self):
Spandan Das559132f2021-08-25 18:17:33 +0000263 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100264Ljava/lang/Object;->toString()Ljava/lang/String;,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000265""")
266 modular = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100267Ljava/lang/Object;->toString()Ljava/lang/String;,blocked
Spandan Das559132f2021-08-25 18:17:33 +0000268""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100269 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin428c6512021-07-21 15:33:22 +0100270 expected = [
271 (
Paul Duffin181b56c2022-04-08 00:03:32 +0100272 "Ljava/lang/Object;->toString()Ljava/lang/String;",
273 ["blocked"],
274 ["public-api", "system-api", "test-api"],
Paul Duffin428c6512021-07-21 15:33:22 +0100275 ),
276 ]
277 self.assertEqual(expected, mismatches)
278
Paul Duffin280bae62021-07-20 18:03:53 +0100279 def test_match_treat_missing_from_modular_as_blocked(self):
Paul Duffin181b56c2022-04-08 00:03:32 +0100280 monolithic = self.read_signature_csv_from_string_as_dict("")
Spandan Das559132f2021-08-25 18:17:33 +0000281 modular = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100282Ljava/lang/Object;->toString()Ljava/lang/String;,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000283""")
Paul Duffin181b56c2022-04-08 00:03:32 +0100284 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin428c6512021-07-21 15:33:22 +0100285 expected = [
286 (
Paul Duffin181b56c2022-04-08 00:03:32 +0100287 "Ljava/lang/Object;->toString()Ljava/lang/String;",
288 ["public-api", "system-api", "test-api"],
Paul Duffin428c6512021-07-21 15:33:22 +0100289 [],
290 ),
291 ]
292 self.assertEqual(expected, mismatches)
293
Paul Duffin280bae62021-07-20 18:03:53 +0100294 def test_mismatch_treat_missing_from_modular_as_blocked(self):
Spandan Das559132f2021-08-25 18:17:33 +0000295 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100296Ljava/lang/Object;->hashCode()I,public-api,system-api,test-api
Spandan Das559132f2021-08-25 18:17:33 +0000297""")
Paul Duffin428c6512021-07-21 15:33:22 +0100298 modular = {}
Paul Duffin181b56c2022-04-08 00:03:32 +0100299 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin53a76072021-07-21 17:27:09 +0100300 expected = [
301 (
Paul Duffin181b56c2022-04-08 00:03:32 +0100302 "Ljava/lang/Object;->hashCode()I",
303 ["blocked"],
304 ["public-api", "system-api", "test-api"],
Paul Duffin53a76072021-07-21 17:27:09 +0100305 ),
306 ]
Paul Duffin428c6512021-07-21 15:33:22 +0100307 self.assertEqual(expected, mismatches)
308
309 def test_blocked_missing_from_modular(self):
Spandan Das559132f2021-08-25 18:17:33 +0000310 monolithic = self.read_signature_csv_from_string_as_dict("""
Paul Duffin428c6512021-07-21 15:33:22 +0100311Ljava/lang/Object;->hashCode()I,blocked
Spandan Das559132f2021-08-25 18:17:33 +0000312""")
Paul Duffin428c6512021-07-21 15:33:22 +0100313 modular = {}
Paul Duffin181b56c2022-04-08 00:03:32 +0100314 mismatches = vo.compare_signature_flags(monolithic, modular)
Paul Duffin280bae62021-07-20 18:03:53 +0100315 expected = []
Paul Duffin428c6512021-07-21 15:33:22 +0100316 self.assertEqual(expected, mismatches)
Paul Duffinb5cd5222022-02-28 19:06:49 +0000317
318
Paul Duffin181b56c2022-04-08 00:03:32 +0100319if __name__ == "__main__":
Paul Duffin428c6512021-07-21 15:33:22 +0100320 unittest.main(verbosity=2)