/*
 * Copyright (C) 2017 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.
 */

#include "config/ConfigManager.h"
#include "storage/StorageManager.h"

#include "stats_util.h"

#include <android-base/file.h>
#include <dirent.h>
#include <stdio.h>
#include <vector>
#include "android-base/stringprintf.h"

namespace android {
namespace os {
namespace statsd {

using std::map;
using std::pair;
using std::set;
using std::string;
using std::vector;

#define STATS_SERVICE_DIR "/data/misc/stats-service"

using android::base::StringPrintf;
using std::unique_ptr;

ConfigManager::ConfigManager() {
}

ConfigManager::~ConfigManager() {
}

void ConfigManager::Startup() {
    map<ConfigKey, StatsdConfig> configsFromDisk;
    StorageManager::readConfigFromDisk(configsFromDisk);
    // TODO(b/70667694): Make the configs from disk be used. And remove the fake config,
    // and tests shouldn't call this Startup(), maybe call StartupForTest() so we don't read
    // configs from disk for tests.
    // for (const auto& pair : configsFromDisk) {
    //    UpdateConfig(pair.first, pair.second);
    //}

    // Uncomment the following line and use the hard coded config for development.
    // UpdateConfig(ConfigKey(1000, "fake"), build_fake_config());
}

void ConfigManager::AddListener(const sp<ConfigListener>& listener) {
    mListeners.push_back(listener);
}

void ConfigManager::UpdateConfig(const ConfigKey& key, const StatsdConfig& config) {
    // Add to set
    mConfigs.insert(key);

    // Save to disk
    update_saved_configs(key, config);

    // Tell everyone
    for (auto& listener : mListeners) {
        listener->OnConfigUpdated(key, config);
    }
}

void ConfigManager::SetConfigReceiver(const ConfigKey& key, const string& pkg, const string& cls) {
    mConfigReceivers[key] = pair<string, string>(pkg, cls);
}

void ConfigManager::RemoveConfigReceiver(const ConfigKey& key) {
    mConfigReceivers.erase(key);
}

void ConfigManager::RemoveConfig(const ConfigKey& key) {
    auto it = mConfigs.find(key);
    if (it != mConfigs.end()) {
        // Remove from map
        mConfigs.erase(it);

        // Tell everyone
        for (auto& listener : mListeners) {
            listener->OnConfigRemoved(key);
        }
    }

    // Remove from disk. There can still be a lingering file on disk so we check
    // whether or not the config was on memory.
    remove_saved_configs(key);
}

void ConfigManager::remove_saved_configs(const ConfigKey& key) {
    string prefix = StringPrintf("%d-%s", key.GetUid(), key.GetName().c_str());
    StorageManager::deletePrefixedFiles(STATS_SERVICE_DIR, prefix.c_str());
}

void ConfigManager::RemoveConfigs(int uid) {
    vector<ConfigKey> removed;

    for (auto it = mConfigs.begin(); it != mConfigs.end();) {
        // Remove from map
        if (it->GetUid() == uid) {
            removed.push_back(*it);
            mConfigReceivers.erase(*it);
            it = mConfigs.erase(it);
        } else {
            it++;
        }
    }

    // Remove separately so if they do anything in the callback they can't mess up our iteration.
    for (auto& key : removed) {
        // Tell everyone
        for (auto& listener : mListeners) {
            listener->OnConfigRemoved(key);
        }
    }
}

void ConfigManager::RemoveAllConfigs() {
    vector<ConfigKey> removed;

    for (auto it = mConfigs.begin(); it != mConfigs.end();) {
        // Remove from map
        removed.push_back(*it);
        auto receiverIt = mConfigReceivers.find(*it);
        if (receiverIt != mConfigReceivers.end()) {
            mConfigReceivers.erase(*it);
        }
        it = mConfigs.erase(it);
    }

    // Remove separately so if they do anything in the callback they can't mess up our iteration.
    for (auto& key : removed) {
        // Tell everyone
        for (auto& listener : mListeners) {
            listener->OnConfigRemoved(key);
        }
    }
}

vector<ConfigKey> ConfigManager::GetAllConfigKeys() const {
    vector<ConfigKey> ret;
    for (auto it = mConfigs.cbegin(); it != mConfigs.cend(); ++it) {
        ret.push_back(*it);
    }
    return ret;
}

const pair<string, string> ConfigManager::GetConfigReceiver(const ConfigKey& key) const {
    auto it = mConfigReceivers.find(key);
    if (it == mConfigReceivers.end()) {
        return pair<string,string>();
    } else {
        return it->second;
    }
}

void ConfigManager::Dump(FILE* out) {
    fprintf(out, "CONFIGURATIONS (%d)\n", (int)mConfigs.size());
    fprintf(out, "     uid name\n");
    for (const auto& key : mConfigs) {
        fprintf(out, "  %6d %s\n", key.GetUid(), key.GetName().c_str());
        auto receiverIt = mConfigReceivers.find(key);
        if (receiverIt != mConfigReceivers.end()) {
            fprintf(out, "    -> received by %s, %s\n", receiverIt->second.first.c_str(),
                    receiverIt->second.second.c_str());
        }
    }
}

void ConfigManager::update_saved_configs(const ConfigKey& key, const StatsdConfig& config) {
    mkdir(STATS_SERVICE_DIR, S_IRWXU);

    // If there is a pre-existing config with same key we should first delete it.
    remove_saved_configs(key);

    // Then we save the latest config.
    string file_name = StringPrintf("%s/%d-%s-%ld", STATS_SERVICE_DIR, key.GetUid(),
                                    key.GetName().c_str(), time(nullptr));
    const int numBytes = config.ByteSize();
    vector<uint8_t> buffer(numBytes);
    config.SerializeToArray(&buffer[0], numBytes);
    StorageManager::writeFile(file_name.c_str(), &buffer[0], numBytes);
}

StatsdConfig build_fake_config() {
    // HACK: Hard code a test metric for counting screen on events...
    StatsdConfig config;
    config.set_name("CONFIG_12345");

    int WAKE_LOCK_TAG_ID = 1111;  // put a fake id here to make testing easier.
    int WAKE_LOCK_UID_KEY_ID = 1;
    int WAKE_LOCK_NAME_KEY = 3;
    int WAKE_LOCK_STATE_KEY = 4;
    int WAKE_LOCK_ACQUIRE_VALUE = 1;
    int WAKE_LOCK_RELEASE_VALUE = 0;

    int APP_USAGE_TAG_ID = 12345;
    int APP_USAGE_UID_KEY_ID = 1;
    int APP_USAGE_STATE_KEY = 2;
    int APP_USAGE_FOREGROUND = 1;
    int APP_USAGE_BACKGROUND = 0;

    int SCREEN_EVENT_TAG_ID = 29;
    int SCREEN_EVENT_STATE_KEY = 1;
    int SCREEN_EVENT_ON_VALUE = 2;
    int SCREEN_EVENT_OFF_VALUE = 1;

    int UID_PROCESS_STATE_TAG_ID = 27;
    int UID_PROCESS_STATE_UID_KEY = 1;

    int KERNEL_WAKELOCK_TAG_ID = 1004;
    int KERNEL_WAKELOCK_COUNT_KEY = 2;
    int KERNEL_WAKELOCK_NAME_KEY = 1;

    int DEVICE_TEMPERATURE_TAG_ID = 33;
    int DEVICE_TEMPERATURE_KEY = 1;

    // Count Screen ON events.
    CountMetric* metric = config.add_count_metric();
    metric->set_name("METRIC_1");
    metric->set_what("SCREEN_TURNED_ON");
    metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);

    // Anomaly threshold for screen-on count.
    // TODO(b/70627390): Uncomment once the bug is fixed.
    /*Alert* alert = config.add_alert();
    alert->set_name("ALERT_1");
    alert->set_metric_name("METRIC_1");
    alert->set_number_of_buckets(6);
    alert->set_trigger_if_sum_gt(10);
    alert->set_refractory_period_secs(30);
    Alert::IncidentdDetails* details = alert->mutable_incidentd_details();
    details->add_section(12);
    details->add_section(13);*/

    AllowedLogSource* logSource = config.mutable_log_source();
    logSource->add_uid(1000);
    logSource->add_uid(0);
    logSource->add_package("com.android.statsd.dogfood");
    logSource->add_package("com.android.bluetooth");

    // Count process state changes, slice by uid.
    metric = config.add_count_metric();
    metric->set_name("METRIC_2");
    metric->set_what("PROCESS_STATE_CHANGE");
    metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
    FieldMatcher* dimensions = metric->mutable_dimensions();
    dimensions->set_field(UID_PROCESS_STATE_TAG_ID);
    dimensions->add_child()->set_field(UID_PROCESS_STATE_UID_KEY);

    // Anomaly threshold for background count.
    // TODO(b/70627390): Uncomment once the bug is fixed.
    /*
    alert = config.add_alert();
    alert->set_name("ALERT_2");
    alert->set_metric_name("METRIC_2");
    alert->set_number_of_buckets(4);
    alert->set_trigger_if_sum_gt(30);
    alert->set_refractory_period_secs(20);
    details = alert->mutable_incidentd_details();
    details->add_section(14);
    details->add_section(15);*/

    // Count process state changes, slice by uid, while SCREEN_IS_OFF
    metric = config.add_count_metric();
    metric->set_name("METRIC_3");
    metric->set_what("PROCESS_STATE_CHANGE");
    metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);

    dimensions = metric->mutable_dimensions();
    dimensions->set_field(UID_PROCESS_STATE_TAG_ID);
    dimensions->add_child()->set_field(UID_PROCESS_STATE_UID_KEY);
    metric->set_condition("SCREEN_IS_OFF");

    // Count wake lock, slice by uid, while SCREEN_IS_ON and app in background
    metric = config.add_count_metric();
    metric->set_name("METRIC_4");
    metric->set_what("APP_GET_WL");
    metric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
    dimensions = metric->mutable_dimensions();
    dimensions->set_field(WAKE_LOCK_TAG_ID);
    dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);


    metric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
    MetricConditionLink* link = metric->add_links();
    link->set_condition("APP_IS_BACKGROUND");
    link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
    link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
    link->mutable_dimensions_in_condition()->add_child()->set_field(APP_USAGE_UID_KEY_ID);

    // Duration of an app holding any wl, while screen on and app in background, slice by uid
    DurationMetric* durationMetric = config.add_duration_metric();
    durationMetric->set_name("METRIC_5");
    durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
    durationMetric->set_aggregation_type(DurationMetric_AggregationType_SUM);
    dimensions = durationMetric->mutable_dimensions();
    dimensions->set_field(WAKE_LOCK_TAG_ID);
    dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
    durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
    link = durationMetric->add_links();
    link->set_condition("APP_IS_BACKGROUND");
    link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
    link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
    link->mutable_dimensions_in_condition()->add_child()->set_field(APP_USAGE_UID_KEY_ID);

    // max Duration of an app holding any wl, while screen on and app in background, slice by uid
    durationMetric = config.add_duration_metric();
    durationMetric->set_name("METRIC_6");
    durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
    durationMetric->set_aggregation_type(DurationMetric_AggregationType_MAX_SPARSE);
    dimensions = durationMetric->mutable_dimensions();
    dimensions->set_field(WAKE_LOCK_TAG_ID);
    dimensions->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
    durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
    link = durationMetric->add_links();
    link->set_condition("APP_IS_BACKGROUND");
    link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
    link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
    link->mutable_dimensions_in_condition()->add_child()->set_field(APP_USAGE_UID_KEY_ID);

    // Duration of an app holding any wl, while screen on and app in background
    durationMetric = config.add_duration_metric();
    durationMetric->set_name("METRIC_7");
    durationMetric->mutable_bucket()->set_bucket_size_millis(30 * 1000L);
    durationMetric->set_aggregation_type(DurationMetric_AggregationType_MAX_SPARSE);
    durationMetric->set_what("WL_HELD_PER_APP_PER_NAME");
    durationMetric->set_condition("APP_IS_BACKGROUND_AND_SCREEN_ON");
    link = durationMetric->add_links();
    link->set_condition("APP_IS_BACKGROUND");
    link->mutable_dimensions_in_what()->set_field(WAKE_LOCK_TAG_ID);
    link->mutable_dimensions_in_what()->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    link->mutable_dimensions_in_condition()->set_field(APP_USAGE_TAG_ID);
    link->mutable_dimensions_in_condition()->add_child()->set_field(APP_USAGE_UID_KEY_ID);


    // Duration of screen on time.
    durationMetric = config.add_duration_metric();
    durationMetric->set_name("METRIC_8");
    durationMetric->mutable_bucket()->set_bucket_size_millis(10 * 1000L);
    durationMetric->set_aggregation_type(DurationMetric_AggregationType_SUM);
    durationMetric->set_what("SCREEN_IS_ON");

    // Anomaly threshold for background count.
    // TODO(b/70627390): Uncomment once the bug is fixed.
    /*
    alert = config.add_alert();
    alert->set_name("ALERT_8");
    alert->set_metric_name("METRIC_8");
    alert->set_number_of_buckets(4);
    alert->set_trigger_if_sum_gt(2000000000); // 2 seconds
    alert->set_refractory_period_secs(120);
    details = alert->mutable_incidentd_details();
    details->add_section(-1);*/

    // Value metric to count KERNEL_WAKELOCK when screen turned on
    ValueMetric* valueMetric = config.add_value_metric();
    valueMetric->set_name("METRIC_6");
    valueMetric->set_what("KERNEL_WAKELOCK");
    valueMetric->set_value_field(KERNEL_WAKELOCK_COUNT_KEY);
    valueMetric->set_condition("SCREEN_IS_ON");
    dimensions = valueMetric->mutable_dimensions();
    dimensions->set_field(KERNEL_WAKELOCK_TAG_ID);
    dimensions->add_child()->set_field(KERNEL_WAKELOCK_NAME_KEY);
    // This is for testing easier. We should never set bucket size this small.
    valueMetric->mutable_bucket()->set_bucket_size_millis(60 * 1000L);

    // Add an EventMetric to log process state change events.
    EventMetric* eventMetric = config.add_event_metric();
    eventMetric->set_name("METRIC_9");
    eventMetric->set_what("SCREEN_TURNED_ON");

    // Add an GaugeMetric.
    GaugeMetric* gaugeMetric = config.add_gauge_metric();
    gaugeMetric->set_name("METRIC_10");
    gaugeMetric->set_what("DEVICE_TEMPERATURE");
    auto gaugeFieldMatcher = gaugeMetric->mutable_gauge_fields_filter()->mutable_fields();
    gaugeFieldMatcher->set_field(DEVICE_TEMPERATURE_TAG_ID);
    gaugeFieldMatcher->add_child()->set_field(DEVICE_TEMPERATURE_KEY);
    gaugeMetric->mutable_bucket()->set_bucket_size_millis(60 * 1000L);

    // Event matchers.
    AtomMatcher* temperatureAtomMatcher = config.add_atom_matcher();
    temperatureAtomMatcher->set_name("DEVICE_TEMPERATURE");
    temperatureAtomMatcher->mutable_simple_atom_matcher()->set_atom_id(
        DEVICE_TEMPERATURE_TAG_ID);

    AtomMatcher* eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("SCREEN_TURNED_ON");
    SimpleAtomMatcher* simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(SCREEN_EVENT_TAG_ID);
    FieldValueMatcher* fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(SCREEN_EVENT_STATE_KEY);
    fieldValueMatcher->set_eq_int(SCREEN_EVENT_ON_VALUE);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("SCREEN_TURNED_OFF");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(SCREEN_EVENT_TAG_ID);
    fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(SCREEN_EVENT_STATE_KEY);
    fieldValueMatcher->set_eq_int(SCREEN_EVENT_OFF_VALUE);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("PROCESS_STATE_CHANGE");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(UID_PROCESS_STATE_TAG_ID);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("APP_GOES_BACKGROUND");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(APP_USAGE_TAG_ID);
    fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(APP_USAGE_STATE_KEY);
    fieldValueMatcher->set_eq_int(APP_USAGE_BACKGROUND);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("APP_GOES_FOREGROUND");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(APP_USAGE_TAG_ID);
    fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(APP_USAGE_STATE_KEY);
    fieldValueMatcher->set_eq_int(APP_USAGE_FOREGROUND);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("APP_GET_WL");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(WAKE_LOCK_TAG_ID);
    fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(WAKE_LOCK_STATE_KEY);
    fieldValueMatcher->set_eq_int(WAKE_LOCK_ACQUIRE_VALUE);

    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("APP_RELEASE_WL");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(WAKE_LOCK_TAG_ID);
    fieldValueMatcher = simpleAtomMatcher->add_field_value_matcher();
    fieldValueMatcher->set_field(WAKE_LOCK_STATE_KEY);
    fieldValueMatcher->set_eq_int(WAKE_LOCK_RELEASE_VALUE);

    // pulled events
    eventMatcher = config.add_atom_matcher();
    eventMatcher->set_name("KERNEL_WAKELOCK");
    simpleAtomMatcher = eventMatcher->mutable_simple_atom_matcher();
    simpleAtomMatcher->set_atom_id(KERNEL_WAKELOCK_TAG_ID);

    // Predicates.............
    Predicate* predicate = config.add_predicate();
    predicate->set_name("SCREEN_IS_ON");
    SimplePredicate* simplePredicate = predicate->mutable_simple_predicate();
    simplePredicate->set_start("SCREEN_TURNED_ON");
    simplePredicate->set_stop("SCREEN_TURNED_OFF");
    simplePredicate->set_count_nesting(false);

    predicate = config.add_predicate();
    predicate->set_name("SCREEN_IS_OFF");
    simplePredicate = predicate->mutable_simple_predicate();
    simplePredicate->set_start("SCREEN_TURNED_OFF");
    simplePredicate->set_stop("SCREEN_TURNED_ON");
    simplePredicate->set_count_nesting(false);

    predicate = config.add_predicate();
    predicate->set_name("APP_IS_BACKGROUND");
    simplePredicate = predicate->mutable_simple_predicate();
    simplePredicate->set_start("APP_GOES_BACKGROUND");
    simplePredicate->set_stop("APP_GOES_FOREGROUND");
    FieldMatcher* predicate_dimension1 = simplePredicate->mutable_dimensions();
    predicate_dimension1->set_field(APP_USAGE_TAG_ID);
    predicate_dimension1->add_child()->set_field(APP_USAGE_UID_KEY_ID);
    simplePredicate->set_count_nesting(false);

    predicate = config.add_predicate();
    predicate->set_name("APP_IS_BACKGROUND_AND_SCREEN_ON");
    Predicate_Combination* combination_predicate = predicate->mutable_combination();
    combination_predicate->set_operation(LogicalOperation::AND);
    combination_predicate->add_predicate("APP_IS_BACKGROUND");
    combination_predicate->add_predicate("SCREEN_IS_ON");

    predicate = config.add_predicate();
    predicate->set_name("WL_HELD_PER_APP_PER_NAME");
    simplePredicate = predicate->mutable_simple_predicate();
    simplePredicate->set_start("APP_GET_WL");
    simplePredicate->set_stop("APP_RELEASE_WL");
    FieldMatcher* predicate_dimension = simplePredicate->mutable_dimensions();
    predicate_dimension1->set_field(WAKE_LOCK_TAG_ID);
    predicate_dimension->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    predicate_dimension->add_child()->set_field(WAKE_LOCK_NAME_KEY);
    simplePredicate->set_count_nesting(true);

    predicate = config.add_predicate();
    predicate->set_name("WL_HELD_PER_APP");
    simplePredicate = predicate->mutable_simple_predicate();
    simplePredicate->set_start("APP_GET_WL");
    simplePredicate->set_stop("APP_RELEASE_WL");
    simplePredicate->set_initial_value(SimplePredicate_InitialValue_FALSE);
    predicate_dimension = simplePredicate->mutable_dimensions();
    predicate_dimension->set_field(WAKE_LOCK_TAG_ID);
    predicate_dimension->add_child()->set_field(WAKE_LOCK_UID_KEY_ID);
    simplePredicate->set_count_nesting(true);

    return config;
}

}  // namespace statsd
}  // namespace os
}  // namespace android
