From 5765fa9fb81e14850e605d84b67c631e0448f840 Mon Sep 17 00:00:00 2001 From: Andrei Onea Date: Thu, 16 Dec 2021 17:22:47 +0000 Subject: [PATCH] Add test for parsing apex allowlists Test: atest FrameworksServicesTests:SystemConfigTest Bug: 190375768 Change-Id: Ia530a7b5b62774660c410ca8a9f49b18ff9b9b57 --- .../java/com/android/server/SystemConfig.java | 17 ++++-- .../server/systemconfig/SystemConfigTest.java | 56 +++++++++++++++++-- 2 files changed, 62 insertions(+), 11 deletions(-) diff --git a/core/java/com/android/server/SystemConfig.java b/core/java/com/android/server/SystemConfig.java index 39f17e510a1cf..f364cb27888dc 100644 --- a/core/java/com/android/server/SystemConfig.java +++ b/core/java/com/android/server/SystemConfig.java @@ -1175,7 +1175,8 @@ public class SystemConfig { readPrivAppPermissions(parser, mSystemExtPrivAppPermissions, mSystemExtPrivAppDenyPermissions); } else if (apex) { - readApexPrivAppPermissions(parser, permFile); + readApexPrivAppPermissions(parser, permFile, + Environment.getApexDirectory().toPath()); } else { readPrivAppPermissions(parser, mPrivAppPermissions, mPrivAppDenyPermissions); @@ -1735,8 +1736,7 @@ public class SystemConfig { /** * Returns the module name for a file in the apex module's partition. */ - private String getApexModuleNameFromFilePath(Path path) { - final Path apexDirectoryPath = Environment.getApexDirectory().toPath(); + private String getApexModuleNameFromFilePath(Path path, Path apexDirectoryPath) { if (!path.startsWith(apexDirectoryPath)) { throw new IllegalArgumentException("File " + path + " is not part of an APEX."); } @@ -1748,9 +1748,14 @@ public class SystemConfig { return path.getName(apexDirectoryPath.getNameCount()).toString(); } - private void readApexPrivAppPermissions(XmlPullParser parser, File permFile) - throws IOException, XmlPullParserException { - final String moduleName = getApexModuleNameFromFilePath(permFile.toPath()); + /** + * Reads the contents of the privileged permission allowlist stored inside an APEX. + */ + @VisibleForTesting + public void readApexPrivAppPermissions(XmlPullParser parser, File permFile, + Path apexDirectoryPath) throws IOException, XmlPullParserException { + final String moduleName = + getApexModuleNameFromFilePath(permFile.toPath(), apexDirectoryPath); final ArrayMap> privAppPermissions; if (mApexPrivAppPermissions.containsKey(moduleName)) { privAppPermissions = mApexPrivAppPermissions.get(moduleName); diff --git a/services/tests/servicestests/src/com/android/server/systemconfig/SystemConfigTest.java b/services/tests/servicestests/src/com/android/server/systemconfig/SystemConfigTest.java index eeaf781dd3071..ca756f4778d50 100644 --- a/services/tests/servicestests/src/com/android/server/systemconfig/SystemConfigTest.java +++ b/services/tests/servicestests/src/com/android/server/systemconfig/SystemConfigTest.java @@ -39,9 +39,11 @@ import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.junit.runner.RunWith; import org.xmlpull.v1.XmlPullParser; +import org.xmlpull.v1.XmlPullParserException; import java.io.BufferedWriter; import java.io.File; +import java.io.FileReader; import java.io.FileWriter; import java.io.IOException; import java.util.Arrays; @@ -137,13 +139,14 @@ public class SystemConfigTest { new ArraySet<>(Arrays.asList("GUEST", "PROFILE"))); final File folder1 = createTempSubfolder("folder1"); - createTempFile(folder1, "permFile1.xml", contents1); + createTempFile(folder1, "permissionFile1.xml", contents1); final File folder2 = createTempSubfolder("folder2"); - createTempFile(folder2, "permFile2.xml", contents2); + createTempFile(folder2, "permissionFile2.xml", contents2); - // Also, make a third file, but with the name folder1/permFile2.xml, to prove no conflicts. - createTempFile(folder1, "permFile2.xml", contents3); + // Also, make a third file, but with the name folder1/permissionFile2.xml, to prove no + // conflicts. + createTempFile(folder1, "permissionFile2.xml", contents3); readPermissions(folder1, /* No permission needed anyway */ 0); readPermissions(folder2, /* No permission needed anyway */ 0); @@ -333,6 +336,30 @@ public class SystemConfigTest { assertThat(mSysConfig.getAllowedVendorApexes()).isEmpty(); } + @Test + public void readApexPrivAppPermissions_addAllPermissions() + throws Exception { + final String contents = + "" + + "" + + "" + + ""; + File apexDir = createTempSubfolder("apex"); + File permissionFile = createTempFile( + createTempSubfolder("apex/com.android.my_module/etc/permissions"), + "permissions.xml", contents); + XmlPullParser parser = readXmlUntilStartTag(permissionFile); + + mSysConfig.readApexPrivAppPermissions(parser, permissionFile, apexDir.toPath()); + + assertThat(mSysConfig.getApexPrivAppPermissions("com.android.my_module", + "com.android.apk_in_apex")) + .containsExactly("android.permission.FOO"); + assertThat(mSysConfig.getApexPrivAppDenyPermissions("com.android.my_module", + "com.android.apk_in_apex")) + .containsExactly("android.permission.BAR"); + } + /** * Tests that readPermissions works correctly for a library with on-bootclasspath-before * and on-bootclasspath-since. @@ -491,6 +518,25 @@ public class SystemConfigTest { readPermissions(folder, /* permissionFlag = ALLOW_LIBS */ 0x02); } + /** + * Create an {@link XmlPullParser} for {@param permissionFile} and begin parsing it until + * reaching the root tag. + */ + private XmlPullParser readXmlUntilStartTag(File permissionFile) + throws IOException, XmlPullParserException { + FileReader permReader = new FileReader(permissionFile); + XmlPullParser parser = Xml.newPullParser(); + parser.setInput(permReader); + int type; + do { + type = parser.next(); + } while (type != parser.START_TAG && type != parser.END_DOCUMENT); + if (type != parser.START_TAG) { + throw new XmlPullParserException("No start tag found"); + } + return parser; + } + /** * Creates folderName/fileName in the mTemporaryFolder and fills it with the contents. * @@ -500,7 +546,7 @@ public class SystemConfigTest { private File createTempSubfolder(String folderName) throws IOException { File folder = new File(mTemporaryFolder.getRoot(), folderName); - folder.mkdir(); + folder.mkdirs(); return folder; }