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

Commit 39eda3e3 authored by android-build-team Robot's avatar android-build-team Robot
Browse files

Snap for 6035658 from 73b065fe to rvc-release

Change-Id: If2621c78b0552fd0f31968c6c4270fe8339377db
parents 71567037 73b065fe
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -15,7 +15,7 @@
apex {
    name: "test_com.android.media",
    manifest: "test_manifest.json",
    file_contexts: "com.android.media",
    file_contexts: ":com.android.media-file_contexts",
    defaults: ["com.android.media-defaults"],
    installable: false,
}
@@ -23,7 +23,7 @@ apex {
apex {
    name: "test_com.android.media.swcodec",
    manifest: "test_manifest_codec.json",
    file_contexts: "com.android.media.swcodec",
    file_contexts: ":com.android.media.swcodec-file_contexts",
    defaults: ["com.android.media.swcodec-defaults"],
    installable: false,
}
+59 −16
Original line number Diff line number Diff line
@@ -23,7 +23,9 @@
#include <hidl/HidlTransportSupport.h>
#include <minijail.h>

#include <util/C2InterfaceHelper.h>
#include <C2Component.h>
#include <C2Config.h>

// This is the absolute on-device path of the prebuild_etc module
// "android.hardware.media.c2@1.1-default-seccomp_policy" in Android.bp.
@@ -37,11 +39,14 @@ static constexpr char kExtSeccompPolicyPath[] =
        "/vendor/etc/seccomp_policy/"
        "android.hardware.media.c2@1.1-extended-seccomp-policy";

class DummyC2Store : public C2ComponentStore {
class StoreImpl : public C2ComponentStore {
public:
    DummyC2Store() = default;
    StoreImpl()
        : mReflectorHelper(std::make_shared<C2ReflectorHelper>()),
          mInterface(mReflectorHelper) {
    }

    virtual ~DummyC2Store() override = default;
    virtual ~StoreImpl() override = default;

    virtual C2String getName() const override {
        return "default";
@@ -71,31 +76,69 @@ public:
    }

    virtual c2_status_t query_sm(
        const std::vector<C2Param*>& /* stackParams */,
        const std::vector<C2Param::Index>& /* heapParamIndices */,
        std::vector<std::unique_ptr<C2Param>>* const /* heapParams */) const override {
        return C2_OMITTED;
        const std::vector<C2Param*>& stackParams,
        const std::vector<C2Param::Index>& heapParamIndices,
        std::vector<std::unique_ptr<C2Param>>* const heapParams) const override {
        return mInterface.query(stackParams, heapParamIndices, C2_MAY_BLOCK, heapParams);
    }

    virtual c2_status_t config_sm(
            const std::vector<C2Param*>& /* params */,
            std::vector<std::unique_ptr<C2SettingResult>>* const /* failures */) override {
        return C2_OMITTED;
            const std::vector<C2Param*>& params,
            std::vector<std::unique_ptr<C2SettingResult>>* const failures) override {
        return mInterface.config(params, C2_MAY_BLOCK, failures);
    }

    virtual std::shared_ptr<C2ParamReflector> getParamReflector() const override {
        return nullptr;
        return mReflectorHelper;
    }

    virtual c2_status_t querySupportedParams_nb(
            std::vector<std::shared_ptr<C2ParamDescriptor>>* const /* params */) const override {
        return C2_OMITTED;
            std::vector<std::shared_ptr<C2ParamDescriptor>>* const params) const override {
        return mInterface.querySupportedParams(params);
    }

    virtual c2_status_t querySupportedValues_sm(
            std::vector<C2FieldSupportedValuesQuery>& /* fields */) const override {
        return C2_OMITTED;
            std::vector<C2FieldSupportedValuesQuery>& fields) const override {
        return mInterface.querySupportedValues(fields, C2_MAY_BLOCK);
    }

private:
    class Interface : public C2InterfaceHelper {
    public:
        Interface(const std::shared_ptr<C2ReflectorHelper> &helper)
            : C2InterfaceHelper(helper) {
            setDerivedInstance(this);

            addParameter(
                DefineParam(mIonUsageInfo, "ion-usage")
                .withDefault(new C2StoreIonUsageInfo())
                .withFields({
                    C2F(mIonUsageInfo, usage).flags(
                            {C2MemoryUsage::CPU_READ | C2MemoryUsage::CPU_WRITE}),
                    C2F(mIonUsageInfo, capacity).inRange(0, UINT32_MAX, 1024),
                    C2F(mIonUsageInfo, heapMask).any(),
                    C2F(mIonUsageInfo, allocFlags).flags({}),
                    C2F(mIonUsageInfo, minAlignment).equalTo(0)
                })
                .withSetter(SetIonUsage)
                .build());
        }

        virtual ~Interface() = default;

    private:
        static C2R SetIonUsage(bool /* mayBlock */, C2P<C2StoreIonUsageInfo> &me) {
            // Vendor's TODO: put appropriate mapping logic
            me.set().heapMask = ~0;
            me.set().allocFlags = 0;
            me.set().minAlignment = 0;
            return C2R::Ok();
        }

        std::shared_ptr<C2StoreIonUsageInfo> mIonUsageInfo;
    };
    std::shared_ptr<C2ReflectorHelper> mReflectorHelper;
    Interface mInterface;
};

int main(int /* argc */, char** /* argv */) {
@@ -124,7 +167,7 @@ int main(int /* argc */, char** /* argv */) {
        //         /* implementation of C2ComponentStore */);
        LOG(DEBUG) << "Instantiating Codec2's IComponentStore service...";
        store = new utils::ComponentStore(
                std::make_shared<DummyC2Store>());
                std::make_shared<StoreImpl>());

        if (store == nullptr) {
            LOG(ERROR) << "Cannot create Codec2's IComponentStore service.";
+1 −0
Original line number Diff line number Diff line
@@ -16,6 +16,7 @@ cc_library_shared {
    vendor_available: true,

    srcs: [
        "C2AllocatorBlob.cpp",
        "C2AllocatorIon.cpp",
        "C2AllocatorGralloc.cpp",
        "C2Buffer.cpp",
+186 −0
Original line number Diff line number Diff line
/*
 * 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.
 */

// #define LOG_NDEBUG 0
#define LOG_TAG "C2AllocatorBlob"

#include <C2AllocatorBlob.h>
#include <C2PlatformSupport.h>

#include <android/hardware/graphics/common/1.2/types.h>
#include <utils/Log.h>

namespace android {

using ::android::hardware::graphics::common::V1_2::PixelFormat;

constexpr uint32_t kLinearBufferHeight = 1u;
constexpr uint32_t kLinearBufferFormat = static_cast<uint32_t>(PixelFormat::BLOB);

namespace {

c2_status_t GetCapacityFromHandle(const C2Handle* const grallocHandle, size_t* capacity) {
    uint32_t width, height, format, stride, generation, igbp_slot;
    uint64_t usage, igbp_id;
    _UnwrapNativeCodec2GrallocMetadata(grallocHandle, &width, &height, &format, &usage, &stride,
                                       &generation, &igbp_id, &igbp_slot);

    if (height != kLinearBufferHeight || format != kLinearBufferFormat) {
        return C2_BAD_VALUE;
    }
    *capacity = width;
    return C2_OK;
}

}  // namespace

// C2AllocationBlob is a wrapper for C2AllocationGralloc allocated by C2AllocatorGralloc.
// C2AllocationBlob::handle() delegates to the backed C2AllocationGralloc::handle().
class C2AllocationBlob : public C2LinearAllocation {
public:
    C2AllocationBlob(std::shared_ptr<C2GraphicAllocation> graphicAllocation, size_t capacity,
                     C2Allocator::id_t allocatorId);
    ~C2AllocationBlob() override;
    c2_status_t map(size_t offset, size_t size, C2MemoryUsage usage, C2Fence* fence,
                    void** addr /* nonnull */) override;
    c2_status_t unmap(void* addr, size_t size, C2Fence* fenceFd) override;

    id_t getAllocatorId() const override { return mAllocatorId; }
    const C2Handle* handle() const override { return mGraphicAllocation->handle(); }
    bool equals(const std::shared_ptr<C2LinearAllocation>& other) const override {
        return other && other->handle() == handle();
    }

private:
    const std::shared_ptr<C2GraphicAllocation> mGraphicAllocation;
    const C2Allocator::id_t mAllocatorId;
};

C2AllocationBlob::C2AllocationBlob(
        std::shared_ptr<C2GraphicAllocation> graphicAllocation, size_t capacity,
        C2Allocator::id_t allocatorId)
      : C2LinearAllocation(capacity),
        mGraphicAllocation(std::move(graphicAllocation)),
        mAllocatorId(allocatorId) {}

C2AllocationBlob::~C2AllocationBlob() {}

c2_status_t C2AllocationBlob::map(size_t offset, size_t size, C2MemoryUsage usage,
                                  C2Fence* fence, void** addr /* nonnull */) {
    C2PlanarLayout layout;
    C2Rect rect = C2Rect(size, kLinearBufferHeight).at(offset, 0u);
    return mGraphicAllocation->map(rect, usage, fence, &layout, reinterpret_cast<uint8_t**>(addr));
}

c2_status_t C2AllocationBlob::unmap(void* addr, size_t size, C2Fence* fenceFd) {
    C2Rect rect(size, kLinearBufferHeight);
    return mGraphicAllocation->unmap(reinterpret_cast<uint8_t**>(&addr), rect, fenceFd);
}

/* ====================================== BLOB ALLOCATOR ====================================== */
C2AllocatorBlob::C2AllocatorBlob(id_t id) {
    C2MemoryUsage minUsage = {0, 0};
    C2MemoryUsage maxUsage = {C2MemoryUsage::CPU_READ | C2MemoryUsage::READ_PROTECTED,
                              C2MemoryUsage::CPU_WRITE};
    Traits traits = {"android.allocator.blob", id, LINEAR, minUsage, maxUsage};
    mTraits = std::make_shared<C2Allocator::Traits>(traits);
    auto allocatorStore = GetCodec2PlatformAllocatorStore();
    allocatorStore->fetchAllocator(C2PlatformAllocatorStore::GRALLOC, &mC2AllocatorGralloc);
    if (!mC2AllocatorGralloc) {
        ALOGE("Failed to obtain C2AllocatorGralloc as backed allocator");
    }
}

C2AllocatorBlob::~C2AllocatorBlob() {}

c2_status_t C2AllocatorBlob::newLinearAllocation(
        uint32_t capacity, C2MemoryUsage usage, std::shared_ptr<C2LinearAllocation>* allocation) {
    if (allocation == nullptr) {
        return C2_BAD_VALUE;
    }

    allocation->reset();

    if (!mC2AllocatorGralloc) {
        return C2_CORRUPTED;
    }

    std::shared_ptr<C2GraphicAllocation> graphicAllocation;
    c2_status_t status = mC2AllocatorGralloc->newGraphicAllocation(
            capacity, kLinearBufferHeight, kLinearBufferFormat, usage, &graphicAllocation);
    if (status != C2_OK) {
        ALOGE("Failed newGraphicAllocation");
        return status;
    }

    allocation->reset(new C2AllocationBlob(std::move(graphicAllocation),
                                           static_cast<size_t>(capacity), mTraits->id));
    return C2_OK;
}

c2_status_t C2AllocatorBlob::priorLinearAllocation(
        const C2Handle* handle, std::shared_ptr<C2LinearAllocation>* allocation) {
    if (allocation == nullptr) {
        return C2_BAD_VALUE;
    }

    allocation->reset();

    if (!mC2AllocatorGralloc) {
        return C2_CORRUPTED;
    }

    std::shared_ptr<C2GraphicAllocation> graphicAllocation;
    c2_status_t status = mC2AllocatorGralloc->priorGraphicAllocation(handle, &graphicAllocation);
    if (status != C2_OK) {
        ALOGE("Failed priorGraphicAllocation");
        return status;
    }

    const C2Handle* const grallocHandle = graphicAllocation->handle();
    size_t capacity = 0;
    status = GetCapacityFromHandle(grallocHandle, &capacity);
    if (status != C2_OK) {
        ALOGE("Failed to extract capacity from Handle");
        return status;
    }

    allocation->reset(new C2AllocationBlob(std::move(graphicAllocation), capacity, mTraits->id));
    return C2_OK;
}

id_t C2AllocatorBlob::getId() const {
    return mTraits->id;
}

C2String C2AllocatorBlob::getName() const {
    return mTraits->name;
}

std::shared_ptr<const C2Allocator::Traits> C2AllocatorBlob::getTraits() const {
    return mTraits;
}

// static
bool C2AllocatorBlob::isValid(const C2Handle* const o) {
    size_t capacity;
    // Distinguish C2Handle purely allocated by C2AllocatorGralloc, or one allocated through
    // C2AllocatorBlob, by checking the handle's height is 1, and its format is
    // PixelFormat::BLOB by GetCapacityFromHandle().
    return C2AllocatorGralloc::isValid(o) && GetCapacityFromHandle(o, &capacity) == C2_OK;
}

}  // namespace android
+74 −29
Original line number Diff line number Diff line
@@ -605,14 +605,11 @@ c2_status_t C2AllocationGralloc::map(
                          (int32_t)rect.width, (int32_t)rect.height },
                        // TODO: fence
                        hidl_handle(),
                        [&err, &pointer](const auto &maperr, const auto &mapPointer,
                                         int32_t bytesPerPixel, int32_t bytesPerStride) {
                        [&err, &pointer](const auto &maperr, const auto &mapPointer) {
                            err = maperr2error(maperr);
                            if (err == C2_OK) {
                                pointer = mapPointer;
                            }
                            (void)bytesPerPixel;
                            (void)bytesPerStride;
                        }).isOk()) {
                    ALOGE("failed transaction: lock(RGBA_1010102) (@4.0)");
                    return C2_CORRUPTED;
@@ -743,14 +740,11 @@ c2_status_t C2AllocationGralloc::map(
                          (int32_t)rect.width, (int32_t)rect.height },
                        // TODO: fence
                        hidl_handle(),
                        [&err, &pointer](const auto &maperr, const auto &mapPointer,
                                         int32_t bytesPerPixel, int32_t bytesPerStride) {
                        [&err, &pointer](const auto &maperr, const auto &mapPointer) {
                            err = maperr2error(maperr);
                            if (err == C2_OK) {
                                pointer = mapPointer;
                            }
                            (void)bytesPerPixel;
                            (void)bytesPerStride;
                        }).isOk()) {
                    ALOGE("failed transaction: lock(RGBA_8888) (@4.0)");
                    return C2_CORRUPTED;
@@ -816,6 +810,70 @@ c2_status_t C2AllocationGralloc::map(
            break;
        }

        case PixelFormat4::BLOB: {
            void* pointer = nullptr;
            if (mMapper2) {
                if (!mMapper2->lock(const_cast<native_handle_t*>(mBuffer), grallocUsage,
                                    {(int32_t)rect.left, (int32_t)rect.top, (int32_t)rect.width,
                                     (int32_t)rect.height},
                                    // TODO: fence
                                    hidl_handle(),
                                    [&err, &pointer](const auto& maperr, const auto& mapPointer) {
                                        err = maperr2error(maperr);
                                        if (err == C2_OK) {
                                            pointer = mapPointer;
                                        }
                                    }).isOk()) {
                    ALOGE("failed transaction: lock(BLOB)");
                    return C2_CORRUPTED;
                }
            } else if (mMapper3) {
                if (!mMapper3->lock(
                        const_cast<native_handle_t*>(mBuffer),
                        grallocUsage,
                        { (int32_t)rect.left, (int32_t)rect.top,
                          (int32_t)rect.width, (int32_t)rect.height },
                        // TODO: fence
                        hidl_handle(),
                        [&err, &pointer](const auto &maperr, const auto &mapPointer,
                                         int32_t bytesPerPixel, int32_t bytesPerStride) {
                            err = maperr2error(maperr);
                            if (err == C2_OK) {
                                pointer = mapPointer;
                            }
                            (void)bytesPerPixel;
                            (void)bytesPerStride;
                        }).isOk()) {
                    ALOGE("failed transaction: lock(BLOB) (@3.0)");
                    return C2_CORRUPTED;
                }
            } else {
                if (!mMapper4->lock(
                        const_cast<native_handle_t *>(mBuffer),
                        grallocUsage,
                        { (int32_t)rect.left, (int32_t)rect.top,
                          (int32_t)rect.width, (int32_t)rect.height },
                        // TODO: fence
                        hidl_handle(),
                        [&err, &pointer](const auto &maperr, const auto &mapPointer) {
                            err = maperr2error(maperr);
                            if (err == C2_OK) {
                                pointer = mapPointer;
                            }
                        }).isOk()) {
                    ALOGE("failed transaction: lock(BLOB) (@4.0)");
                    return C2_CORRUPTED;
                }
            }
            if (err != C2_OK) {
                ALOGD("lock failed: %d", err);
                return err;
            }

            *addr = static_cast<uint8_t*>(pointer);
            break;
        }

        case PixelFormat4::YCBCR_420_888:
            // fall-through
        case PixelFormat4::YV12:
@@ -875,28 +933,15 @@ c2_status_t C2AllocationGralloc::map(
                    return C2_CORRUPTED;
                }
            } else {
                if (!mMapper4->lockYCbCr(
                        const_cast<native_handle_t *>(mBuffer), grallocUsage,
                        { (int32_t)rect.left, (int32_t)rect.top,
                          (int32_t)rect.width, (int32_t)rect.height },
                        // TODO: fence
                        hidl_handle(),
                        [&err, &ycbcrLayout](const auto &maperr, const auto &mapLayout) {
                            err = maperr2error(maperr);
                            if (err == C2_OK) {
                                ycbcrLayout = YCbCrLayout{
                                        mapLayout.y,
                                        mapLayout.cb,
                                        mapLayout.cr,
                                        mapLayout.yStride,
                                        mapLayout.cStride,
                                        mapLayout.chromaStep};
                            }
                        }).isOk()) {
                // No device currently supports IMapper 4.0 so it is safe to just return an error
                // code here.
                //
                // This will be supported by a combination of lock and BufferMetadata getters.
                // We are going to refactor all the IAllocator/IMapper versioning code into a
                // shared library. We will then add the IMapper 4.0 lockYCbCr support then.
                ALOGE("failed transaction: lockYCbCr (@4.0)");
                return C2_CORRUPTED;
            }
            }
            if (err != C2_OK) {
                ALOGD("lockYCbCr failed: %d", err);
                return err;
Loading