/*
 * Copyright 2022 Google LLC
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

#include "src/gpu/graphite/dawn/DawnGraphiteUtils.h"

#include "include/gpu/ShaderErrorHandler.h"
#include "include/gpu/graphite/Context.h"
#include "include/gpu/graphite/dawn/DawnBackendContext.h"
#include "src/gpu/graphite/ContextPriv.h"
#include "src/gpu/graphite/TextureFormat.h"
#include "src/gpu/graphite/dawn/DawnQueueManager.h"
#include "src/gpu/graphite/dawn/DawnSharedContext.h"

namespace skgpu::graphite {

namespace ContextFactory {
std::unique_ptr<Context> MakeDawn(const DawnBackendContext& backendContext,
                                  const ContextOptions& options) {
    sk_sp<SharedContext> sharedContext = DawnSharedContext::Make(backendContext, options);
    if (!sharedContext) {
        return nullptr;
    }

    auto queueManager =
            std::make_unique<DawnQueueManager>(backendContext.fQueue, sharedContext.get());
    if (!queueManager) {
        return nullptr;
    }

    auto context = ContextCtorAccessor::MakeContext(std::move(sharedContext),
                                                    std::move(queueManager),
                                                    options);
    SkASSERT(context);
    return context;
}
} // namespace ContextFactory

SkTextureCompressionType DawnFormatToCompressionType(wgpu::TextureFormat format) {
    switch (format) {
        case wgpu::TextureFormat::ETC2RGB8Unorm: return SkTextureCompressionType::kETC2_RGB8_UNORM;
        case wgpu::TextureFormat::BC1RGBAUnorm:  return SkTextureCompressionType::kBC1_RGBA8_UNORM;
        default:                                 return SkTextureCompressionType::kNone;
    }
}

#define DAWN_FORMAT_MAPPING(M) \
        M(TextureFormat::kR8,             wgpu::TextureFormat::R8Unorm)                     \
        /*TextureFormat::kR16             Native-only */                                    \
        M(TextureFormat::kR16F,           wgpu::TextureFormat::R16Float)                    \
        M(TextureFormat::kR32F,           wgpu::TextureFormat::R32Float)                    \
        /*TextureFormat::kA8              unsupported */                                    \
        M(TextureFormat::kRG8,            wgpu::TextureFormat::RG8Unorm)                    \
        /*TextureFormat::kR16             Native-only */                                    \
        M(TextureFormat::kRG16F,          wgpu::TextureFormat::RG16Float)                   \
        M(TextureFormat::kRG32F,          wgpu::TextureFormat::RG32Float)                   \
        /*TextureFormat::kRGB8            unsupported */                                    \
        /*TextureFormat::kBGR8            unsupported */                                    \
        /*TextureFormat::kB5_G6_R5,       unsupported */                                    \
        /*TextureFormat::kR5_G6_B5        unsupported */                                    \
        /*TextureFormat::kRGB16           unsupported */                                    \
        /*TextureFormat::kRGB16F          unsupported */                                    \
        /*TextureFormat::kRGB32F          unsupported */                                    \
        /*TextureFormat::kRGB8_sRGB       unsupported */                                    \
        /*TextureFormat::kBGR10_XR        unsupported */                                    \
        M(TextureFormat::kRGBA8,          wgpu::TextureFormat::RGBA8Unorm)                  \
        /*TextureFormat::kRGBA16          Native-only */                                    \
        M(TextureFormat::kRGBA16F,        wgpu::TextureFormat::RGBA16Float)                 \
        M(TextureFormat::kRGBA32F,        wgpu::TextureFormat::RGBA32Float)                 \
        M(TextureFormat::kRGB10_A2,       wgpu::TextureFormat::RGB10A2Unorm)                \
        M(TextureFormat::kRGBA8_sRGB,     wgpu::TextureFormat::RGBA8UnormSrgb)              \
        M(TextureFormat::kBGRA8,          wgpu::TextureFormat::BGRA8Unorm)                  \
        /*TextureFormat::kBGR10_A2        unsupported */                                    \
        M(TextureFormat::kBGRA8_sRGB,     wgpu::TextureFormat::BGRA8UnormSrgb)              \
        /*TextureFormat::kABGR4,          unsupported */                                    \
        /*TextureFormat::kARGB4           unsupported */                                    \
        /*TextureFormat::kBGRA10x6_XR     unsupported */                                    \
        M(TextureFormat::kRGB8_ETC2,      wgpu::TextureFormat::ETC2RGB8Unorm)               \
        M(TextureFormat::kRGB8_ETC2_sRGB, wgpu::TextureFormat::ETC2RGB8UnormSrgb)           \
        /*TextureFormat::kRGB_BC1         unsupported */                                    \
        M(TextureFormat::kRGBA8_BC1,      wgpu::TextureFormat::BC1RGBAUnorm)                \
        M(TextureFormat::kRGBA8_BC1_sRGB, wgpu::TextureFormat::BC1RGBAUnormSrgb)            \
        /*TextureFormat::kYUV8_P2_420     Native-only */                                    \
        /*TextureFormat::kYUV8_P3_420     unsupported */                                    \
        /*TextureFormat::kYUV10x6_P2_420  Native-only */                                    \
        /*TextureFormat::kExternal        Native-only */                                    \
        M(TextureFormat::kS8,             wgpu::TextureFormat::Stencil8)                    \
        M(TextureFormat::kD16,            wgpu::TextureFormat::Depth16Unorm)                \
        M(TextureFormat::kD32F,           wgpu::TextureFormat::Depth32Float)                \
        M(TextureFormat::kD24_S8,         wgpu::TextureFormat::Depth24PlusStencil8)         \
        M(TextureFormat::kD32F_S8,        wgpu::TextureFormat::Depth32FloatStencil8)        \

#if !defined(__EMSCRIPTEN__)
#define DAWN_FORMAT_MAPPING_NATIVE_ONLY(M) \
        M(TextureFormat::kR16,            wgpu::TextureFormat::R16Unorm)                    \
        M(TextureFormat::kRG16,           wgpu::TextureFormat::RG16Unorm)                   \
        M(TextureFormat::kRGBA16,         wgpu::TextureFormat::RGBA16Unorm)                 \
        M(TextureFormat::kYUV8_P2_420,    wgpu::TextureFormat::R8BG8Biplanar420Unorm)       \
        M(TextureFormat::kYUV10x6_P2_420, wgpu::TextureFormat::R10X6BG10X6Biplanar420Unorm) \
        M(TextureFormat::kExternal,       wgpu::TextureFormat::External)
#else
#define DAWN_FORMAT_MAPPING_NATIVE_ONLY(M)
#endif

TextureFormat DawnFormatToTextureFormat(wgpu::TextureFormat format) {
#define M(TF, WGPU) case WGPU: return TF;
    switch(format) {
        DAWN_FORMAT_MAPPING(M)
        DAWN_FORMAT_MAPPING_NATIVE_ONLY(M)
        default: return TextureFormat::kUnsupported;
    }
#undef M
}
wgpu::TextureFormat TextureFormatToDawnFormat(TextureFormat format) {
#define M(TF, WGPU) case TF: return WGPU;
    switch(format) {
        DAWN_FORMAT_MAPPING(M)
        DAWN_FORMAT_MAPPING_NATIVE_ONLY(M)
        default: return wgpu::TextureFormat::Undefined;
    }
#undef M
}

static bool check_shader_module([[maybe_unused]] const DawnSharedContext* sharedContext,
                                wgpu::ShaderModule* module,
                                const char* shaderText,
                                ShaderErrorHandler* errorHandler) {
    // Prior to emsdk 3.1.51 wgpu::ShaderModule::GetCompilationInfo is unimplemented.
#if defined(__EMSCRIPTEN__)                                      &&  \
        ((__EMSCRIPTEN_major__ <  3                               || \
         (__EMSCRIPTEN_major__ == 3 && __EMSCRIPTEN_minor__ <  1) || \
         (__EMSCRIPTEN_major__ == 3 && __EMSCRIPTEN_minor__ == 1 && __EMSCRIPTEN_tiny__ < 51)))
    return true;
#else
    struct Handler {
        static void Fn(WGPUCompilationInfoRequestStatus status,
                       const WGPUCompilationInfo* info,
                       void* userdata) {
            Handler* self = reinterpret_cast<Handler*>(userdata);
            SkASSERT(status == WGPUCompilationInfoRequestStatus_Success);

            // Walk the message list and check for hard errors.
            self->fSuccess = true;
            for (size_t index = 0; index < info->messageCount; ++index) {
                const WGPUCompilationMessage& entry = info->messages[index];
                if (entry.type == WGPUCompilationMessageType_Error) {
                    self->fSuccess = false;
                    break;
                }
            }

            // If we found a hard error, report the compilation messages to the error handler.
            if (!self->fSuccess) {
                std::string errors;
                for (size_t index = 0; index < info->messageCount; ++index) {
                    const WGPUCompilationMessage& entry = info->messages[index];
                    std::string messageString(entry.message.data, entry.message.length);
                    errors += "line " + std::to_string(entry.lineNum) + ':' +
                              std::to_string(entry.linePos) + ' ' + messageString + '\n';
                }
                self->fErrorHandler->compileError(
                        self->fShaderText, errors.c_str(), /*shaderWasCached=*/false);
            }
        }

        const char* fShaderText;
        ShaderErrorHandler* fErrorHandler;
        bool fSuccess = false;
    };

    Handler handler;
    handler.fShaderText = shaderText;
    handler.fErrorHandler = errorHandler;
#if defined(__EMSCRIPTEN__)
    // Deprecated function.
    module->GetCompilationInfo(&Handler::Fn, &handler);
#else
    // New API.
    wgpu::FutureWaitInfo waitInfo{};
    waitInfo.future = module->GetCompilationInfo(
            wgpu::CallbackMode::WaitAnyOnly,
            [handlerPtr = &handler](wgpu::CompilationInfoRequestStatus status,
                                    const wgpu::CompilationInfo* info) {
                Handler::Fn(static_cast<WGPUCompilationInfoRequestStatus>(status),
                            reinterpret_cast<const WGPUCompilationInfo*>(info),
                            handlerPtr);
            });

    const auto& instance = static_cast<const DawnSharedContext*>(sharedContext)->instance();
    [[maybe_unused]] auto status =
            instance.WaitAny(1, &waitInfo, /*timeoutNS=*/std::numeric_limits<uint64_t>::max());
    SkASSERT(status == wgpu::WaitStatus::Success);
#endif  // defined(__EMSCRIPTEN__)

    return handler.fSuccess;
#endif
}

bool DawnCompileWGSLShaderModule(const DawnSharedContext* sharedContext,
                                 const char* label,
                                 const SkSL::NativeShader& wgsl,
                                 wgpu::ShaderModule* module,
                                 ShaderErrorHandler* errorHandler) {
#if defined(__EMSCRIPTEN__)
    wgpu::ShaderModuleWGSLDescriptor wgslDesc;
#else
    wgpu::ShaderSourceWGSL wgslDesc;
#endif
    wgslDesc.code = wgsl.fText.c_str();

    wgpu::ShaderModuleDescriptor desc;
    desc.nextInChain = &wgslDesc;
    if (sharedContext->caps()->setBackendLabels()) {
        desc.label = label;
    }

    *module = sharedContext->device().CreateShaderModule(&desc);

    return check_shader_module(sharedContext, module, wgsl.fText.c_str(), errorHandler);
}

#if !defined(__EMSCRIPTEN__)

namespace {

static constexpr int kUsesExternalFormatBits  = 1;
static constexpr int kYcbcrModelBits          = 3;
static constexpr int kYcbcrRangeBits          = 1;
static constexpr int kXChromaOffsetBits       = 1;
static constexpr int kYChromaOffsetBits       = 1;
// wgpu::FilterMode contains Undefined/Nearest/Linear entries (Linear is 2).
static constexpr int kChromaFilterBits        = 2;
static constexpr int kForceExplicitReconBits  = 1;
static constexpr int kComponentBits           = 3;

static constexpr int kUsesExternalFormatShift = 0;
static constexpr int kYcbcrModelShift         = kUsesExternalFormatShift + kUsesExternalFormatBits;
static constexpr int kYcbcrRangeShift         = kYcbcrModelShift         + kYcbcrModelBits;
static constexpr int kXChromaOffsetShift      = kYcbcrRangeShift         + kYcbcrRangeBits;
static constexpr int kYChromaOffsetShift      = kXChromaOffsetShift      + kXChromaOffsetBits;
static constexpr int kChromaFilterShift       = kYChromaOffsetShift      + kYChromaOffsetBits;
static constexpr int kForceExplicitReconShift = kChromaFilterShift       + kChromaFilterBits;
static constexpr int kComponentRShift         = kForceExplicitReconShift + kForceExplicitReconBits;
static constexpr int kComponentGShift         = kComponentRShift         + kComponentBits;
static constexpr int kComponentBShift         = kComponentGShift         + kComponentBits;
static constexpr int kComponentAShift         = kComponentBShift         + kComponentBits;

static constexpr uint32_t kUseExternalFormatMask =
        ((1 << kUsesExternalFormatBits) - 1) << kUsesExternalFormatShift;
static constexpr uint32_t kYcbcrModelMask =
        ((1 << kYcbcrModelBits) - 1) << kYcbcrModelShift;
static constexpr uint32_t kYcbcrRangeMask =
        ((1 << kYcbcrRangeBits) - 1) << kYcbcrRangeShift;
static constexpr uint32_t kXChromaOffsetMask =
        ((1 << kXChromaOffsetBits) - 1) << kXChromaOffsetShift;
static constexpr uint32_t kYChromaOffsetMask =
        ((1 << kYChromaOffsetBits) - 1) << kYChromaOffsetShift;
static constexpr uint32_t kChromaFilterMask =
        ((1 << kChromaFilterBits) - 1) << kChromaFilterShift;
static constexpr uint32_t kForceExplicitReconMask =
        ((1 << kForceExplicitReconBits) - 1) << kForceExplicitReconShift;
static constexpr uint32_t kComponentRMask = ((1 << kComponentBits) - 1) << kComponentRShift;
static constexpr uint32_t kComponentBMask = ((1 << kComponentBits) - 1) << kComponentBShift;
static constexpr uint32_t kComponentGMask = ((1 << kComponentBits) - 1) << kComponentGShift;
static constexpr uint32_t kComponentAMask = ((1 << kComponentBits) - 1) << kComponentAShift;

} // anonymous namespace

bool DawnDescriptorsAreEquivalent(const wgpu::YCbCrVkDescriptor& desc1,
                                  const wgpu::YCbCrVkDescriptor& desc2) {
    return desc1.vkFormat                    == desc2.vkFormat                    &&
           desc1.vkYCbCrModel                == desc2.vkYCbCrModel                &&
           desc1.vkYCbCrRange                == desc2.vkYCbCrRange                &&
           desc1.vkComponentSwizzleRed       == desc2.vkComponentSwizzleRed       &&
           desc1.vkComponentSwizzleGreen     == desc2.vkComponentSwizzleGreen     &&
           desc1.vkComponentSwizzleBlue      == desc2.vkComponentSwizzleBlue      &&
           desc1.vkComponentSwizzleAlpha     == desc2.vkComponentSwizzleAlpha     &&
           desc1.vkXChromaOffset             == desc2.vkXChromaOffset             &&
           desc1.vkYChromaOffset             == desc2.vkYChromaOffset             &&
           desc1.vkChromaFilter              == desc2.vkChromaFilter              &&
           desc1.forceExplicitReconstruction == desc2.forceExplicitReconstruction &&
           desc1.externalFormat              == desc2.externalFormat;
}

bool DawnDescriptorIsValid(const wgpu::YCbCrVkDescriptor& desc) {
    static const wgpu::YCbCrVkDescriptor kDefaultYcbcrDescriptor = {};
    return !DawnDescriptorsAreEquivalent(desc, kDefaultYcbcrDescriptor);
}

bool DawnDescriptorUsesExternalFormat(const wgpu::YCbCrVkDescriptor& desc) {
    SkASSERT(desc.externalFormat != 0 || desc.vkFormat != 0);
    return desc.externalFormat != 0;
}

ImmutableSamplerInfo DawnDescriptorToImmutableSamplerInfo(const wgpu::YCbCrVkDescriptor& desc) {
    static_assert(kComponentAShift + kComponentBits <= 32);
    SkASSERT(desc.vkYCbCrModel                          < (1u << kYcbcrModelBits    ));
    SkASSERT(desc.vkYCbCrRange                          < (1u << kYcbcrRangeBits    ));
    SkASSERT(desc.vkXChromaOffset                       < (1u << kXChromaOffsetBits ));
    SkASSERT(desc.vkYChromaOffset                       < (1u << kYChromaOffsetBits ));
    SkASSERT(static_cast<uint32_t>(desc.vkChromaFilter) < (1u << kChromaFilterBits  ));
    SkASSERT(desc.vkComponentSwizzleRed                 < (1u << kComponentBits     ));
    SkASSERT(desc.vkComponentSwizzleGreen               < (1u << kComponentBits     ));
    SkASSERT(desc.vkComponentSwizzleBlue                < (1u << kComponentBits     ));
    SkASSERT(desc.vkComponentSwizzleAlpha               < (1u << kComponentBits     ));
    SkASSERT(static_cast<uint32_t>(desc.forceExplicitReconstruction)
             < (1u << kForceExplicitReconBits));

    const bool usesExternalFormat = DawnDescriptorUsesExternalFormat(desc);

    ImmutableSamplerInfo info;
    info.fNonFormatYcbcrConversionInfo =
            (((uint32_t)(usesExternalFormat               ) << kUsesExternalFormatShift) |
             ((uint32_t)(desc.vkYCbCrModel                ) << kYcbcrModelShift        ) |
             ((uint32_t)(desc.vkYCbCrRange                ) << kYcbcrRangeShift        ) |
             ((uint32_t)(desc.vkXChromaOffset             ) << kXChromaOffsetShift     ) |
             ((uint32_t)(desc.vkYChromaOffset             ) << kYChromaOffsetShift     ) |
             ((uint32_t)(desc.vkChromaFilter              ) << kChromaFilterShift      ) |
             ((uint32_t)(desc.forceExplicitReconstruction ) << kForceExplicitReconShift) |
             ((uint32_t)(desc.vkComponentSwizzleRed       ) << kComponentRShift        ) |
             ((uint32_t)(desc.vkComponentSwizzleGreen     ) << kComponentGShift        ) |
             ((uint32_t)(desc.vkComponentSwizzleBlue      ) << kComponentBShift        ) |
             ((uint32_t)(desc.vkComponentSwizzleAlpha     ) << kComponentAShift        ));
    info.fFormat = usesExternalFormat ? desc.externalFormat : desc.vkFormat;
    return info;
}

wgpu::YCbCrVkDescriptor DawnDescriptorFromImmutableSamplerInfo(ImmutableSamplerInfo info) {
    const uint32_t nonFormatInfo = info.fNonFormatYcbcrConversionInfo;

    wgpu::YCbCrVkDescriptor desc;
    const bool usesExternalFormat =
            (nonFormatInfo >> kUsesExternalFormatShift) & kUseExternalFormatMask;
    if (usesExternalFormat) {
        desc.vkFormat = 0;
        desc.externalFormat = info.fFormat;
    } else {
        desc.vkFormat = (uint32_t) info.fFormat;
        desc.externalFormat = 0;
    }

    desc.vkYCbCrModel                = (nonFormatInfo & kYcbcrModelMask)    >> kYcbcrModelShift;
    desc.vkYCbCrRange                = (nonFormatInfo & kYcbcrRangeMask)    >> kYcbcrRangeShift;
    desc.vkComponentSwizzleRed       = (nonFormatInfo & kComponentRMask)    >> kComponentRShift;
    desc.vkComponentSwizzleGreen     = (nonFormatInfo & kComponentGMask)    >> kComponentGShift;
    desc.vkComponentSwizzleBlue      = (nonFormatInfo & kComponentBMask)    >> kComponentBShift;
    desc.vkComponentSwizzleAlpha     = (nonFormatInfo & kComponentAMask)    >> kComponentAShift;
    desc.vkXChromaOffset             = (nonFormatInfo & kXChromaOffsetMask) >> kXChromaOffsetShift;
    desc.vkYChromaOffset             = (nonFormatInfo & kYChromaOffsetMask) >> kYChromaOffsetShift;
    desc.vkChromaFilter              = static_cast<wgpu::FilterMode>(
            (nonFormatInfo & kChromaFilterMask) >> kChromaFilterShift);
    desc.forceExplicitReconstruction =
            (nonFormatInfo & kForceExplicitReconMask) >> kForceExplicitReconShift;
    return desc;
}

#endif // !defined(__EMSCRIPTEN__)

} // namespace skgpu::graphite
