blob: 8160e9663a2d04350f54321eb159f977be410d65 [file] [log] [blame] [edit]
// Copyright 2023 The ChromiumOS Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "permission_broker/rule_utils.h"
#include <optional>
#include <string>
#include <type_traits>
#include <vector>
#include "base/logging.h"
#include "base/strings/string_number_conversions.h"
#include "chromeos-config/libcros_config/cros_config.h"
#include "permission_broker/allow_lists.h"
namespace {
std::string LoadFormFactor() {
brillo::CrosConfig cros_config;
std::string form_factor;
if (!cros_config.GetString("/hardware-properties", "form-factor",
&form_factor)) {
LOG(ERROR) << "Unable to ascertain form-factor from CrosConfig, this may "
"affect rule processing.";
}
return form_factor;
}
permission_broker::FormFactor StringToFormFactor(std::string form_factor) {
if (form_factor.empty()) {
return permission_broker::FormFactor::kUnknown;
} else if (form_factor == "CHROMEBOX") {
return permission_broker::FormFactor::kChromebox;
}
return permission_broker::FormFactor::kOther;
}
} // namespace
namespace permission_broker {
const FormFactor& GetFormFactor() {
static_assert(std::is_trivially_destructible<FormFactor>::value);
static const FormFactor s = StringToFormFactor(LoadFormFactor());
return s;
}
std::optional<CrosUsbLocationProperty> GetCrosUsbLocationProperty(
udev_device* device) {
const char* prop = udev_device_get_property_value(device, kCrosUsbLocation);
if (!prop) {
return std::nullopt;
}
std::string tag(prop);
if (tag == "external") {
return CrosUsbLocationProperty::kExternal;
} else if (tag == "internal") {
return CrosUsbLocationProperty::kInternal;
} else {
if (tag != "unknown") {
VLOG(1) << "Unexpected value for CROS_USB_LOCATION property: '" << tag
<< "'";
}
return CrosUsbLocationProperty::kUnknown;
}
}
bool GetUIntSysattr(udev_device* device, const char* key, uint32_t* val) {
CHECK(val);
const char* str_val = udev_device_get_sysattr_value(device, key);
return str_val && base::HexStringToUInt(str_val, val);
}
template <typename Iterator>
bool UsbDeviceListContainsId(Iterator first,
Iterator last,
uint16_t vendor_id,
uint16_t product_id) {
while (first != last) {
if (first->vendor_id == vendor_id &&
(!first->product_id || first->product_id == product_id))
return true;
++first;
}
return false;
}
bool IsDeviceAllowedWebHID(udev_device* device) {
uint32_t vendor_id, product_id;
if (!GetUIntSysattr(device, "idVendor", &vendor_id) ||
!GetUIntSysattr(device, "idProduct", &product_id)) {
return false;
}
return UsbDeviceListContainsId(std::begin(kWebHIDAllowedIds),
std::end(kWebHIDAllowedIds), vendor_id,
product_id);
}
template bool UsbDeviceListContainsId<const policy::DevicePolicy::UsbDeviceId*>(
const policy::DevicePolicy::UsbDeviceId* first,
const policy::DevicePolicy::UsbDeviceId* last,
uint16_t vendor_id,
uint16_t product_id);
template bool UsbDeviceListContainsId<
std::vector<policy::DevicePolicy::UsbDeviceId>::iterator>(
std::vector<policy::DevicePolicy::UsbDeviceId>::iterator first,
std::vector<policy::DevicePolicy::UsbDeviceId>::iterator last,
uint16_t vendor_id,
uint16_t product_id);
} // namespace permission_broker