Loading core/java/android/net/IpSecManager.java +6 −0 Original line number Diff line number Diff line Loading @@ -19,11 +19,13 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresFeature; import android.annotation.RequiresPermission; import android.annotation.SystemApi; import android.annotation.SystemService; import android.annotation.TestApi; import android.content.Context; import android.content.pm.PackageManager; import android.os.Binder; import android.os.ParcelFileDescriptor; import android.os.RemoteException; Loading Loading @@ -749,6 +751,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void addAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { Loading @@ -771,6 +774,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void removeAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { Loading Loading @@ -886,6 +890,7 @@ public final class IpSecManager { */ @SystemApi @NonNull @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTunnelInterface createIpSecTunnelInterface(@NonNull InetAddress localAddress, @NonNull InetAddress remoteAddress, @NonNull Network underlyingNetwork) Loading Loading @@ -916,6 +921,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void applyTunnelModeTransform(@NonNull IpSecTunnelInterface tunnel, @PolicyDirection int direction, @NonNull IpSecTransform transform) throws IOException { Loading core/java/android/net/IpSecTransform.java +3 −0 Original line number Diff line number Diff line Loading @@ -21,9 +21,11 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresFeature; import android.annotation.RequiresPermission; import android.annotation.SystemApi; import android.content.Context; import android.content.pm.PackageManager; import android.os.Binder; import android.os.Handler; import android.os.IBinder; Loading Loading @@ -483,6 +485,7 @@ public final class IpSecTransform implements AutoCloseable { */ @SystemApi @NonNull @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTransform buildTunnelModeTransform( @NonNull InetAddress sourceAddress, Loading services/core/java/com/android/server/IpSecService.java +13 −7 Original line number Diff line number Diff line Loading @@ -30,6 +30,7 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.NonNull; import android.app.AppOpsManager; import android.content.Context; import android.content.pm.PackageManager; import android.net.IIpSecService; import android.net.INetd; import android.net.IpSecAlgorithm; Loading Loading @@ -1276,7 +1277,7 @@ public class IpSecService extends IIpSecService.Stub { public synchronized IpSecTunnelInterfaceResponse createTunnelInterface( String localAddr, String remoteAddr, Network underlyingNetwork, IBinder binder, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); checkNotNull(binder, "Null Binder passed to createTunnelInterface"); checkNotNull(underlyingNetwork, "No underlying network was specified"); checkInetAddress(localAddr); Loading Loading @@ -1362,7 +1363,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void addAddressToTunnelInterface( int tunnelResourceId, LinkAddress localAddr, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); // Get tunnelInterface record; if no such interface is found, will throw Loading Loading @@ -1391,7 +1392,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void removeAddressFromTunnelInterface( int tunnelResourceId, LinkAddress localAddr, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); // Get tunnelInterface record; if no such interface is found, will throw Loading Loading @@ -1420,7 +1421,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void deleteTunnelInterface( int resourceId, String callingPackage) throws RemoteException { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); releaseResource(userRecord.mTunnelInterfaceRecords, resourceId); } Loading Loading @@ -1549,7 +1550,12 @@ public class IpSecService extends IIpSecService.Stub { private static final String TUNNEL_OP = AppOpsManager.OPSTR_MANAGE_IPSEC_TUNNELS; private void enforceTunnelPermissions(String callingPackage) { private void enforceTunnelFeatureAndPermissions(String callingPackage) { if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_IPSEC_TUNNELS)) { throw new UnsupportedOperationException( "IPsec Tunnel Mode requires PackageManager.FEATURE_IPSEC_TUNNELS"); } checkNotNull(callingPackage, "Null calling package cannot create IpSec tunnels"); switch (getAppOpsManager().noteOp(TUNNEL_OP, Binder.getCallingUid(), callingPackage)) { case AppOpsManager.MODE_DEFAULT: Loading Loading @@ -1621,7 +1627,7 @@ public class IpSecService extends IIpSecService.Stub { IpSecConfig c, IBinder binder, String callingPackage) throws RemoteException { checkNotNull(c); if (c.getMode() == IpSecTransform.MODE_TUNNEL) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); } checkIpSecConfig(c); checkNotNull(binder, "Null Binder passed to createTransform"); Loading Loading @@ -1729,7 +1735,7 @@ public class IpSecService extends IIpSecService.Stub { public synchronized void applyTunnelModeTransform( int tunnelResourceId, int direction, int transformResourceId, String callingPackage) throws RemoteException { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); checkDirection(direction); int callingUid = Binder.getCallingUid(); Loading tests/net/java/com/android/server/IpSecServiceParameterizedTest.java +27 −0 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ import static org.mockito.Mockito.when; import android.app.AppOpsManager; import android.content.Context; import android.content.pm.PackageManager; import android.net.INetd; import android.net.IpSecAlgorithm; import android.net.IpSecConfig; Loading @@ -57,6 +58,7 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.junit.runners.Parameterized; import java.net.Inet4Address; import java.net.Socket; import java.util.Arrays; import java.util.Collection; Loading Loading @@ -118,6 +120,11 @@ public class IpSecServiceParameterizedTest { } } @Override public PackageManager getPackageManager() { return mMockPkgMgr; } @Override public void enforceCallingOrSelfPermission(String permission, String message) { if (permission == android.Manifest.permission.MANAGE_IPSEC_TUNNELS) { Loading @@ -128,6 +135,7 @@ public class IpSecServiceParameterizedTest { }; INetd mMockNetd; PackageManager mMockPkgMgr; IpSecService.IpSecServiceConfiguration mMockIpSecSrvConfig; IpSecService mIpSecService; Network fakeNetwork = new Network(0xAB); Loading @@ -152,11 +160,16 @@ public class IpSecServiceParameterizedTest { @Before public void setUp() throws Exception { mMockNetd = mock(INetd.class); mMockPkgMgr = mock(PackageManager.class); mMockIpSecSrvConfig = mock(IpSecService.IpSecServiceConfiguration.class); mIpSecService = new IpSecService(mMockContext, mMockIpSecSrvConfig); // Injecting mock netd when(mMockIpSecSrvConfig.getNetdInstance()).thenReturn(mMockNetd); // PackageManager should always return true (feature flag tests in IpSecServiceTest) when(mMockPkgMgr.hasSystemFeature(anyString())).thenReturn(true); // A package granted the AppOp for MANAGE_IPSEC_TUNNELS will be MODE_ALLOWED. when(mMockAppOps.noteOp(anyInt(), anyInt(), eq("blessedPackage"))) .thenReturn(AppOpsManager.MODE_ALLOWED); Loading Loading @@ -709,4 +722,18 @@ public class IpSecServiceParameterizedTest { } catch (SecurityException expected) { } } @Test public void testFeatureFlagVerification() throws Exception { when(mMockPkgMgr.hasSystemFeature(eq(PackageManager.FEATURE_IPSEC_TUNNELS))) .thenReturn(false); try { String addr = Inet4Address.getLoopbackAddress().getHostAddress(); mIpSecService.createTunnelInterface( addr, addr, new Network(0), new Binder(), "blessedPackage"); fail("Expected UnsupportedOperationException for disabled feature"); } catch (UnsupportedOperationException expected) { } } } Loading
core/java/android/net/IpSecManager.java +6 −0 Original line number Diff line number Diff line Loading @@ -19,11 +19,13 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresFeature; import android.annotation.RequiresPermission; import android.annotation.SystemApi; import android.annotation.SystemService; import android.annotation.TestApi; import android.content.Context; import android.content.pm.PackageManager; import android.os.Binder; import android.os.ParcelFileDescriptor; import android.os.RemoteException; Loading Loading @@ -749,6 +751,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void addAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { Loading @@ -771,6 +774,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void removeAddress(@NonNull InetAddress address, int prefixLen) throws IOException { try { Loading Loading @@ -886,6 +890,7 @@ public final class IpSecManager { */ @SystemApi @NonNull @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTunnelInterface createIpSecTunnelInterface(@NonNull InetAddress localAddress, @NonNull InetAddress remoteAddress, @NonNull Network underlyingNetwork) Loading Loading @@ -916,6 +921,7 @@ public final class IpSecManager { * @hide */ @SystemApi @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public void applyTunnelModeTransform(@NonNull IpSecTunnelInterface tunnel, @PolicyDirection int direction, @NonNull IpSecTransform transform) throws IOException { Loading
core/java/android/net/IpSecTransform.java +3 −0 Original line number Diff line number Diff line Loading @@ -21,9 +21,11 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.IntDef; import android.annotation.NonNull; import android.annotation.RequiresFeature; import android.annotation.RequiresPermission; import android.annotation.SystemApi; import android.content.Context; import android.content.pm.PackageManager; import android.os.Binder; import android.os.Handler; import android.os.IBinder; Loading Loading @@ -483,6 +485,7 @@ public final class IpSecTransform implements AutoCloseable { */ @SystemApi @NonNull @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS) @RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS) public IpSecTransform buildTunnelModeTransform( @NonNull InetAddress sourceAddress, Loading
services/core/java/com/android/server/IpSecService.java +13 −7 Original line number Diff line number Diff line Loading @@ -30,6 +30,7 @@ import static com.android.internal.util.Preconditions.checkNotNull; import android.annotation.NonNull; import android.app.AppOpsManager; import android.content.Context; import android.content.pm.PackageManager; import android.net.IIpSecService; import android.net.INetd; import android.net.IpSecAlgorithm; Loading Loading @@ -1276,7 +1277,7 @@ public class IpSecService extends IIpSecService.Stub { public synchronized IpSecTunnelInterfaceResponse createTunnelInterface( String localAddr, String remoteAddr, Network underlyingNetwork, IBinder binder, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); checkNotNull(binder, "Null Binder passed to createTunnelInterface"); checkNotNull(underlyingNetwork, "No underlying network was specified"); checkInetAddress(localAddr); Loading Loading @@ -1362,7 +1363,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void addAddressToTunnelInterface( int tunnelResourceId, LinkAddress localAddr, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); // Get tunnelInterface record; if no such interface is found, will throw Loading Loading @@ -1391,7 +1392,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void removeAddressFromTunnelInterface( int tunnelResourceId, LinkAddress localAddr, String callingPackage) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); // Get tunnelInterface record; if no such interface is found, will throw Loading Loading @@ -1420,7 +1421,7 @@ public class IpSecService extends IIpSecService.Stub { @Override public synchronized void deleteTunnelInterface( int resourceId, String callingPackage) throws RemoteException { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid()); releaseResource(userRecord.mTunnelInterfaceRecords, resourceId); } Loading Loading @@ -1549,7 +1550,12 @@ public class IpSecService extends IIpSecService.Stub { private static final String TUNNEL_OP = AppOpsManager.OPSTR_MANAGE_IPSEC_TUNNELS; private void enforceTunnelPermissions(String callingPackage) { private void enforceTunnelFeatureAndPermissions(String callingPackage) { if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_IPSEC_TUNNELS)) { throw new UnsupportedOperationException( "IPsec Tunnel Mode requires PackageManager.FEATURE_IPSEC_TUNNELS"); } checkNotNull(callingPackage, "Null calling package cannot create IpSec tunnels"); switch (getAppOpsManager().noteOp(TUNNEL_OP, Binder.getCallingUid(), callingPackage)) { case AppOpsManager.MODE_DEFAULT: Loading Loading @@ -1621,7 +1627,7 @@ public class IpSecService extends IIpSecService.Stub { IpSecConfig c, IBinder binder, String callingPackage) throws RemoteException { checkNotNull(c); if (c.getMode() == IpSecTransform.MODE_TUNNEL) { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); } checkIpSecConfig(c); checkNotNull(binder, "Null Binder passed to createTransform"); Loading Loading @@ -1729,7 +1735,7 @@ public class IpSecService extends IIpSecService.Stub { public synchronized void applyTunnelModeTransform( int tunnelResourceId, int direction, int transformResourceId, String callingPackage) throws RemoteException { enforceTunnelPermissions(callingPackage); enforceTunnelFeatureAndPermissions(callingPackage); checkDirection(direction); int callingUid = Binder.getCallingUid(); Loading
tests/net/java/com/android/server/IpSecServiceParameterizedTest.java +27 −0 Original line number Diff line number Diff line Loading @@ -32,6 +32,7 @@ import static org.mockito.Mockito.when; import android.app.AppOpsManager; import android.content.Context; import android.content.pm.PackageManager; import android.net.INetd; import android.net.IpSecAlgorithm; import android.net.IpSecConfig; Loading @@ -57,6 +58,7 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.junit.runners.Parameterized; import java.net.Inet4Address; import java.net.Socket; import java.util.Arrays; import java.util.Collection; Loading Loading @@ -118,6 +120,11 @@ public class IpSecServiceParameterizedTest { } } @Override public PackageManager getPackageManager() { return mMockPkgMgr; } @Override public void enforceCallingOrSelfPermission(String permission, String message) { if (permission == android.Manifest.permission.MANAGE_IPSEC_TUNNELS) { Loading @@ -128,6 +135,7 @@ public class IpSecServiceParameterizedTest { }; INetd mMockNetd; PackageManager mMockPkgMgr; IpSecService.IpSecServiceConfiguration mMockIpSecSrvConfig; IpSecService mIpSecService; Network fakeNetwork = new Network(0xAB); Loading @@ -152,11 +160,16 @@ public class IpSecServiceParameterizedTest { @Before public void setUp() throws Exception { mMockNetd = mock(INetd.class); mMockPkgMgr = mock(PackageManager.class); mMockIpSecSrvConfig = mock(IpSecService.IpSecServiceConfiguration.class); mIpSecService = new IpSecService(mMockContext, mMockIpSecSrvConfig); // Injecting mock netd when(mMockIpSecSrvConfig.getNetdInstance()).thenReturn(mMockNetd); // PackageManager should always return true (feature flag tests in IpSecServiceTest) when(mMockPkgMgr.hasSystemFeature(anyString())).thenReturn(true); // A package granted the AppOp for MANAGE_IPSEC_TUNNELS will be MODE_ALLOWED. when(mMockAppOps.noteOp(anyInt(), anyInt(), eq("blessedPackage"))) .thenReturn(AppOpsManager.MODE_ALLOWED); Loading Loading @@ -709,4 +722,18 @@ public class IpSecServiceParameterizedTest { } catch (SecurityException expected) { } } @Test public void testFeatureFlagVerification() throws Exception { when(mMockPkgMgr.hasSystemFeature(eq(PackageManager.FEATURE_IPSEC_TUNNELS))) .thenReturn(false); try { String addr = Inet4Address.getLoopbackAddress().getHostAddress(); mIpSecService.createTunnelInterface( addr, addr, new Network(0), new Binder(), "blessedPackage"); fail("Expected UnsupportedOperationException for disabled feature"); } catch (UnsupportedOperationException expected) { } } }