1 /*
2  * Copyright (C) 2023 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 android.security.cts.CVE_2023_21251;
18 
19 import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
20 
21 import static com.android.internal.net.VpnConfig.DIALOGS_PACKAGE;
22 
23 import static org.junit.Assert.assertFalse;
24 import static org.junit.Assume.assumeNoException;
25 import static org.junit.Assume.assumeNotNull;
26 import static org.junit.Assume.assumeTrue;
27 
28 import android.app.Instrumentation;
29 import android.content.BroadcastReceiver;
30 import android.content.Context;
31 import android.content.Intent;
32 import android.content.IntentFilter;
33 
34 import androidx.test.runner.AndroidJUnit4;
35 import androidx.test.uiautomator.By;
36 import androidx.test.uiautomator.UiDevice;
37 import androidx.test.uiautomator.UiObject2;
38 import androidx.test.uiautomator.Until;
39 
40 import org.junit.Test;
41 import org.junit.runner.RunWith;
42 
43 import java.util.concurrent.Semaphore;
44 import java.util.concurrent.TimeUnit;
45 
46 @RunWith(AndroidJUnit4.class)
47 public class DeviceTest {
48 
49     @Test
testPocCVE_2023_21251()50     public void testPocCVE_2023_21251() {
51         try {
52             Instrumentation instrumentation = getInstrumentation();
53             Context context = instrumentation.getTargetContext();
54 
55             // Registering a broadcast receiver to wait for PocActivity to start
56             Semaphore broadcastReceived = new Semaphore(0);
57             BroadcastReceiver broadcastReceiver =
58                     new BroadcastReceiver() {
59                         @Override
60                         public void onReceive(Context context, Intent intent) {
61                             try {
62                                 broadcastReceived.release();
63                             } catch (Exception ignore) {
64                                 // ignore
65                             }
66                         }
67                     };
68             IntentFilter broadcastFilter =
69                     new IntentFilter(context.getString(R.string.broadcastAction));
70             context.registerReceiver(broadcastReceiver, broadcastFilter);
71 
72             // Start and wait for PocActivity to be launched
73             Intent intent =
74                     new Intent(context, PocActivity.class).setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
75             context.startActivity(intent);
76             final int timeout = 10000;
77             assumeTrue(
78                     context.getString(R.string.activityNotStarted),
79                     broadcastReceived.tryAcquire(timeout, TimeUnit.MILLISECONDS));
80 
81             // Wait for the ConfirmDialog window to be launched
82             final UiDevice uiDevice = UiDevice.getInstance(instrumentation);
83             UiObject2 uiObject =
84                     uiDevice.wait(Until.findObject(By.pkg(DIALOGS_PACKAGE)
85                             .res(DIALOGS_PACKAGE, context.getString(R.string.resId))),
86                             timeout);
87             assumeNotNull(context.getString(R.string.confirmDialogNotAppeared), uiObject);
88 
89             // With fix, uiobject's text field contains html syntax.
90             final String lineSeparator = System.lineSeparator();
91             final String decodedHtml =
92                     context.getString(R.string.bugIdDecoded, lineSeparator, lineSeparator);
93             assertFalse(
94                     context.getString(R.string.failMessage),
95                     uiObject.getText().contains(decodedHtml));
96         } catch (Exception e) {
97             assumeNoException(e);
98         }
99     }
100 }
101