blob: 705804fef5605fd61023152b1533dc20a908f64e [file] [log] [blame]
Yao Chen967b2052017-11-07 16:36:43 -08001// Copyright (C) 2017 The Android Open Source Project
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14#include "src/condition/SimpleConditionTracker.h"
15
16#include <gmock/gmock.h>
17#include <gtest/gtest.h>
18#include <stdio.h>
19#include <vector>
Yangster-mac20877162017-12-22 17:19:39 -080020#include <numeric>
Yao Chen967b2052017-11-07 16:36:43 -080021
22using std::map;
23using std::unordered_map;
24using std::vector;
25
26#ifdef __ANDROID__
27
28namespace android {
29namespace os {
30namespace statsd {
31
Yao Chenb3561512017-11-21 18:07:17 -080032const ConfigKey kConfigKey(0, "test");
33
Yangster-mac20877162017-12-22 17:19:39 -080034const int ATTRIBUTION_NODE_FIELD_ID = 1;
35const int ATTRIBUTION_UID_FIELD_ID = 1;
36const int TAG_ID = 1;
37
Stefan Lafon12d01fa2017-12-04 20:56:09 -080038SimplePredicate getWakeLockHeldCondition(bool countNesting, bool defaultFalse,
Yangster-mac20877162017-12-22 17:19:39 -080039 bool outputSlicedUid, Position position) {
Stefan Lafon12d01fa2017-12-04 20:56:09 -080040 SimplePredicate simplePredicate;
41 simplePredicate.set_start("WAKE_LOCK_ACQUIRE");
42 simplePredicate.set_stop("WAKE_LOCK_RELEASE");
43 simplePredicate.set_stop_all("RELEASE_ALL");
Yao Chen967b2052017-11-07 16:36:43 -080044 if (outputSlicedUid) {
Yangster-mac20877162017-12-22 17:19:39 -080045 simplePredicate.mutable_dimensions()->set_field(TAG_ID);
46 simplePredicate.mutable_dimensions()->add_child()->set_field(ATTRIBUTION_NODE_FIELD_ID);
47 simplePredicate.mutable_dimensions()->mutable_child(0)->set_position(position);
48 simplePredicate.mutable_dimensions()->mutable_child(0)->add_child()->set_field(
49 ATTRIBUTION_UID_FIELD_ID);
Yao Chen967b2052017-11-07 16:36:43 -080050 }
51
Stefan Lafon12d01fa2017-12-04 20:56:09 -080052 simplePredicate.set_count_nesting(countNesting);
53 simplePredicate.set_initial_value(defaultFalse ? SimplePredicate_InitialValue_FALSE
54 : SimplePredicate_InitialValue_UNKNOWN);
55 return simplePredicate;
Yao Chen967b2052017-11-07 16:36:43 -080056}
57
Yangster-mac20877162017-12-22 17:19:39 -080058void writeAttributionNodesToEvent(LogEvent* event, const std::vector<int> &uids) {
59 std::vector<AttributionNode> nodes;
60 for (size_t i = 0; i < uids.size(); ++i) {
61 AttributionNode node;
62 node.set_uid(uids[i]);
63 nodes.push_back(node);
64 }
65 event->write(nodes); // attribution chain.
66}
67
68void makeWakeLockEvent(
69 LogEvent* event, const std::vector<int> &uids, const string& wl, int acquire) {
70 writeAttributionNodesToEvent(event, uids);
Yao Chen80235402017-11-13 20:42:25 -080071 event->write(wl);
72 event->write(acquire);
Yao Chen967b2052017-11-07 16:36:43 -080073 event->init();
74}
75
Yangster-mac20877162017-12-22 17:19:39 -080076std::map<string, std::vector<HashableDimensionKey>> getWakeLockQueryKey(
77 const Position position,
78 const std::vector<int> &uids, const string& conditionName) {
79 std::map<string, std::vector<HashableDimensionKey>> outputKeyMap;
80 std::vector<int> uid_indexes;
81 switch(position) {
82 case Position::FIRST:
83 uid_indexes.push_back(0);
84 break;
85 case Position::LAST:
86 uid_indexes.push_back(uids.size() - 1);
87 break;
88 case Position::ANY:
89 uid_indexes.resize(uids.size());
90 std::iota(uid_indexes.begin(), uid_indexes.end(), 0);
91 break;
92 default:
93 break;
94 }
95
96 for (const int idx : uid_indexes) {
97 DimensionsValue dimensionsValue;
98 dimensionsValue.set_field(TAG_ID);
99 dimensionsValue.mutable_value_tuple()->add_dimensions_value()->set_field(ATTRIBUTION_NODE_FIELD_ID);
100 dimensionsValue.mutable_value_tuple()->mutable_dimensions_value(0)
101 ->mutable_value_tuple()->add_dimensions_value()->set_field(ATTRIBUTION_NODE_FIELD_ID);
102 dimensionsValue.mutable_value_tuple()->mutable_dimensions_value(0)
103 ->mutable_value_tuple()->mutable_dimensions_value(0)->set_value_int(uids[idx]);
104 outputKeyMap[conditionName].push_back(HashableDimensionKey(dimensionsValue));
105 }
106 return outputKeyMap;
Yao Chen967b2052017-11-07 16:36:43 -0800107}
108
109TEST(SimpleConditionTrackerTest, TestNonSlicedCondition) {
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800110 SimplePredicate simplePredicate;
111 simplePredicate.set_start("SCREEN_TURNED_ON");
112 simplePredicate.set_stop("SCREEN_TURNED_OFF");
113 simplePredicate.set_count_nesting(false);
114 simplePredicate.set_initial_value(SimplePredicate_InitialValue_UNKNOWN);
Yao Chen967b2052017-11-07 16:36:43 -0800115
116 unordered_map<string, int> trackerNameIndexMap;
117 trackerNameIndexMap["SCREEN_TURNED_ON"] = 0;
118 trackerNameIndexMap["SCREEN_TURNED_OFF"] = 1;
119
Yao Chenb3561512017-11-21 18:07:17 -0800120 SimpleConditionTracker conditionTracker(kConfigKey, "SCREEN_IS_ON", 0 /*tracker index*/,
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800121 simplePredicate, trackerNameIndexMap);
Yao Chen967b2052017-11-07 16:36:43 -0800122
123 LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
124
125 vector<MatchingState> matcherState;
126 matcherState.push_back(MatchingState::kNotMatched);
127 matcherState.push_back(MatchingState::kNotMatched);
128
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800129 vector<sp<ConditionTracker>> allPredicates;
Yao Chen967b2052017-11-07 16:36:43 -0800130 vector<ConditionState> conditionCache(1, ConditionState::kNotEvaluated);
131 vector<bool> changedCache(1, false);
132
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800133 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800134 changedCache);
135 // not matched start or stop. condition doesn't change
136 EXPECT_EQ(ConditionState::kUnknown, conditionCache[0]);
137 EXPECT_FALSE(changedCache[0]);
138
139 // prepare a case for match start.
140 matcherState.clear();
141 matcherState.push_back(MatchingState::kMatched);
142 matcherState.push_back(MatchingState::kNotMatched);
143 conditionCache[0] = ConditionState::kNotEvaluated;
144 changedCache[0] = false;
145
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800146 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800147 changedCache);
148 // now condition should change to true.
149 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
150 EXPECT_TRUE(changedCache[0]);
151
Yao Chend41c4222017-11-15 19:26:14 -0800152 // match nothing.
153 matcherState.clear();
154 matcherState.push_back(MatchingState::kNotMatched);
155 matcherState.push_back(MatchingState::kNotMatched);
156 conditionCache[0] = ConditionState::kNotEvaluated;
157 changedCache[0] = false;
158
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800159 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chend41c4222017-11-15 19:26:14 -0800160 changedCache);
161 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
162 EXPECT_FALSE(changedCache[0]);
163
Yao Chen967b2052017-11-07 16:36:43 -0800164 // the case for match stop.
165 matcherState.clear();
166 matcherState.push_back(MatchingState::kNotMatched);
167 matcherState.push_back(MatchingState::kMatched);
168 conditionCache[0] = ConditionState::kNotEvaluated;
169 changedCache[0] = false;
170
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800171 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800172 changedCache);
173
174 // condition changes to false.
175 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
176 EXPECT_TRUE(changedCache[0]);
177
178 // match stop again.
179 matcherState.clear();
180 matcherState.push_back(MatchingState::kNotMatched);
181 matcherState.push_back(MatchingState::kMatched);
182 conditionCache[0] = ConditionState::kNotEvaluated;
183 changedCache[0] = false;
184
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800185 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800186 changedCache);
187 // condition should still be false. not changed.
188 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
189 EXPECT_FALSE(changedCache[0]);
190}
191
192TEST(SimpleConditionTrackerTest, TestNonSlicedConditionNestCounting) {
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800193 SimplePredicate simplePredicate;
194 simplePredicate.set_start("SCREEN_TURNED_ON");
195 simplePredicate.set_stop("SCREEN_TURNED_OFF");
196 simplePredicate.set_count_nesting(true);
Yao Chen967b2052017-11-07 16:36:43 -0800197
198 unordered_map<string, int> trackerNameIndexMap;
199 trackerNameIndexMap["SCREEN_TURNED_ON"] = 0;
200 trackerNameIndexMap["SCREEN_TURNED_OFF"] = 1;
201
Yao Chenb3561512017-11-21 18:07:17 -0800202 SimpleConditionTracker conditionTracker(kConfigKey, "SCREEN_IS_ON",
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800203 0 /*condition tracker index*/, simplePredicate,
Yao Chenb3561512017-11-21 18:07:17 -0800204 trackerNameIndexMap);
Yao Chen967b2052017-11-07 16:36:43 -0800205
206 LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
207
208 // one matched start
209 vector<MatchingState> matcherState;
210 matcherState.push_back(MatchingState::kMatched);
211 matcherState.push_back(MatchingState::kNotMatched);
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800212 vector<sp<ConditionTracker>> allPredicates;
Yao Chen967b2052017-11-07 16:36:43 -0800213 vector<ConditionState> conditionCache(1, ConditionState::kNotEvaluated);
214 vector<bool> changedCache(1, false);
215
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800216 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800217 changedCache);
218
219 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
220 EXPECT_TRUE(changedCache[0]);
221
222 // prepare for another matched start.
223 matcherState.clear();
224 matcherState.push_back(MatchingState::kMatched);
225 matcherState.push_back(MatchingState::kNotMatched);
226 conditionCache[0] = ConditionState::kNotEvaluated;
227 changedCache[0] = false;
228
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800229 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800230 changedCache);
231
232 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
233 EXPECT_FALSE(changedCache[0]);
234
235 // ONE MATCHED STOP
236 matcherState.clear();
237 matcherState.push_back(MatchingState::kNotMatched);
238 matcherState.push_back(MatchingState::kMatched);
239 conditionCache[0] = ConditionState::kNotEvaluated;
240 changedCache[0] = false;
241
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800242 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800243 changedCache);
244 // result should still be true
245 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
246 EXPECT_FALSE(changedCache[0]);
247
248 // ANOTHER MATCHED STOP
249 matcherState.clear();
250 matcherState.push_back(MatchingState::kNotMatched);
251 matcherState.push_back(MatchingState::kMatched);
252 conditionCache[0] = ConditionState::kNotEvaluated;
253 changedCache[0] = false;
254
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800255 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800256 changedCache);
257 // result should still be true
258 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
259 EXPECT_TRUE(changedCache[0]);
260}
261
262TEST(SimpleConditionTrackerTest, TestSlicedCondition) {
Yangster-mac20877162017-12-22 17:19:39 -0800263 for (Position position :
264 { Position::ANY, Position::FIRST, Position::LAST}) {
265 SimplePredicate simplePredicate = getWakeLockHeldCondition(
266 true /*nesting*/, true /*default to false*/, true /*output slice by uid*/,
267 position);
268 string conditionName = "WL_HELD_BY_UID2";
Yao Chen967b2052017-11-07 16:36:43 -0800269
Yangster-mac20877162017-12-22 17:19:39 -0800270 unordered_map<string, int> trackerNameIndexMap;
271 trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
272 trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
273 trackerNameIndexMap["RELEASE_ALL"] = 2;
Yao Chen967b2052017-11-07 16:36:43 -0800274
Yangster-mac20877162017-12-22 17:19:39 -0800275 SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
276 0 /*condition tracker index*/, simplePredicate,
277 trackerNameIndexMap);
278 std::vector<int> uids = {111, 222, 333};
Yao Chen967b2052017-11-07 16:36:43 -0800279
Yangster-mac20877162017-12-22 17:19:39 -0800280 LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
281 makeWakeLockEvent(&event, uids, "wl1", 1);
Yao Chen967b2052017-11-07 16:36:43 -0800282
Yangster-mac20877162017-12-22 17:19:39 -0800283 // one matched start
284 vector<MatchingState> matcherState;
285 matcherState.push_back(MatchingState::kMatched);
286 matcherState.push_back(MatchingState::kNotMatched);
287 matcherState.push_back(MatchingState::kNotMatched);
288 vector<sp<ConditionTracker>> allPredicates;
289 vector<ConditionState> conditionCache(1, ConditionState::kNotEvaluated);
290 vector<bool> changedCache(1, false);
Yao Chen967b2052017-11-07 16:36:43 -0800291
Yangster-mac20877162017-12-22 17:19:39 -0800292 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
293 changedCache);
Yao Chen967b2052017-11-07 16:36:43 -0800294
Yangster-mac20877162017-12-22 17:19:39 -0800295 if (position == Position::FIRST ||
296 position == Position::LAST) {
297 EXPECT_EQ(1UL, conditionTracker.mSlicedConditionState.size());
298 } else {
299 EXPECT_EQ(uids.size(), conditionTracker.mSlicedConditionState.size());
300 }
301 EXPECT_TRUE(changedCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800302
Yangster-mac20877162017-12-22 17:19:39 -0800303 // Now test query
304 const auto queryKey = getWakeLockQueryKey(position, uids, conditionName);
305 conditionCache[0] = ConditionState::kNotEvaluated;
Yao Chen967b2052017-11-07 16:36:43 -0800306
Yangster-mac20877162017-12-22 17:19:39 -0800307 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
308 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800309
Yangster-mac20877162017-12-22 17:19:39 -0800310 // another wake lock acquired by this uid
311 LogEvent event2(1 /*tagId*/, 0 /*timestamp*/);
312 makeWakeLockEvent(&event2, uids, "wl2", 1);
313 matcherState.clear();
314 matcherState.push_back(MatchingState::kMatched);
315 matcherState.push_back(MatchingState::kNotMatched);
316 conditionCache[0] = ConditionState::kNotEvaluated;
317 changedCache[0] = false;
318 conditionTracker.evaluateCondition(event2, matcherState, allPredicates, conditionCache,
319 changedCache);
320 EXPECT_FALSE(changedCache[0]);
321 if (position == Position::FIRST ||
322 position == Position::LAST) {
323 EXPECT_EQ(1UL, conditionTracker.mSlicedConditionState.size());
324 } else {
325 EXPECT_EQ(uids.size(), conditionTracker.mSlicedConditionState.size());
326 }
Yao Chen967b2052017-11-07 16:36:43 -0800327
Yangster-mac20877162017-12-22 17:19:39 -0800328 // wake lock 1 release
329 LogEvent event3(1 /*tagId*/, 0 /*timestamp*/);
330 makeWakeLockEvent(&event3, uids, "wl1", 0); // now release it.
331 matcherState.clear();
332 matcherState.push_back(MatchingState::kNotMatched);
333 matcherState.push_back(MatchingState::kMatched);
334 conditionCache[0] = ConditionState::kNotEvaluated;
335 changedCache[0] = false;
336 conditionTracker.evaluateCondition(event3, matcherState, allPredicates, conditionCache,
337 changedCache);
338 // nothing changes, because wake lock 2 is still held for this uid
339 EXPECT_FALSE(changedCache[0]);
340 if (position == Position::FIRST ||
341 position == Position::LAST) {
342 EXPECT_EQ(1UL, conditionTracker.mSlicedConditionState.size());
343 } else {
344 EXPECT_EQ(uids.size(), conditionTracker.mSlicedConditionState.size());
345 }
Yao Chen967b2052017-11-07 16:36:43 -0800346
Yangster-mac20877162017-12-22 17:19:39 -0800347 LogEvent event4(1 /*tagId*/, 0 /*timestamp*/);
348 makeWakeLockEvent(&event4, uids, "wl2", 0); // now release it.
349 matcherState.clear();
350 matcherState.push_back(MatchingState::kNotMatched);
351 matcherState.push_back(MatchingState::kMatched);
352 conditionCache[0] = ConditionState::kNotEvaluated;
353 changedCache[0] = false;
354 conditionTracker.evaluateCondition(event4, matcherState, allPredicates, conditionCache,
355 changedCache);
356 EXPECT_EQ(0UL, conditionTracker.mSlicedConditionState.size());
357 EXPECT_TRUE(changedCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800358
Yangster-mac20877162017-12-22 17:19:39 -0800359 // query again
360 conditionCache[0] = ConditionState::kNotEvaluated;
361 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
362 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
363
364 }
365
Yao Chen967b2052017-11-07 16:36:43 -0800366}
367
368TEST(SimpleConditionTrackerTest, TestSlicedWithNoOutputDim) {
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800369 SimplePredicate simplePredicate = getWakeLockHeldCondition(
Yangster-mac20877162017-12-22 17:19:39 -0800370 true /*nesting*/, true /*default to false*/, false /*slice output by uid*/,
371 Position::ANY /* position */);
Yao Chen967b2052017-11-07 16:36:43 -0800372 string conditionName = "WL_HELD";
373
374 unordered_map<string, int> trackerNameIndexMap;
375 trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
376 trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
377 trackerNameIndexMap["RELEASE_ALL"] = 2;
378
Yao Chenb3561512017-11-21 18:07:17 -0800379 SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800380 0 /*condition tracker index*/, simplePredicate,
Yao Chenb3561512017-11-21 18:07:17 -0800381 trackerNameIndexMap);
Yangster-mac20877162017-12-22 17:19:39 -0800382
383 std::vector<int> uid_list1 = {111, 1111, 11111};
Yao Chen967b2052017-11-07 16:36:43 -0800384 string uid1_wl1 = "wl1_1";
Yangster-mac20877162017-12-22 17:19:39 -0800385 std::vector<int> uid_list2 = {222, 2222, 22222};
Yao Chen967b2052017-11-07 16:36:43 -0800386 string uid2_wl1 = "wl2_1";
387
388 LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
Yangster-mac20877162017-12-22 17:19:39 -0800389 makeWakeLockEvent(&event, uid_list1, uid1_wl1, 1);
Yao Chen967b2052017-11-07 16:36:43 -0800390
391 // one matched start for uid1
392 vector<MatchingState> matcherState;
393 matcherState.push_back(MatchingState::kMatched);
394 matcherState.push_back(MatchingState::kNotMatched);
Yao Chen99752052017-11-27 11:40:45 -0800395 matcherState.push_back(MatchingState::kNotMatched);
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800396 vector<sp<ConditionTracker>> allPredicates;
Yao Chen967b2052017-11-07 16:36:43 -0800397 vector<ConditionState> conditionCache(1, ConditionState::kNotEvaluated);
398 vector<bool> changedCache(1, false);
399
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800400 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800401 changedCache);
402
403 EXPECT_EQ(1UL, conditionTracker.mSlicedConditionState.size());
404 EXPECT_TRUE(changedCache[0]);
405
406 // Now test query
Yangster-mac20877162017-12-22 17:19:39 -0800407 ConditionKey queryKey;
Yao Chen967b2052017-11-07 16:36:43 -0800408 conditionCache[0] = ConditionState::kNotEvaluated;
409
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800410 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
Yao Chen967b2052017-11-07 16:36:43 -0800411 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
412
413 // another wake lock acquired by this uid
414 LogEvent event2(1 /*tagId*/, 0 /*timestamp*/);
Yangster-mac20877162017-12-22 17:19:39 -0800415 makeWakeLockEvent(&event2, uid_list2, uid2_wl1, 1);
Yao Chen967b2052017-11-07 16:36:43 -0800416 matcherState.clear();
417 matcherState.push_back(MatchingState::kMatched);
418 matcherState.push_back(MatchingState::kNotMatched);
419 conditionCache[0] = ConditionState::kNotEvaluated;
420 changedCache[0] = false;
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800421 conditionTracker.evaluateCondition(event2, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800422 changedCache);
423 EXPECT_FALSE(changedCache[0]);
424
425 // uid1 wake lock 1 release
426 LogEvent event3(1 /*tagId*/, 0 /*timestamp*/);
Yangster-mac20877162017-12-22 17:19:39 -0800427 makeWakeLockEvent(&event3, uid_list1, uid1_wl1, 0); // now release it.
Yao Chen967b2052017-11-07 16:36:43 -0800428 matcherState.clear();
429 matcherState.push_back(MatchingState::kNotMatched);
430 matcherState.push_back(MatchingState::kMatched);
431 conditionCache[0] = ConditionState::kNotEvaluated;
432 changedCache[0] = false;
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800433 conditionTracker.evaluateCondition(event3, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800434 changedCache);
435 // nothing changes, because uid2 is still holding wl.
436 EXPECT_FALSE(changedCache[0]);
437
438 LogEvent event4(1 /*tagId*/, 0 /*timestamp*/);
Yangster-mac20877162017-12-22 17:19:39 -0800439 makeWakeLockEvent(&event4, uid_list2, uid2_wl1, 0); // now release it.
Yao Chen967b2052017-11-07 16:36:43 -0800440 matcherState.clear();
441 matcherState.push_back(MatchingState::kNotMatched);
442 matcherState.push_back(MatchingState::kMatched);
443 conditionCache[0] = ConditionState::kNotEvaluated;
444 changedCache[0] = false;
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800445 conditionTracker.evaluateCondition(event4, matcherState, allPredicates, conditionCache,
Yao Chen967b2052017-11-07 16:36:43 -0800446 changedCache);
447 EXPECT_EQ(0UL, conditionTracker.mSlicedConditionState.size());
448 EXPECT_TRUE(changedCache[0]);
449
450 // query again
451 conditionCache[0] = ConditionState::kNotEvaluated;
Stefan Lafon12d01fa2017-12-04 20:56:09 -0800452 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
Yao Chen967b2052017-11-07 16:36:43 -0800453 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
454}
455
456TEST(SimpleConditionTrackerTest, TestStopAll) {
Yangster-mac20877162017-12-22 17:19:39 -0800457 for (Position position :
458 {Position::ANY, Position::FIRST, Position::LAST}) {
459 SimplePredicate simplePredicate = getWakeLockHeldCondition(
460 true /*nesting*/, true /*default to false*/, true /*output slice by uid*/,
461 position);
462 string conditionName = "WL_HELD_BY_UID3";
Yao Chen967b2052017-11-07 16:36:43 -0800463
Yangster-mac20877162017-12-22 17:19:39 -0800464 unordered_map<string, int> trackerNameIndexMap;
465 trackerNameIndexMap["WAKE_LOCK_ACQUIRE"] = 0;
466 trackerNameIndexMap["WAKE_LOCK_RELEASE"] = 1;
467 trackerNameIndexMap["RELEASE_ALL"] = 2;
Yao Chen967b2052017-11-07 16:36:43 -0800468
Yangster-mac20877162017-12-22 17:19:39 -0800469 SimpleConditionTracker conditionTracker(kConfigKey, conditionName,
470 0 /*condition tracker index*/, simplePredicate,
471 trackerNameIndexMap);
Yao Chen967b2052017-11-07 16:36:43 -0800472
Yangster-mac20877162017-12-22 17:19:39 -0800473 std::vector<int> uid_list1 = {111, 1111, 11111};
474 std::vector<int> uid_list2 = {222, 2222, 22222};
Yao Chen967b2052017-11-07 16:36:43 -0800475
Yangster-mac20877162017-12-22 17:19:39 -0800476 LogEvent event(1 /*tagId*/, 0 /*timestamp*/);
477 makeWakeLockEvent(&event, uid_list1, "wl1", 1);
Yao Chen967b2052017-11-07 16:36:43 -0800478
Yangster-mac20877162017-12-22 17:19:39 -0800479 // one matched start
480 vector<MatchingState> matcherState;
481 matcherState.push_back(MatchingState::kMatched);
482 matcherState.push_back(MatchingState::kNotMatched);
483 matcherState.push_back(MatchingState::kNotMatched);
484 vector<sp<ConditionTracker>> allPredicates;
485 vector<ConditionState> conditionCache(1, ConditionState::kNotEvaluated);
486 vector<bool> changedCache(1, false);
Yao Chen967b2052017-11-07 16:36:43 -0800487
Yangster-mac20877162017-12-22 17:19:39 -0800488 conditionTracker.evaluateCondition(event, matcherState, allPredicates, conditionCache,
489 changedCache);
490 if (position == Position::FIRST ||
491 position == Position::LAST) {
492 EXPECT_EQ(1UL, conditionTracker.mSlicedConditionState.size());
493 } else {
494 EXPECT_EQ(uid_list1.size(), conditionTracker.mSlicedConditionState.size());
495 }
496 EXPECT_TRUE(changedCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800497
Yangster-mac20877162017-12-22 17:19:39 -0800498 // Now test query
499 const auto queryKey = getWakeLockQueryKey(position, uid_list1, conditionName);
500 conditionCache[0] = ConditionState::kNotEvaluated;
Yao Chen967b2052017-11-07 16:36:43 -0800501
Yangster-mac20877162017-12-22 17:19:39 -0800502 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
503 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800504
Yangster-mac20877162017-12-22 17:19:39 -0800505 // another wake lock acquired by uid2
506 LogEvent event2(1 /*tagId*/, 0 /*timestamp*/);
507 makeWakeLockEvent(&event2, uid_list2, "wl2", 1);
508 matcherState.clear();
509 matcherState.push_back(MatchingState::kMatched);
510 matcherState.push_back(MatchingState::kNotMatched);
511 matcherState.push_back(MatchingState::kNotMatched);
512 conditionCache[0] = ConditionState::kNotEvaluated;
513 changedCache[0] = false;
514 conditionTracker.evaluateCondition(event2, matcherState, allPredicates, conditionCache,
515 changedCache);
516 if (position == Position::FIRST ||
517 position == Position::LAST) {
518 EXPECT_EQ(2UL, conditionTracker.mSlicedConditionState.size());
519 } else {
520 EXPECT_EQ(uid_list1.size() + uid_list2.size(),
521 conditionTracker.mSlicedConditionState.size());
522 }
523 EXPECT_TRUE(changedCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800524
Yangster-mac20877162017-12-22 17:19:39 -0800525 // TEST QUERY
526 const auto queryKey2 = getWakeLockQueryKey(position, uid_list2, conditionName);
527 conditionCache[0] = ConditionState::kNotEvaluated;
Yao Chen967b2052017-11-07 16:36:43 -0800528
Yangster-mac20877162017-12-22 17:19:39 -0800529 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
530 EXPECT_EQ(ConditionState::kTrue, conditionCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800531
532
Yangster-mac20877162017-12-22 17:19:39 -0800533 // stop all event
534 LogEvent event3(2 /*tagId*/, 0 /*timestamp*/);
535 matcherState.clear();
536 matcherState.push_back(MatchingState::kNotMatched);
537 matcherState.push_back(MatchingState::kNotMatched);
538 matcherState.push_back(MatchingState::kMatched);
Yao Chen967b2052017-11-07 16:36:43 -0800539
Yangster-mac20877162017-12-22 17:19:39 -0800540 conditionCache[0] = ConditionState::kNotEvaluated;
541 changedCache[0] = false;
542 conditionTracker.evaluateCondition(event3, matcherState, allPredicates, conditionCache,
543 changedCache);
544 EXPECT_TRUE(changedCache[0]);
545 EXPECT_EQ(0UL, conditionTracker.mSlicedConditionState.size());
Yao Chen967b2052017-11-07 16:36:43 -0800546
Yangster-mac20877162017-12-22 17:19:39 -0800547 // TEST QUERY
548 const auto queryKey3 = getWakeLockQueryKey(position, uid_list1, conditionName);
549 conditionCache[0] = ConditionState::kNotEvaluated;
Yao Chen967b2052017-11-07 16:36:43 -0800550
Yangster-mac20877162017-12-22 17:19:39 -0800551 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
552 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
Yao Chen967b2052017-11-07 16:36:43 -0800553
Yangster-mac20877162017-12-22 17:19:39 -0800554 // TEST QUERY
555 const auto queryKey4 = getWakeLockQueryKey(position, uid_list2, conditionName);
556 conditionCache[0] = ConditionState::kNotEvaluated;
Yao Chen967b2052017-11-07 16:36:43 -0800557
Yangster-mac20877162017-12-22 17:19:39 -0800558 conditionTracker.isConditionMet(queryKey, allPredicates, conditionCache);
559 EXPECT_EQ(ConditionState::kFalse, conditionCache[0]);
560 }
561
Yao Chen967b2052017-11-07 16:36:43 -0800562}
563
564} // namespace statsd
565} // namespace os
566} // namespace android
567#else
568GTEST_LOG_(INFO) << "This test does nothing.\n";
569#endif