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

Commit a21e2f1a authored by Michael Butler's avatar Michael Butler Committed by Android (Google) Code Review
Browse files

Merge "Add missing validation for NN canonical types"

parents cf4ed06c 08ee3f92
Loading
Loading
Loading
Loading
+14 −0
Original line number Diff line number Diff line
@@ -22,10 +22,15 @@
#include <android-base/logging.h>
#include <android/hardware/neuralnetworks/1.0/types.h>
#include <nnapi/Result.h>
#include <nnapi/TypeUtils.h>
#include <nnapi/Types.h>
#include <nnapi/Validation.h>
#include <nnapi/hal/HandleError.h>

namespace android::hardware::neuralnetworks::V1_0::utils {

constexpr auto kVersion = nn::Version::ANDROID_OC_MR1;

template <typename Type>
nn::Result<void> validate(const Type& halObject) {
    const auto maybeCanonical = nn::convert(halObject);
@@ -44,6 +49,15 @@ bool valid(const Type& halObject) {
    return result.has_value();
}

template <typename Type>
nn::GeneralResult<void> compliantVersion(const Type& canonical) {
    const auto version = NN_TRY(hal::utils::makeGeneralFailure(nn::validate(canonical)));
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    return {};
}

template <typename Type>
auto convertFromNonCanonical(const Type& nonCanonicalObject)
        -> decltype(convert(nn::convert(nonCanonicalObject).value())) {
+12 −26
Original line number Diff line number Diff line
@@ -35,6 +35,8 @@
#include <utility>
#include <variant>

#include "Utils.h"

namespace {

template <typename Type>
@@ -42,8 +44,6 @@ constexpr std::underlying_type_t<Type> underlyingType(Type value) {
    return static_cast<std::underlying_type_t<Type>>(value);
}

constexpr auto kVersion = android::nn::Version::ANDROID_OC_MR1;

}  // namespace

namespace android::nn {
@@ -53,13 +53,13 @@ using hardware::hidl_memory;
using hardware::hidl_vec;

template <typename Input>
using unvalidatedConvertOutput =
using UnvalidatedConvertOutput =
        std::decay_t<decltype(unvalidatedConvert(std::declval<Input>()).value())>;

template <typename Type>
GeneralResult<std::vector<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
GeneralResult<std::vector<UnvalidatedConvertOutput<Type>>> unvalidatedConvert(
        const hidl_vec<Type>& arguments) {
    std::vector<unvalidatedConvertOutput<Type>> canonical;
    std::vector<UnvalidatedConvertOutput<Type>> canonical;
    canonical.reserve(arguments.size());
    for (const auto& argument : arguments) {
        canonical.push_back(NN_TRY(nn::unvalidatedConvert(argument)));
@@ -68,16 +68,9 @@ GeneralResult<std::vector<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
}

template <typename Type>
decltype(nn::unvalidatedConvert(std::declval<Type>())) validatedConvert(const Type& halObject) {
GeneralResult<UnvalidatedConvertOutput<Type>> validatedConvert(const Type& halObject) {
    auto canonical = NN_TRY(nn::unvalidatedConvert(halObject));
    const auto maybeVersion = validate(canonical);
    if (!maybeVersion.has_value()) {
        return error() << maybeVersion.error();
    }
    const auto version = maybeVersion.value();
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    NN_TRY(hal::V1_0::utils::compliantVersion(canonical));
    return canonical;
}

@@ -248,13 +241,13 @@ namespace android::hardware::neuralnetworks::V1_0::utils {
namespace {

template <typename Input>
using unvalidatedConvertOutput =
using UnvalidatedConvertOutput =
        std::decay_t<decltype(unvalidatedConvert(std::declval<Input>()).value())>;

template <typename Type>
nn::GeneralResult<hidl_vec<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
nn::GeneralResult<hidl_vec<UnvalidatedConvertOutput<Type>>> unvalidatedConvert(
        const std::vector<Type>& arguments) {
    hidl_vec<unvalidatedConvertOutput<Type>> halObject(arguments.size());
    hidl_vec<UnvalidatedConvertOutput<Type>> halObject(arguments.size());
    for (size_t i = 0; i < arguments.size(); ++i) {
        halObject[i] = NN_TRY(utils::unvalidatedConvert(arguments[i]));
    }
@@ -262,15 +255,8 @@ nn::GeneralResult<hidl_vec<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
}

template <typename Type>
decltype(utils::unvalidatedConvert(std::declval<Type>())) validatedConvert(const Type& canonical) {
    const auto maybeVersion = nn::validate(canonical);
    if (!maybeVersion.has_value()) {
        return nn::error() << maybeVersion.error();
    }
    const auto version = maybeVersion.value();
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
nn::GeneralResult<UnvalidatedConvertOutput<Type>> validatedConvert(const Type& canonical) {
    NN_TRY(compliantVersion(canonical));
    return utils::unvalidatedConvert(canonical);
}

+13 −0
Original line number Diff line number Diff line
@@ -22,12 +22,16 @@
#include <android-base/logging.h>
#include <android/hardware/neuralnetworks/1.1/types.h>
#include <nnapi/Result.h>
#include <nnapi/TypeUtils.h>
#include <nnapi/Types.h>
#include <nnapi/Validation.h>
#include <nnapi/hal/1.0/Conversions.h>
#include <nnapi/hal/HandleError.h>

namespace android::hardware::neuralnetworks::V1_1::utils {

constexpr auto kDefaultExecutionPreference = ExecutionPreference::FAST_SINGLE_ANSWER;
constexpr auto kVersion = nn::Version::ANDROID_P;

template <typename Type>
nn::Result<void> validate(const Type& halObject) {
@@ -47,6 +51,15 @@ bool valid(const Type& halObject) {
    return result.has_value();
}

template <typename Type>
nn::GeneralResult<void> compliantVersion(const Type& canonical) {
    const auto version = NN_TRY(hal::utils::makeGeneralFailure(nn::validate(canonical)));
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    return {};
}

template <typename Type>
auto convertFromNonCanonical(const Type& nonCanonicalObject)
        -> decltype(convert(nn::convert(nonCanonicalObject).value())) {
+12 −30
Original line number Diff line number Diff line
@@ -35,11 +35,7 @@
#include <type_traits>
#include <utility>

namespace {

constexpr auto kVersion = android::nn::Version::ANDROID_P;

}  // namespace
#include "Utils.h"

namespace android::nn {
namespace {
@@ -47,13 +43,13 @@ namespace {
using hardware::hidl_vec;

template <typename Input>
using unvalidatedConvertOutput =
using UnvalidatedConvertOutput =
        std::decay_t<decltype(unvalidatedConvert(std::declval<Input>()).value())>;

template <typename Type>
GeneralResult<std::vector<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
GeneralResult<std::vector<UnvalidatedConvertOutput<Type>>> unvalidatedConvert(
        const hidl_vec<Type>& arguments) {
    std::vector<unvalidatedConvertOutput<Type>> canonical;
    std::vector<UnvalidatedConvertOutput<Type>> canonical;
    canonical.reserve(arguments.size());
    for (const auto& argument : arguments) {
        canonical.push_back(NN_TRY(nn::unvalidatedConvert(argument)));
@@ -62,16 +58,9 @@ GeneralResult<std::vector<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
}

template <typename Type>
decltype(nn::unvalidatedConvert(std::declval<Type>())) validatedConvert(const Type& halObject) {
GeneralResult<UnvalidatedConvertOutput<Type>> validatedConvert(const Type& halObject) {
    auto canonical = NN_TRY(nn::unvalidatedConvert(halObject));
    const auto maybeVersion = validate(canonical);
    if (!maybeVersion.has_value()) {
        return error() << maybeVersion.error();
    }
    const auto version = maybeVersion.value();
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    NN_TRY(hal::V1_1::utils::compliantVersion(canonical));
    return canonical;
}

@@ -180,13 +169,13 @@ nn::GeneralResult<hidl_memory> unvalidatedConvert(const nn::SharedMemory& memory
}

template <typename Input>
using unvalidatedConvertOutput =
using UnvalidatedConvertOutput =
        std::decay_t<decltype(unvalidatedConvert(std::declval<Input>()).value())>;

template <typename Type>
nn::GeneralResult<hidl_vec<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
nn::GeneralResult<hidl_vec<UnvalidatedConvertOutput<Type>>> unvalidatedConvert(
        const std::vector<Type>& arguments) {
    hidl_vec<unvalidatedConvertOutput<Type>> halObject(arguments.size());
    hidl_vec<UnvalidatedConvertOutput<Type>> halObject(arguments.size());
    for (size_t i = 0; i < arguments.size(); ++i) {
        halObject[i] = NN_TRY(unvalidatedConvert(arguments[i]));
    }
@@ -194,16 +183,9 @@ nn::GeneralResult<hidl_vec<unvalidatedConvertOutput<Type>>> unvalidatedConvert(
}

template <typename Type>
decltype(utils::unvalidatedConvert(std::declval<Type>())) validatedConvert(const Type& canonical) {
    const auto maybeVersion = nn::validate(canonical);
    if (!maybeVersion.has_value()) {
        return nn::error() << maybeVersion.error();
    }
    const auto version = maybeVersion.value();
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    return utils::unvalidatedConvert(canonical);
nn::GeneralResult<UnvalidatedConvertOutput<Type>> validatedConvert(const Type& canonical) {
    NN_TRY(compliantVersion(canonical));
    return unvalidatedConvert(canonical);
}

}  // anonymous namespace
+15 −0
Original line number Diff line number Diff line
@@ -22,19 +22,25 @@
#include <android-base/logging.h>
#include <android/hardware/neuralnetworks/1.2/types.h>
#include <nnapi/Result.h>
#include <nnapi/TypeUtils.h>
#include <nnapi/Types.h>
#include <nnapi/Validation.h>
#include <nnapi/hal/1.0/Conversions.h>
#include <nnapi/hal/1.1/Conversions.h>
#include <nnapi/hal/1.1/Utils.h>
#include <nnapi/hal/HandleError.h>

#include <limits>

namespace android::hardware::neuralnetworks::V1_2::utils {

using CacheToken = hidl_array<uint8_t, static_cast<size_t>(Constant::BYTE_SIZE_OF_CACHE_TOKEN)>;
using V1_1::utils::kDefaultExecutionPreference;

constexpr auto kDefaultMesaureTiming = MeasureTiming::NO;
constexpr auto kNoTiming = Timing{.timeOnDevice = std::numeric_limits<uint64_t>::max(),
                                  .timeInDriver = std::numeric_limits<uint64_t>::max()};
constexpr auto kVersion = nn::Version::ANDROID_Q;

template <typename Type>
nn::Result<void> validate(const Type& halObject) {
@@ -54,6 +60,15 @@ bool valid(const Type& halObject) {
    return result.has_value();
}

template <typename Type>
nn::GeneralResult<void> compliantVersion(const Type& canonical) {
    const auto version = NN_TRY(hal::utils::makeGeneralFailure(nn::validate(canonical)));
    if (version > kVersion) {
        return NN_ERROR() << "Insufficient version: " << version << " vs required " << kVersion;
    }
    return {};
}

template <typename Type>
auto convertFromNonCanonical(const Type& nonCanonicalObject)
        -> decltype(convert(nn::convert(nonCanonicalObject).value())) {
Loading