// Copyright 2024 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 expresso or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "gfxstream/guest/RenderControl.h"

#include <vector>

#include "HostConnection.h"

namespace {

typedef struct compose_layer {
    uint32_t cbHandle;
    hwc2_composition_t composeMode;
    hwc_rect_t displayFrame;
    hwc_frect_t crop;
    int32_t blendMode;
    float alpha;
    hwc_color_t color;
    hwc_transform_t transform;
} ComposeLayer;

typedef struct compose_device {
    uint32_t version;
    uint32_t targetHandle;
    uint32_t numLayers;
    struct compose_layer layer[0];
} ComposeDevice;

typedef struct compose_device_v2 {
    uint32_t version;
    uint32_t displayId;
    uint32_t targetHandle;
    uint32_t numLayers;
    struct compose_layer layer[0];
} ComposeDevice_v2;

class RenderControlDeviceImpl {
   public:
    RenderControlDeviceImpl() : mHostConnection(HostConnection::createUnique()) {}

    RenderControlDeviceImpl(const RenderControlDeviceImpl& rhs) = delete;
    RenderControlDeviceImpl& operator=(const RenderControlDeviceImpl& rhs) = delete;

    RenderControlDeviceImpl(RenderControlDeviceImpl&& rhs) = delete;
    RenderControlDeviceImpl& operator=(RenderControlDeviceImpl&& rhs) = delete;

    int DoCompose(std::vector<uint8_t>& bytes) {
        if (!mHostConnection) {
            ALOGE("RenderControlDevice missing HostConnection.");
            return -1;
        }

        auto* rc = mHostConnection->rcEncoder();
        if (!rc) {
            ALOGE("RenderControlDevice missing rcEncoder.");
            return -1;
        }

        mHostConnection->lock();
        rc->rcCompose(rc, bytes.size(), bytes.data());
        mHostConnection->unlock();
        return 0;
    }

   private:
    std::unique_ptr<HostConnection> mHostConnection;
};

RenderControlDevice* ToHandle(RenderControlDeviceImpl* device) {
    return reinterpret_cast<RenderControlDevice*>(device);
}

RenderControlDeviceImpl* ToImpl(RenderControlDevice* device) {
    return reinterpret_cast<RenderControlDeviceImpl*>(device);
}

}  // namespace

extern "C" __attribute__((visibility("default"))) RenderControlDevice* rcCreateDevice() {
    return ToHandle(new RenderControlDeviceImpl());
}

extern "C" __attribute__((visibility("default"))) void rcDestroyDevice(
    RenderControlDevice* pDevice) {
    if (pDevice != nullptr) {
        delete ToImpl(pDevice);
    }
}

extern "C" __attribute__((visibility("default"))) int rcCompose(
    RenderControlDevice* deviceHandle, const RenderControlComposition* pComposition,
    uint32_t compositionLayerCount, const RenderControlCompositionLayer* pCompositionLayers) {
    const size_t bytesNeeded =
        sizeof(ComposeDevice_v2) + (sizeof(ComposeLayer) * compositionLayerCount);
    std::vector<uint8_t> bytes(bytesNeeded);

    auto* composeDevice = reinterpret_cast<ComposeDevice_v2*>(bytes.data());
    auto* composeLayers = composeDevice->layer;

    composeDevice->version = 2;
    composeDevice->displayId = 0;
    composeDevice->targetHandle = pComposition->compositionResultColorBufferHandle;
    composeDevice->numLayers = compositionLayerCount;

    for (uint32_t i = 0; i < compositionLayerCount; i++) {
        auto& requestLayer = pCompositionLayers[i];
        auto& composeLayer = composeLayers[i];
        composeLayer.cbHandle = requestLayer.colorBufferHandle;
        composeLayer.composeMode = requestLayer.composeMode;
        composeLayer.displayFrame = requestLayer.displayFrame;
        composeLayer.crop = requestLayer.crop;
        composeLayer.blendMode = requestLayer.blendMode;
        composeLayer.alpha = requestLayer.alpha;
        composeLayer.color = requestLayer.color;
        composeLayer.transform = requestLayer.transform;
    }

    RenderControlDeviceImpl* device = ToImpl(deviceHandle);
    return device->DoCompose(bytes);
}
