condition_util.cpp revision 17adac9cf3e03ad95372eb8657b26909d0414ac0
1/* 2 * Copyright (C) 2017 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#include "Log.h" 18 19#include "condition_util.h" 20 21#include <log/event_tag_map.h> 22#include <log/log_event_list.h> 23#include <log/logprint.h> 24#include <utils/Errors.h> 25#include <unordered_map> 26#include "../matchers/matcher_util.h" 27#include "ConditionTracker.h" 28#include "frameworks/base/cmds/statsd/src/statsd_config.pb.h" 29#include "stats_util.h" 30 31namespace android { 32namespace os { 33namespace statsd { 34 35using std::set; 36using std::string; 37using std::unordered_map; 38using std::vector; 39 40 41ConditionState evaluateCombinationCondition(const std::vector<int>& children, 42 const LogicalOperation& operation, 43 const std::vector<ConditionState>& conditionCache) { 44 ConditionState newCondition; 45 46 bool hasUnknown = false; 47 bool hasFalse = false; 48 bool hasTrue = false; 49 50 for (auto childIndex : children) { 51 ConditionState childState = conditionCache[childIndex]; 52 if (childState == ConditionState::kUnknown) { 53 hasUnknown = true; 54 break; 55 } 56 if (childState == ConditionState::kFalse) { 57 hasFalse = true; 58 } 59 if (childState == ConditionState::kTrue) { 60 hasTrue = true; 61 } 62 } 63 64 // If any child condition is in unknown state, the condition is unknown too. 65 if (hasUnknown) { 66 return ConditionState::kUnknown; 67 } 68 69 switch (operation) { 70 case LogicalOperation::AND: { 71 newCondition = hasFalse ? ConditionState::kFalse : ConditionState::kTrue; 72 break; 73 } 74 case LogicalOperation::OR: { 75 newCondition = hasTrue ? ConditionState::kTrue : ConditionState::kFalse; 76 break; 77 } 78 case LogicalOperation::NOT: 79 newCondition = (conditionCache[children[0]] == ConditionState::kFalse) 80 ? ConditionState::kTrue 81 : ConditionState::kFalse; 82 break; 83 case LogicalOperation::NAND: 84 newCondition = hasFalse ? ConditionState::kTrue : ConditionState::kFalse; 85 break; 86 case LogicalOperation::NOR: 87 newCondition = hasTrue ? ConditionState::kFalse : ConditionState::kTrue; 88 break; 89 } 90 return newCondition; 91} 92 93HashableDimensionKey getDimensionKeyForCondition(const LogEvent& event, 94 const EventConditionLink& link) { 95 vector<KeyMatcher> eventKey; 96 eventKey.reserve(link.key_in_main().size()); 97 98 for (const auto& key : link.key_in_main()) { 99 eventKey.push_back(key); 100 } 101 102 vector<KeyValuePair> dimensionKey = getDimensionKey(event, eventKey); 103 104 for (int i = 0; i < link.key_in_main_size(); i++) { 105 auto& kv = dimensionKey[i]; 106 kv.set_key(link.key_in_condition(i).key()); 107 } 108 109 return getHashableKey(dimensionKey); 110} 111 112} // namespace statsd 113} // namespace os 114} // namespace android 115