diff --git a/services/core/java/com/android/server/integrity/engine/RuleEvaluationEngine.java b/services/core/java/com/android/server/integrity/engine/RuleEvaluationEngine.java index fc4430640b900..93b2c55d47358 100644 --- a/services/core/java/com/android/server/integrity/engine/RuleEvaluationEngine.java +++ b/services/core/java/com/android/server/integrity/engine/RuleEvaluationEngine.java @@ -16,6 +16,10 @@ package com.android.server.integrity.engine; +import android.util.Slog; + +import com.android.server.integrity.model.AppInstallMetadata; +import com.android.server.integrity.model.IntegrityCheckResult; import com.android.server.integrity.model.Rule; import java.util.ArrayList; @@ -24,8 +28,8 @@ import java.util.List; /** * The engine used to evaluate rules against app installs. * - *

Every app install is evaluated against rules (pushed by the verifier) by the evaluation engine - * to allow/block that install. + *

Every app install is evaluated against rules (pushed by the verifier) by the evaluation + * engine to allow/block that install. */ public final class RuleEvaluationEngine { private static final String TAG = "RuleEvaluation"; @@ -34,15 +38,6 @@ public final class RuleEvaluationEngine { // installs against rules. private static RuleEvaluationEngine sRuleEvaluationEngine; - // The subset of rules loaded to be used to evaluate an app install request. - // TODO: Load rules relevant to app installs. - private List mRules; - - private RuleEvaluationEngine() { - // Initialize rules with the empty rule set. - mRules = new ArrayList<>(); - } - /** * Provide a singleton instance of the rule evaluation engine. */ @@ -52,4 +47,33 @@ public final class RuleEvaluationEngine { } return sRuleEvaluationEngine; } + + /** + * Load, and match the list of rules against an app install metadata. + * + * @param appInstallMetadata Metadata of the app to be installed, and to evaluate the rules + * against. + * @return A rule matching the metadata. If there are multiple matching rules, returns any. If + * no rules are matching, returns {@link Rule#EMPTY}. + */ + public IntegrityCheckResult evaluate(AppInstallMetadata appInstallMetadata) { + List rules = loadRules(appInstallMetadata); + Rule matchedRule = RuleEvaluator.evaluateRules(rules, appInstallMetadata); + if (matchedRule == Rule.EMPTY) { + return IntegrityCheckResult.allow(); + } else { + switch (matchedRule.getEffect()) { + case DENY: + return IntegrityCheckResult.deny(matchedRule); + default: + Slog.i(TAG, "Matched a non-DENY rule: " + matchedRule); + return IntegrityCheckResult.allow(); + } + } + } + + private List loadRules(AppInstallMetadata appInstallMetadata) { + // TODO: Load rules + return new ArrayList<>(); + } } diff --git a/services/core/java/com/android/server/integrity/engine/RuleEvaluator.java b/services/core/java/com/android/server/integrity/engine/RuleEvaluator.java new file mode 100644 index 0000000000000..bd2c1c65e637b --- /dev/null +++ b/services/core/java/com/android/server/integrity/engine/RuleEvaluator.java @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2019 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.server.integrity.engine; + +import com.android.server.integrity.model.AppInstallMetadata; +import com.android.server.integrity.model.Rule; + +import java.util.List; + +/** + * A helper class for evaluating rules against app install metadata to find if there are matching + * rules. + */ +final class RuleEvaluator { + + /** + * Match the list of rules against an app install metadata. + * + * @param rules The list of rules to evaluate. + * @param appInstallMetadata Metadata of the app to be installed, and to evaluate the rules + * against. + * @return A rule matching the metadata. If there are multiple matching rules, returns any. If + * no rules are matching, returns {@link Rule#EMPTY}. + */ + static Rule evaluateRules(List rules, AppInstallMetadata appInstallMetadata) { + for (Rule rule : rules) { + if (isMatch(rule, appInstallMetadata)) { + return rule; + } + } + return Rule.EMPTY; + } + + private static boolean isMatch(Rule rule, AppInstallMetadata appInstallMetadata) { + // TODO: Add matching logic + return false; + } +} diff --git a/services/core/java/com/android/server/integrity/model/EvaluationOutcome.java b/services/core/java/com/android/server/integrity/model/IntegrityCheckResult.java similarity index 82% rename from services/core/java/com/android/server/integrity/model/EvaluationOutcome.java rename to services/core/java/com/android/server/integrity/model/IntegrityCheckResult.java index dc30dc39f44a1..7aeb0c1b188e7 100644 --- a/services/core/java/com/android/server/integrity/model/EvaluationOutcome.java +++ b/services/core/java/com/android/server/integrity/model/IntegrityCheckResult.java @@ -23,7 +23,7 @@ package com.android.server.integrity.model; *

It contains the outcome effect (whether to allow or block the install), and the rule causing * that effect. */ -public final class EvaluationOutcome { +public final class IntegrityCheckResult { public enum Effect { ALLOW, @@ -33,7 +33,7 @@ public final class EvaluationOutcome { private final Effect mEffect; private final Rule mRule; - private EvaluationOutcome(Effect effect, Rule rule) { + private IntegrityCheckResult(Effect effect, Rule rule) { this.mEffect = effect; this.mRule = rule; } @@ -51,8 +51,8 @@ public final class EvaluationOutcome { * * @return An evaluation outcome with ALLOW effect and empty rule. */ - public static EvaluationOutcome allow() { - return new EvaluationOutcome(Effect.ALLOW, Rule.EMPTY); + public static IntegrityCheckResult allow() { + return new IntegrityCheckResult(Effect.ALLOW, Rule.EMPTY); } /** @@ -61,7 +61,7 @@ public final class EvaluationOutcome { * @param rule Rule causing the DENY effect. * @return An evaluation outcome with DENY effect and rule causing that effect. */ - public static EvaluationOutcome deny(Rule rule) { - return new EvaluationOutcome(Effect.DENY, rule); + public static IntegrityCheckResult deny(Rule rule) { + return new IntegrityCheckResult(Effect.DENY, rule); } }