Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d02ef554 authored by Chris Manton's avatar Chris Manton
Browse files

dumpsys: Remove user filtering capabilities

We only use the developer capabilities

Bug: 335736809
Test: m .
Flag: EXEMPT, Code Removal
Change-Id: Iabb6308b1932e6535f40673466712a599231adff
parent 2809a5c9
Loading
Loading
Loading
Loading
+6 −123
Original line number Diff line number Diff line
@@ -20,10 +20,6 @@

#include <memory>

#include "common/init_flags.h"
#include "dumpsys/internal/filter_internal.h"
#include "os/log.h"

using namespace bluetooth;
using namespace dumpsys;

@@ -35,8 +31,7 @@ class Filter {

  virtual void FilterInPlace(char* dumpsys_data) = 0;

  static std::unique_ptr<Filter> Factory(
      dumpsys::FilterType filter_type, const dumpsys::ReflectionSchema& reflection_schema);
  static std::unique_ptr<Filter> Factory(const dumpsys::ReflectionSchema& reflection_schema);

 protected:
  /**
@@ -88,124 +83,12 @@ class DeveloperPrivacyFilter : public Filter {
  }
};

class UserPrivacyFilter : public Filter {
 public:
  UserPrivacyFilter(const dumpsys::ReflectionSchema& reflection_schema) : Filter(reflection_schema) {}
  void FilterInPlace(char* dumpsys_data) override;

 protected:
  bool FilterField(const reflection::Field* field, flatbuffers::Table* table) override;
  void FilterObject(const reflection::Object* object, flatbuffers::Table* table) override;
  void FilterTable(const reflection::Schema* schema, flatbuffers::Table* table) override;
};

bool UserPrivacyFilter::FilterField(const reflection::Field* field, flatbuffers::Table* table) {
  log::assert_that(field != nullptr, "assert failed: field != nullptr");
  log::assert_that(table != nullptr, "assert failed: table != nullptr");
  internal::PrivacyLevel privacy_level = internal::FindFieldPrivacyLevel(*field);

  const auto type = static_cast<flatbuffers::BaseType>(field->type()->base_type());
  switch (type) {
    case flatbuffers::BASE_TYPE_INT:
      return internal::FilterTypeInteger(*field, table, privacy_level);
      break;
    case flatbuffers::BASE_TYPE_FLOAT:
      return internal::FilterTypeFloat(*field, table, privacy_level);
      break;
    case flatbuffers::BASE_TYPE_STRING:
      return internal::FilterTypeString(*field, table, privacy_level);
      break;
    case flatbuffers::BASE_TYPE_STRUCT:
      return internal::FilterTypeStruct(*field, table, privacy_level);
      break;
    case flatbuffers::BASE_TYPE_BOOL:
      return internal::FilterTypeBool(*field, table, privacy_level);
      break;
    case flatbuffers::BASE_TYPE_LONG:
      return internal::FilterTypeLong(*field, table, privacy_level);
      break;
    default:
      log::warn("Unsupported base type:{}", internal::FlatbufferTypeText(type));
      break;
  }
  return false;
}

void UserPrivacyFilter::FilterObject(const reflection::Object* object, flatbuffers::Table* table) {
  log::assert_that(object != nullptr, "assert failed: object != nullptr");
  if (table == nullptr) {
    return;  // table data is not populated
  }
  for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
    if (!FilterField(*it, table)) {
      log::error("Unable to filter field from an object when it's expected it will work");
    };
  }
}

void UserPrivacyFilter::FilterTable(const reflection::Schema* schema, flatbuffers::Table* table) {
  if (schema == nullptr) {
    log::warn("schema is nullptr...probably ok");
    return;
  }

  const reflection::Object* object = schema->root_table();
  if (object == nullptr) {
    log::warn("reflection object is nullptr...is ok ?");
    return;
  }

  if (table == nullptr) {
    return;  // table not populated
  }

  for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
    if (FilterField(*it, table)) {
      continue;  // Field successfully filtered
    }
    // Get the index of this complex non-string object from the schema which is
    // also the same index into the data table.
    int32_t index = it->type()->index();
    log::assert_that(index != -1, "assert failed: index != -1");

    flatbuffers::Table* sub_table = table->GetPointer<flatbuffers::Table*>(it->offset());
    const reflection::Schema* sub_schema =
        reflection_schema_.FindInReflectionSchema(schema->objects()->Get(index)->name()->str());

    if (sub_schema != nullptr) {
      FilterTable(sub_schema, sub_table);  // Top level schema
    } else {
      // Leaf node schema
      const flatbuffers::String* name = schema->objects()->Get(index)->name();
      const reflection::Object* sub_object = internal::FindReflectionObject(schema->objects(), name);
      if (sub_object != nullptr) {
        FilterObject(sub_object, sub_table);
      } else {
        log::error("Unable to find reflection sub object:{}", name->c_str());
      }
    }
  }
}

void UserPrivacyFilter::FilterInPlace(char* dumpsys_data) {
  log::assert_that(dumpsys_data != nullptr, "assert failed: dumpsys_data != nullptr");
  const reflection::Schema* root_schema = reflection_schema_.FindInReflectionSchema(reflection_schema_.GetRootName());
  flatbuffers::Table* table = const_cast<flatbuffers::Table*>(flatbuffers::GetRoot<flatbuffers::Table>(dumpsys_data));
  FilterTable(root_schema, table);
}

std::unique_ptr<Filter> Filter::Factory(
    dumpsys::FilterType filter_type, const dumpsys::ReflectionSchema& reflection_schema) {
  switch (filter_type) {
    case dumpsys::FilterType::AS_DEVELOPER:
std::unique_ptr<Filter> Filter::Factory(const dumpsys::ReflectionSchema& reflection_schema) {
  return std::make_unique<DeveloperPrivacyFilter>(reflection_schema);
    default:
      return std::make_unique<UserPrivacyFilter>(reflection_schema);
  }
}

void bluetooth::dumpsys::FilterInPlace(
    FilterType filter_type, const ReflectionSchema& reflection_schema, std::string* dumpsys_data) {
  auto filter = Filter::Factory(filter_type, reflection_schema);
void bluetooth::dumpsys::FilterSchema(
    const ReflectionSchema& reflection_schema, std::string* dumpsys_data) {
  auto filter = Filter::Factory(reflection_schema);
  filter->FilterInPlace(dumpsys_data->data());
}
+1 −3
Original line number Diff line number Diff line
@@ -20,9 +20,7 @@
namespace bluetooth {
namespace dumpsys {

enum FilterType { AS_USER = 0, AS_DEVELOPER };

void FilterInPlace(FilterType filter_type, const ReflectionSchema& reflection_schema, std::string* dumpsys_data);
void FilterSchema(const ReflectionSchema& reflection_schema, std::string* dumpsys_data);

}  // namespace dumpsys
}  // namespace bluetooth
+3 −62
Original line number Diff line number Diff line
@@ -29,10 +29,10 @@
#include "test_data/qux.h"
#include "test_data/root.h"

namespace testing {

using namespace bluetooth;

namespace testing {

class DumpsysFilterTest : public Test {
 protected:
  void SetUp() override {
@@ -87,7 +87,7 @@ TEST_F(DumpsysFilterTest, filter_as_developer) {
  std::string dumpsys_data = PopulateTestSchema();
  dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());

  dumpsys::FilterInPlace(dumpsys::FilterType::AS_DEVELOPER, reflection_schema, &dumpsys_data);
  dumpsys::FilterSchema(reflection_schema, &dumpsys_data);

  const testing::DumpsysTestDataRoot* data_root = GetDumpsysTestDataRoot(dumpsys_data.data());

@@ -118,63 +118,4 @@ TEST_F(DumpsysFilterTest, filter_as_developer) {
  ASSERT_STREQ("123.456", foo->foo_float_string()->c_str());
}

TEST_F(DumpsysFilterTest, filter_as_user) {
  std::string dumpsys_data = PopulateTestSchema();
  dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());

  dumpsys::FilterInPlace(dumpsys::FilterType::AS_USER, reflection_schema, &dumpsys_data);

  [[maybe_unused]] const testing::DumpsysTestDataRoot* data_root = GetDumpsysTestDataRoot(dumpsys_data.data());

  ASSERT_TRUE(data_root->string_private() == nullptr);
  ASSERT_TRUE(data_root->string_opaque()->str() == "*************");
  ASSERT_TRUE(data_root->string_anonymized()->str() != "String anonymized");
  ASSERT_TRUE(data_root->string_any()->str() == "String any");

  ASSERT_TRUE(data_root->int_private() == 0);
  ASSERT_TRUE(data_root->int_opaque() == 0);
  ASSERT_TRUE(data_root->int_anonymized() != 789);
  ASSERT_TRUE(data_root->int_any() == 0xabc);

  // bar
  ASSERT_EQ(nullptr, data_root->bar_module_data());

  // baz
  const testing::BazTestSchema* baz = data_root->baz_module_data();
  ASSERT_NE(nullptr, baz);

  const testing::BazSubTableAny* baz_any = baz->sub_table_any();
  ASSERT_NE(nullptr, baz_any);
  ASSERT_EQ(nullptr, baz->sub_table_anonymized());
  ASSERT_EQ(nullptr, baz->sub_table_opaque());
  ASSERT_EQ(nullptr, baz->sub_table_private());

  ASSERT_EQ(0, baz_any->subtable_int_private());     // 1
  ASSERT_EQ(0, baz_any->subtable_int_opaque());      // 2
  ASSERT_NE(3, baz_any->subtable_int_anonymized());  // 3
  ASSERT_EQ(4, baz_any->subtable_int_any());         // 4
  ASSERT_STREQ("Baz Subtable Any", baz_any->subtable_string_any()->c_str());

  // foo
  const testing::FooTestSchema* foo = data_root->foo_module_data();
  ASSERT_EQ(0, foo->foo_int_private());
  ASSERT_EQ(0, foo->foo_int_opaque());
  ASSERT_NE(123, foo->foo_int_anonymized());
  ASSERT_EQ(123, foo->foo_int_any());
  ASSERT_STREQ("123", foo->foo_int_string()->c_str());
  ASSERT_FLOAT_EQ(0.0, foo->foo_float_private());
  ASSERT_FLOAT_EQ(0.0, foo->foo_float_opaque());
  ASSERT_THAT(foo->foo_float_anonymized(), Not(FloatEq(123.456)));
  ASSERT_FLOAT_EQ(123.456, foo->foo_float_any());
  ASSERT_STREQ("123.456", foo->foo_float_string()->c_str());

  // qux
  const testing::QuxTestSchema* qux = data_root->qux_module_data();
  ASSERT_EQ(0, qux->qux_int_private());
  ASSERT_EQ(0, qux->qux_int_opaque());
  ASSERT_NE(789, qux->qux_int_anonymized());
  ASSERT_EQ(0xabc, qux->qux_int_any());
  ASSERT_STREQ("Qux Module String", qux->qux_string_name()->c_str());
}

}  // namespace testing
+4 −10
Original line number Diff line number Diff line
@@ -54,8 +54,7 @@ struct Dumpsys::impl {
  ~impl() = default;

 protected:
  void FilterAsUser(std::string* dumpsys_data) const;
  void FilterAsDeveloper(std::string* dumpsys_data) const;
  void FilterSchema(std::string* dumpsys_data) const;
  std::string PrintAsJson(std::string* dumpsys_data) const;

  bool IsDebuggable() const;
@@ -81,14 +80,9 @@ bool Dumpsys::impl::IsDebuggable() const {
  return (os::GetSystemProperty(kReadOnlyDebuggableProperty) == "1");
}

void Dumpsys::impl::FilterAsDeveloper(std::string* dumpsys_data) const {
void Dumpsys::impl::FilterSchema(std::string* dumpsys_data) const {
  log::assert_that(dumpsys_data != nullptr, "assert failed: dumpsys_data != nullptr");
  dumpsys::FilterInPlace(dumpsys::FilterType::AS_DEVELOPER, reflection_schema_, dumpsys_data);
}

void Dumpsys::impl::FilterAsUser(std::string* dumpsys_data) const {
  log::assert_that(dumpsys_data != nullptr, "assert failed: dumpsys_data != nullptr");
  dumpsys::FilterInPlace(dumpsys::FilterType::AS_USER, reflection_schema_, dumpsys_data);
  dumpsys::FilterSchema(reflection_schema_, dumpsys_data);
}

std::string Dumpsys::impl::PrintAsJson(std::string* dumpsys_data) const {
@@ -151,7 +145,7 @@ void Dumpsys::impl::DumpWithArgsAsync(int fd, const char** args) const {
  dumper.DumpState(&dumpsys_data, oss);

  dprintf(fd, " ----- Filtering as Developer -----\n");
  FilterAsDeveloper(&dumpsys_data);
  FilterSchema(&dumpsys_data);

  dprintf(fd, "%s", PrintAsJson(&dumpsys_data).c_str());
}