1 /*
2  * Copyright (C) 2014 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 com.android.cts.verifier.sensors;
18 
19 import com.android.compatibility.common.util.CddTest;
20 import com.android.cts.verifier.R;
21 import com.android.cts.verifier.sensors.base.SensorCtsVerifierTestActivity;
22 
23 import android.content.pm.PackageManager;
24 import android.hardware.Sensor;
25 import android.hardware.SensorManager;
26 import android.hardware.cts.helpers.TestSensorEnvironment;
27 import android.hardware.cts.helpers.sensoroperations.TestSensorOperation;
28 import android.hardware.cts.helpers.sensorverification.EventBasicVerification;
29 
30 import java.util.concurrent.TimeUnit;
31 
32 /**
33  * Activity that verifies batching capabilities for sensors
34  * (https://source.android.com/devices/sensors/batching.html).
35  *
36  * If a sensor supports the batching mode, FifoReservedEventCount for that sensor should be greater
37  * than one.
38  */
39 public class BatchingTestActivity extends SensorCtsVerifierTestActivity {
BatchingTestActivity()40     public BatchingTestActivity() {
41         super(BatchingTestActivity.class, true);
42     }
43 
44     private static final int SENSOR_BATCHING_RATE_US = SensorManager.SENSOR_DELAY_FASTEST;
45     private static final int REPORT_LATENCY_10_SEC = 10;
46     private static final int BATCHING_PADDING_TIME_S = 2;
47 
48     // we are testing sensors that only trigger based on external events, so leave enough time for
49     // such events to generate
50     private static final int REPORT_LATENCY_25_SEC = 25;
51 
52     // TODO: refactor to discover all available sensors of each type and dynamically generate test
53     // cases for all of them
54     @SuppressWarnings("unused")
testStepCounter_batching()55     public String testStepCounter_batching() throws Throwable {
56         return runBatchTest(
57                 Sensor.TYPE_STEP_COUNTER,
58                 REPORT_LATENCY_25_SEC,
59                 R.string.snsr_batching_walking_needed);
60     }
61 
62     @SuppressWarnings("unused")
testStepCounter_flush()63     public String testStepCounter_flush() throws Throwable {
64         return runFlushTest(
65                 Sensor.TYPE_STEP_COUNTER,
66                 REPORT_LATENCY_25_SEC,
67                 R.string.snsr_batching_walking_needed);
68     }
69 
70     @SuppressWarnings("unused")
testStepDetector_batching()71     public String testStepDetector_batching() throws Throwable {
72         return  runBatchTest(
73                 Sensor.TYPE_STEP_DETECTOR,
74                 REPORT_LATENCY_25_SEC,
75                 R.string.snsr_batching_walking_needed);
76     }
77 
78     @SuppressWarnings("unused")
testStepDetector_flush()79     public String testStepDetector_flush() throws Throwable {
80         return  runFlushTest(
81                 Sensor.TYPE_STEP_DETECTOR,
82                 REPORT_LATENCY_25_SEC,
83                 R.string.snsr_batching_walking_needed);
84     }
85 
86     @CddTest(requirement="7.3.8/C-1-1,C-1-2")
87     @SuppressWarnings("unused")
testProximity_batching()88     public String testProximity_batching() throws Throwable {
89         return runBatchTest(
90                 Sensor.TYPE_PROXIMITY,
91                 REPORT_LATENCY_10_SEC,
92                 R.string.snsr_interaction_needed_prox);
93     }
94 
95     @CddTest(requirement="7.3.8/C-1-1,C-1-2")
96     @SuppressWarnings("unused")
testProximity_flush()97     public String testProximity_flush() throws Throwable {
98         return runFlushTest(
99                 Sensor.TYPE_PROXIMITY,
100                 REPORT_LATENCY_10_SEC,
101                 R.string.snsr_interaction_needed_prox);
102     }
103 
104     @SuppressWarnings("unused")
testLight_batching()105     public String testLight_batching() throws Throwable {
106         return runBatchTest(
107                 Sensor.TYPE_LIGHT,
108                 REPORT_LATENCY_10_SEC,
109                 R.string.snsr_interaction_needed);
110     }
111 
112     @SuppressWarnings("unused")
testLight_flush()113     public String testLight_flush() throws Throwable {
114         return runFlushTest(
115                 Sensor.TYPE_LIGHT,
116                 REPORT_LATENCY_10_SEC,
117                 R.string.snsr_interaction_needed);
118     }
119 
runBatchTest(int sensorType, int maxBatchReportLatencySec, int instructionsResId)120     private String runBatchTest(int sensorType, int maxBatchReportLatencySec, int instructionsResId)
121             throws Throwable {
122 
123         setFirstExecutionInstruction(instructionsResId);
124 
125         int maxBatchReportLatencyUs = (int) TimeUnit.SECONDS.toMicros(maxBatchReportLatencySec);
126         TestSensorEnvironment environment = new TestSensorEnvironment(
127                 getApplicationContext(),
128                 sensorType,
129                 SENSOR_BATCHING_RATE_US,
130                 maxBatchReportLatencyUs);
131 
132         int testDurationSec = maxBatchReportLatencySec + BATCHING_PADDING_TIME_S;
133         TestSensorOperation operation =
134                 TestSensorOperation.createOperation(environment, testDurationSec,TimeUnit.SECONDS);
135 
136         // Expect at least 2 events (for on-change: initial value + changed value; for step sensors
137         // multiple values for walking).
138         EventBasicVerification verification =
139                 new EventBasicVerification(2 /* expectedMinNumEvent */, environment.getSensor());
140         operation.addVerification(verification);
141 
142         return executeTest(operation);
143     }
144 
runFlushTest(int sensorType, int maxBatchReportLatencySec, int instructionsResId)145     private String runFlushTest(int sensorType, int maxBatchReportLatencySec, int instructionsResId)
146             throws Throwable {
147 
148         setFirstExecutionInstruction(instructionsResId);
149 
150         int maxBatchReportLatencyUs = (int) TimeUnit.SECONDS.toMicros(maxBatchReportLatencySec);
151         TestSensorEnvironment environment = new TestSensorEnvironment(
152                 getApplicationContext(),
153                 sensorType,
154                 SENSOR_BATCHING_RATE_US,
155                 maxBatchReportLatencyUs);
156 
157         int flushDurationSec = maxBatchReportLatencySec / 2;
158         TestSensorOperation operation = TestSensorOperation
159                 .createFlushOperation(environment, flushDurationSec, TimeUnit.SECONDS);
160         return executeTest(operation);
161     }
162 
executeTest(TestSensorOperation operation)163     private String executeTest(TestSensorOperation operation) throws Exception {
164         operation.addDefaultVerifications();
165         operation.execute(getCurrentTestNode());
166         return null;
167     }
168 }
169