/*========================== begin_copyright_notice ============================

Copyright (C) 2017-2021 Intel Corporation

SPDX-License-Identifier: MIT

============================= end_copyright_notice ===========================*/

#pragma once
#include "inc/common/igfxfmid.h"
#include "Compiler/compiler_caps.h"
#include "Compiler/igc_workaround.h"
#include "common/Types.hpp"
#include "Probe/Assertion.h"
#include "common/igc_regkeys.hpp"


namespace IGC
{

class CPlatform
{
    PLATFORM m_platformInfo = {};
    SCompilerHwCaps m_caps = {};
    WA_TABLE m_WaTable = {};
    SKU_FEATURE_TABLE m_SkuTable = {};
    GT_SYSTEM_INFO m_GTSystemInfo = {};
    OCLCaps m_OCLCaps = {};

public:
    CPlatform() {}

    CPlatform(const PLATFORM& platform)
    {
        m_platformInfo = platform;
    }

public:
void setOclCaps(OCLCaps& caps) { m_OCLCaps = caps; }
uint32_t getMaxOCLParameteSize() const {
    uint32_t limitFromFlag = IGC_GET_FLAG_VALUE(OverrideOCLMaxParamSize);
    return limitFromFlag ? limitFromFlag : m_OCLCaps.MaxParameterSize;
}
void OverrideRevId(unsigned short newRevId)
{
    m_platformInfo.usRevId = newRevId;
}

void OverrideDeviceId(unsigned short newDeviceID)
{
    m_platformInfo.usDeviceID = newDeviceID;
}


void OverrideProductFamily(unsigned int productID)
{
    PRODUCT_FAMILY eProd = static_cast<PRODUCT_FAMILY>(productID);
    if(eProd > IGFX_UNKNOWN && eProd < IGFX_MAX_PRODUCT)
        m_platformInfo.eProductFamily = (PRODUCT_FAMILY)productID;
}

    WA_TABLE const& getWATable() const { return m_WaTable; }
SKU_FEATURE_TABLE const& getSkuTable() const { return m_SkuTable; }

bool hasPackedVertexAttr() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool hasScaledMessage() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool has8ByteA64ByteScatteredMessage() const { return m_platformInfo.eRenderCoreFamily == IGFX_GEN8_CORE; }

bool hasPredicatedBarriers() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool hasIEEEMinmaxBit() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool hasL1ReadOnlyCache() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }
// Gen10+ HW supports adding vertex start to vertex ID
bool hasVertexOffsetEnable() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }

// Gen10+ HW supports sending base instance, base vertex and draw index with
// VF, this is programmed using 3DSTATE_VF_SGVS2 command.
bool hasSGVS2Command() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }

// Sampler supports normalization of coordinates during sampling from
// rectangle textures.
bool supportsCoordinateNormalizationForRectangleTextures() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }

/// On some platforms ld sources order is: u lod v r
bool hasOldLdOrder() const { return m_platformInfo.eRenderCoreFamily <= IGFX_GEN8_CORE; }
bool supportSampleAndLd_lz() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool supportSamplerToRT() const {
        return (m_platformInfo.eProductFamily == IGFX_CHERRYVIEW) || (m_platformInfo.eRenderCoreFamily == IGFX_GEN9_CORE);
    }
    bool supportFP16() const {
        return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE) ||
            ((m_platformInfo.eRenderCoreFamily == IGFX_GEN8_CORE) && (m_platformInfo.eProductFamily == IGFX_CHERRYVIEW));
    }
bool supportFP16Rounding() const { return false; }
bool supportSamplerFp16Input() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }
bool supportPooledEU() const { return m_SkuTable.FtrPooledEuEnabled != 0; }
bool supportSplitSend() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool supportSendInstShootdown() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }
bool supportHSEightPatchDispatch() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool supportSingleInstanceVertexShader() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }
bool supportDSDualPatchDispatch() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool needsHSBarrierIDWorkaround() const { return m_platformInfo.eRenderCoreFamily <= IGFX_GEN10_CORE; }
bool supportBindless() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool supportsBindlessSamplers() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }

bool SupportSurfaceInfoMessage() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }
bool SupportHDCUnormFormats() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }
    bool localMemFenceSupress() const {
        return m_platformInfo.eRenderCoreFamily <= IGFX_GEN9_CORE ||
            IGC_IS_FLAG_ENABLED(DisbleLocalFences);
    }
bool psSimd32SkipStallHeuristic() const { return m_caps.KernelHwCaps.EUThreadsPerEU == 6; }
bool enablePSsimd32() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE; }

bool supportSimd32PerPixelPSWithNumSamples16() const
{
    return false;
}


bool supportDisableMidThreadPreemptionSwitch() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE; }

bool needSWStencil() const
{
        return (m_platformInfo.eRenderCoreFamily == IGFX_GEN9_CORE && IGC_IS_FLAG_ENABLED(EnableSoftwareStencil));
}
bool supportMSAARateInPayload() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE;
}

bool support16BitImmSrcForMad() const {
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE);
}
PRODUCT_FAMILY GetProductFamily() const { return m_platformInfo.eProductFamily; }
unsigned short GetDeviceId() const { return m_platformInfo.usDeviceID; }
unsigned short GetRevId() const { return m_platformInfo.usRevId; }
GFXCORE_FAMILY GetPlatformFamily() const { return m_platformInfo.eRenderCoreFamily; }
const PLATFORM& getPlatformInfo() const { return m_platformInfo; }
void SetCaps(const SCompilerHwCaps& caps) { m_caps = caps; }
void SetWATable(const WA_TABLE& waTable) { m_WaTable = waTable; }
void SetSkuTable(const SKU_FEATURE_TABLE& skuTable) { m_SkuTable = skuTable; }
void SetGTSystemInfo(const SUscGTSystemInfo gtSystemInfo) {
    m_GTSystemInfo.EUCount = gtSystemInfo.EUCount;
    m_GTSystemInfo.ThreadCount = gtSystemInfo.ThreadCount;
    m_GTSystemInfo.SliceCount = gtSystemInfo.SliceCount;
    m_GTSystemInfo.SubSliceCount = gtSystemInfo.SubSliceCount;
    m_GTSystemInfo.SLMSizeInKb = gtSystemInfo.SLMSizeInKb;
    m_GTSystemInfo.TotalPsThreadsWindowerRange = gtSystemInfo.TotalPsThreadsWindowerRange;
    m_GTSystemInfo.TotalVsThreads = gtSystemInfo.TotalVsThreads;
    m_GTSystemInfo.TotalVsThreads_Pocs = gtSystemInfo.TotalVsThreads_Pocs;
    m_GTSystemInfo.TotalDsThreads = gtSystemInfo.TotalDsThreads;
    m_GTSystemInfo.TotalGsThreads = gtSystemInfo.TotalGsThreads;
    m_GTSystemInfo.TotalHsThreads = gtSystemInfo.TotalHsThreads;
    m_GTSystemInfo.MaxEuPerSubSlice = gtSystemInfo.MaxEuPerSubSlice;
    m_GTSystemInfo.EuCountPerPoolMax = gtSystemInfo.EuCountPerPoolMax;
    m_GTSystemInfo.EuCountPerPoolMin = gtSystemInfo.EuCountPerPoolMin;
    m_GTSystemInfo.MaxSlicesSupported = gtSystemInfo.MaxSlicesSupported;
    m_GTSystemInfo.MaxSubSlicesSupported = gtSystemInfo.MaxSubSlicesSupported;
    m_GTSystemInfo.IsDynamicallyPopulated = gtSystemInfo.IsDynamicallyPopulated;
    m_GTSystemInfo.CsrSizeInMb = gtSystemInfo.CsrSizeInMb;
}

    void SetGTSystemInfo(const GT_SYSTEM_INFO& gtSystemInfo) {
    m_GTSystemInfo = gtSystemInfo;
}

GT_SYSTEM_INFO GetGTSystemInfo() const { return m_GTSystemInfo; }

    unsigned int getMaxPixelShaderThreads() const {
        return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE ?
            m_caps.PixelShaderThreadsWindowerRange - 1 : m_caps.PixelShaderThreadsWindowerRange - 2;
    }
bool supportGPGPUMidThreadPreemption() const {
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE &&
        m_platformInfo.eRenderCoreFamily <= IGFX_GEN11LP_CORE;
}
bool supportFtrWddm2Svm() const { return m_SkuTable.FtrWddm2Svm != 0; }
bool supportStructuredAsRaw() const {
        return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE;
    }
bool supportSamplerCacheResinfo() const { return m_platformInfo.eRenderCoreFamily == IGFX_GEN8_CORE; }

unsigned int getMaxVertexShaderThreads(const bool isPositionOnlyShader) const
{
    const unsigned int maxVertexShaderThreads = isPositionOnlyShader ? m_caps.VertexShaderThreadsPosh : m_caps.VertexShaderThreads;
    return maxVertexShaderThreads - 1;
}
unsigned int getMaxGeometryShaderThreads() const { return m_caps.GeometryShaderThreads - 1; }
unsigned int getMaxHullShaderThreads() const { return m_caps.HullShaderThreads - 1; }
unsigned int getMaxDomainShaderThreads() const { return m_caps.DomainShaderThreads - 1; }
unsigned int getMaxGPGPUShaderThreads() const { return m_caps.MediaShaderThreads - 1; }
unsigned int getKernelPointerAlignSize() const { return m_caps.KernelHwCaps.KernelPointerAlignSize; }
unsigned int getSharedLocalMemoryBlockSize() const { return m_caps.SharedLocalMemoryBlockSize; }
unsigned int getMaxNumberThreadPerSubslice() const
{
    //total number of threads per subslice
        if (m_caps.KernelHwCaps.SubSliceCount != 0)
        return m_caps.KernelHwCaps.ThreadCount / m_caps.KernelHwCaps.SubSliceCount;
    return 0;
}
unsigned int getMaxNumberThreadPerWorkgroupPooledMax() const
{
    return m_caps.KernelHwCaps.EUCountPerPoolMax * m_caps.KernelHwCaps.EUThreadsPerEU;
}
unsigned int getFFTIDBitMask() const {
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE) ? 0x3FF : 0x1FF;
}
unsigned int getBarrierCountBits(unsigned int count) const
{
    // Returns barrier count field + enable for barrier message
    if (m_platformInfo.eRenderCoreFamily <= IGFX_GEN10_CORE)
    {
        // up to Gen9 barrier count is in bits 14:9, enable is bit 15
        return (count << 9) | (1 << 15);
    }
    else
    {
        // for Gen10+ barrier count is in bits 14:8, enable is bit 15
        return (count << 8) | (1 << 15);
    }
}

bool supportsDrawParametersSGVs() const
{
    // Gen10+, 3DSTATE_VF_SGVS_2
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE;
}

bool hasPSDBottleneck() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE; }

bool supportsHardwareResourceStreamer() const
{
    return m_platformInfo.eRenderCoreFamily < IGFX_GEN11_CORE;
}
bool AOComputeShadersSIMD32Mode() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}
unsigned int getHullShaderThreadInstanceIdBitFieldPosition() const
{
    // HS thread receives instance ID in R0.2 bits 22:16 for Gen10+ and bits 23:17 for older Gens
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE) ? 16 : 17;
}
bool supportsBinaryAtomicCounterMessage() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE;
}
bool supportSLMBlockMessage() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}

bool hasSLMFence() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}

bool supportRotateInstruction() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE; }
bool supportLRPInstruction() const { return m_platformInfo.eRenderCoreFamily < IGFX_GEN11_CORE; }
bool support16bitMSAAPayload() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE; }
bool supportTwoStackTSG() const
{
    //Will need check for specific skus where TwoStackTSG is enabled
    //Not all skus have it enabled
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}
bool enableBlendToDiscardAndFill() const
{
    return (m_platformInfo.eRenderCoreFamily < IGFX_GEN11_CORE);
}
bool HSUsesHWBarriers() const
{
    // HS HW barriers work correctly since ICL platform.
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}

bool NeedResetA0forVxHA0() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE);
}

unsigned int GetLogBindlessSamplerSize() const
{
    // Samplers are 16 bytes
    return 4;
}

bool SupportCPS() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN10_CORE);
}

bool supportsThreadCombining() const
{
    return (!(!m_WaTable.WaEnablePooledEuFor2x6 &&
        m_platformInfo.eProductFamily == IGFX_BROXTON &&
        m_GTSystemInfo.SubSliceCount == 2))
        ;
}

bool enableMaxWorkGroupSizeCalculation() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE) &&
        IGC_IS_FLAG_ENABLED(EnableMaxWGSizeCalculation);
}

bool has8DWA64ScatteredMessage() const { return m_platformInfo.eRenderCoreFamily < IGFX_GEN12_CORE; }

bool flushL3ForTypedMemory() const
{
    return m_platformInfo.eRenderCoreFamily <= IGFX_GEN11_CORE;
}

bool supportsStencil(SIMDMode simdMode) const
{
    return getMinDispatchMode() == SIMDMode::SIMD16 ? true : simdMode == SIMDMode::SIMD8;
}

bool hasFDIV() const {
    if (IGC_IS_FLAG_ENABLED(DisableFDIV))
        return false;
    return (m_platformInfo.eRenderCoreFamily < IGFX_GEN12_CORE);
}

bool doIntegerMad() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN11_CORE && m_platformInfo.eProductFamily != IGFX_DG1 &&
        IGC_IS_FLAG_ENABLED(EnableIntegerMad);
}

bool isDG1() const
{
    return m_platformInfo.eProductFamily == IGFX_DG1;
}

bool simplePushIsFasterThanGather() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE;
}

bool singleThreadBasedInstScheduling() const
{
    return m_platformInfo.eRenderCoreFamily < IGFX_GEN12_CORE;
}

//all the platforms which do not support 64 bit operations and
//needs int64 emulation support. Except also for BXT where
//64-bit inst has much lower throughput compared to SKL.
//Emulating it improves performance on some benchmarks and
//won't have impact on the overall performance.
bool need64BitEmulation() const {
    return m_platformInfo.eProductFamily == IGFX_GEMINILAKE ||
        m_platformInfo.eProductFamily == IGFX_BROXTON ||
        hasNoInt64Inst();
}

bool HDCCoalesceSLMAtomicINCWithNoReturn() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE;
}

bool HDCCoalesceAtomicCounterAccess() const
{
    return (m_platformInfo.eRenderCoreFamily < IGFX_GEN12_CORE) && IGC_IS_FLAG_DISABLED(ForceSWCoalescingOfAtomicCounter);
}

bool supportsMCSNonCompressedFix() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE; }

bool hasHWDp4AddSupport() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE; }

bool useOnlyEightPatchDispatchHS() const
{
    return (m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE);
}

bool supportsPrimitiveReplication() const
{
    return ((m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE) ||
            (m_platformInfo.eRenderCoreFamily == IGFX_GEN11_CORE && m_platformInfo.eProductFamily == IGFX_ICELAKE));
}

// If true then screen space coordinates for upper-left vertex of a triangle
// being rasterized are delivered together with source depth or W deltas.
bool hasStartCoordinatesDeliveredWithDeltas() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE;
}

bool disableStaticVertexCount() const
{
    return m_WaTable.Wa_14012504847 != 0 || IGC_IS_FLAG_ENABLED(ForceStaticToDynamic);
}

bool hasSamplerSupport() const
{
    return true;
}

uint32_t getMinPushConstantBufferAlignment() const
{
    return 8; // DWORDs
}

// Returns the default limit of pushed constant data in GRFs. This value limits
// the amount of constant buffer data promoted to registers.
uint32_t getBlockPushConstantGRFThreshold() const
{
    constexpr uint32_t defaultThreshold = 31;
    constexpr uint32_t gen9GT2Threshold = 15;

    const GTTYPE gt = m_platformInfo.eGTType;
    switch (m_platformInfo.eProductFamily)
    {
    case IGFX_COFFEELAKE:
    case IGFX_SKYLAKE:
    case IGFX_KABYLAKE:
        return (gt == GTTYPE_GT2) ? gen9GT2Threshold : defaultThreshold;
    default:
        return defaultThreshold;
    }
}

bool hasDualSubSlices() const
{
    bool hasDualSS = m_platformInfo.eRenderCoreFamily == IGFX_GEN12_CORE ||
        m_platformInfo.eRenderCoreFamily == IGFX_GEN12LP_CORE;
    return hasDualSS;
}

unsigned getSlmSizePerSsOrDss() const
{
    // GTSysInfo sets SLMSize only for gen12+
    unsigned slmSizePerSsOrDss = 65536;
    if (hasDualSubSlices())
    {
        if (GetGTSystemInfo().DualSubSliceCount)
        {
            slmSizePerSsOrDss = GetGTSystemInfo().SLMSizeInKb / GetGTSystemInfo().DualSubSliceCount * 1024;
        }
        else
        {
            slmSizePerSsOrDss = 131072;
        }
    }
    return slmSizePerSsOrDss;
}

bool canForcePrivateToGlobal() const
{
    return m_platformInfo.eRenderCoreFamily >= IGFX_GEN9_CORE && IGC_IS_FLAG_ENABLED(ForcePrivateMemoryToGlobalOnGeneric);
}

bool getHWTIDFromSR0() const
{
    return isXeHPSDVPlus();
}

bool supportAdd3Instruction() const
{
    return isXeHPSDVPlus();
}

bool supportBfnInstruction() const
{
    return isXeHPSDVPlus();
}

bool supportDpasInstruction() const
{
    return isXeHPSDVPlus();
}

bool supportLoadThreadPayloadForCompute() const
{
    return isXeHPSDVPlus();
}

bool Enable32BitIntDivRemEmu() const
{
    return isXeHPSDVPlus();
}

bool support16DWURBWrite() const
{
    return IGC_IS_FLAG_ENABLED(Enable16DWURBWrite) && isXeHPSDVPlus();
}

bool hasScratchSurface() const
{
    return isXeHPSDVPlus();
}

bool hasAtomicPreDec() const
{
    return !isXeHPSDVPlus();
}

bool support26BitBSOFormat() const
{
    return isXeHPSDVPlus();
}

bool needsHeaderForAtomicCounter() const
{
    return isXeHPSDVPlus();
}

bool doScalar64bScan() const
{
    return isXeHPSDVPlus();
}

bool hasHWLocalThreadID() const
{
    return isXeHPSDVPlus();
}

unsigned int getOfflineCompilerMaxWorkGroupSize() const
{
    if (isXeHPSDVPlus())
        return 1024;
    return 448;
}

bool hasFP16AtomicMinMax() const
{
    return isXeHPSDVPlus();
}

bool hasFP32GlobalAtomicAdd() const
{
    return isXeHPSDVPlus();
}

bool has16OWSLMBlockRW() const
{
    return IGC_IS_FLAG_ENABLED(Enable16OWSLMBlockRW) && isXeHPSDVPlus();
}

bool supportInlineData() const
{
    return isXeHPSDVPlus();
}

bool supportsAutoGRFSelection() const
{
    return m_platformInfo.eProductFamily == IGFX_XE_HP_SDV;
}

bool isXeHPSDVPlus() const
{
    return m_platformInfo.eProductFamily >= IGFX_XE_HP_SDV;
}

bool supportInlineDataOCL() const
{
    return isXeHPSDVPlus();
}

bool has64BMediaBlockRW() const
{
    return IGC_IS_FLAG_ENABLED(Enable64BMediaBlockRW) && isXeHPSDVPlus();
}

bool hasNoFullI64Support() const
{
    return hasNoInt64Inst();
}

bool hasNoInt64AddInst() const
{
    return hasNoFullI64Support();
}

bool supportsSIMD16TypedRW() const
{
    return false;
}

bool supportsStaticRegSharing() const
{
    return isXeHPSDVPlus();
}
bool emulateByteScraterMsgForSS() const
{
    return isXeHPSDVPlus() && (m_platformInfo.usRevId == 0 || IGC_IS_FLAG_ENABLED(EnableUntypedSurfRWofSS));
}

//all the platforms which DONOT support 64 bit int operations
bool hasNoInt64Inst() const {
    return m_platformInfo.eProductFamily == IGFX_ICELAKE_LP ||
        m_platformInfo.eProductFamily == IGFX_LAKEFIELD ||
        m_platformInfo.eProductFamily == IGFX_ELKHARTLAKE ||
        m_platformInfo.eProductFamily == IGFX_JASPERLAKE ||
        m_platformInfo.eProductFamily == IGFX_TIGERLAKE_LP ||
        m_platformInfo.eProductFamily == IGFX_ROCKETLAKE ||
        m_platformInfo.eProductFamily == IGFX_ALDERLAKE_S ||
        m_platformInfo.eProductFamily == IGFX_DG1;
}

//all the platforms which DONOT support 64 bit float operations
bool hasNoFP64Inst() const {
    return m_platformInfo.eProductFamily == IGFX_ICELAKE_LP ||
        m_platformInfo.eProductFamily == IGFX_LAKEFIELD ||
        m_platformInfo.eProductFamily == IGFX_ELKHARTLAKE ||
        m_platformInfo.eProductFamily == IGFX_JASPERLAKE ||
        m_platformInfo.eProductFamily == IGFX_TIGERLAKE_LP ||
        m_platformInfo.eProductFamily == IGFX_ROCKETLAKE ||
        m_platformInfo.eProductFamily == IGFX_ALDERLAKE_S ||
        m_platformInfo.eProductFamily == IGFX_DG1;
}

//all the platforms which have correctly rounded macros (INVM, RSQRTM, MADM)
bool hasCorrectlyRoundedMacros() const {
    return m_platformInfo.eProductFamily != IGFX_ICELAKE_LP &&
        m_platformInfo.eProductFamily != IGFX_LAKEFIELD &&
        m_platformInfo.eProductFamily != IGFX_JASPERLAKE &&
        m_platformInfo.eProductFamily != IGFX_TIGERLAKE_LP &&
        m_platformInfo.eProductFamily != IGFX_ROCKETLAKE &&
        m_platformInfo.eProductFamily != IGFX_DG1 &&
        m_platformInfo.eProductFamily != IGFX_ALDERLAKE_S;
}

bool hasFusedEU() const { return m_platformInfo.eRenderCoreFamily >= IGFX_GEN12_CORE; }
bool supportMixMode() const {
    return IGC_IS_FLAG_ENABLED(ForceMixMode) ||
        (IGC_IS_FLAG_DISABLED(DisableMixMode) &&
        (m_platformInfo.eProductFamily == IGFX_CHERRYVIEW ||
            m_platformInfo.eRenderCoreFamily == IGFX_GEN9_CORE ||
            m_platformInfo.eRenderCoreFamily == IGFX_GEN10_CORE));
}
bool DSPrimitiveIDPayloadPhaseCanBeSkipped() const { return false; }
bool useScratchSpaceForOCL() const
{
    return IGC_IS_FLAG_ENABLED(EnableOCLScratchPrivateMemory);
}

uint32_t getGRFSize() const
{
    return 32;
}

uint32_t maxPerThreadScratchSpace() const
{
    return 0x200000;
}

bool supportByteALUOperation() const
{
    return true;
}

bool NeedsHDCFenceBeforeEOTInPixelShader() const
{
    return false;
}

bool canFuseTypedWrite() const
{
    return IGC_IS_FLAG_ENABLED(FuseTypedWrite);
}

unsigned int getMaxNumberHWThreadForEachWG() const
{
    if (m_platformInfo.eRenderCoreFamily < IGFX_GEN12_CORE)
    {
        //each WG is dispatched into one subslice for GEN11 and before
        return getMaxNumberThreadPerSubslice();
    }
    else
    {
        return getMaxNumberThreadPerSubslice() * 2;
    }
}

// max block size for legacy OWord block messages
uint32_t getMaxBlockMsgSize(bool isSLM) const
{
    return 128;
}

SIMDMode getMinDispatchMode() const
{
    return SIMDMode::SIMD8;
}

unsigned getAccChNumUD() const
{
    return 8;
}

int getBSOLocInExtDescriptor() const
{
    return 12;
}

// ***** Below go accessor methods for testing WA data from WA_TABLE *****

bool WaDoNotPushConstantsForAllPulledGSTopologies() const
{
    return (m_platformInfo.eProductFamily == IGFX_BROADWELL) ||
        m_WaTable.WaDoNotPushConstantsForAllPulledGSTopologies != 0;
}

bool WaForceMinMaxGSThreadCount() const
{
    return m_WaTable.WaForceMinMaxGSThreadCount != 0;
}

bool WaOCLEnableFMaxFMinPlusZero() const
{
    return m_WaTable.WaOCLEnableFMaxFMinPlusZero != 0;
}

bool WaDisableSendsSrc0DstOverlap() const
{
    return m_WaTable.WaDisableSendsSrc0DstOverlap != 0;
}

bool WaDisableEuBypass() const
{
        return (m_WaTable.WaDisableEuBypassOnSimd16Float32 != 0);
}

bool WaDisableDSDualPatchMode() const
{
    return m_WaTable.WaDisableDSDualPatchMode == 0;
}

bool WaDispatchGRFHWIssueInGSAndHSUnit() const
{
    return m_WaTable.WaDispatchGRFHWIssueInGSAndHSUnit != 0;
}

bool WaSamplerResponseLengthMustBeGreaterThan1() const
{
    return m_WaTable.WaSamplerResponseLengthMustBeGreaterThan1 != 0;
}

bool WaDisableDSPushConstantsInFusedDownModeWithOnlyTwoSubslices() const
{
    return ((m_WaTable.WaDisableDSPushConstantsInFusedDownModeWithOnlyTwoSubslices) &&
            (m_GTSystemInfo.IsDynamicallyPopulated && m_GTSystemInfo.SubSliceCount == 2));
}

bool WaDisableVSPushConstantsInFusedDownModeWithOnlyTwoSubslices() const
{
    return ((m_WaTable.WaDisableVSPushConstantsInFusedDownModeWithOnlyTwoSubslices) &&
            (m_GTSystemInfo.IsDynamicallyPopulated && m_GTSystemInfo.SubSliceCount == 2));
}

bool WaForceCB0ToBeZeroWhenSendingPC() const
{
    return m_WaTable.WaForceCB0ToBeZeroWhenSendingPC != 0;
}

bool WaConservativeRasterization() const
{
    return (m_WaTable.WaConservativeRasterization != 0 &&
        IGC_IS_FLAG_ENABLED(ApplyConservativeRastWAHeader));
}

bool WaReturnZeroforRTReadOutsidePrimitive() const
{
    return m_WaTable.WaReturnZeroforRTReadOutsidePrimitive != 0;
}

bool WaFixInnerCoverageWithSampleMask() const
{
    return m_WaTable.Wa_220856683 != 0;
}

bool WaForceDSToWriteURB() const
{
    return m_WaTable.Wa_1805992985 != 0;
}

bool WaOverwriteFFID() const
{
    return m_WaTable.Wa_1409460247 != 0;
}


bool WaDisableSendSrcDstOverlap() const
{
    return (!IGC_IS_FLAG_ENABLED(DisableSendSrcDstOverlapWA)) &&
        (m_SkuTable.FtrWddm2Svm != 0 || m_platformInfo.eRenderCoreFamily == IGFX_GEN10_CORE ||
            m_platformInfo.eRenderCoreFamily == IGFX_GEN11_CORE);

}

bool WaInsertHDCFenceBeforeEOTWhenSparseAliasedResources() const
{
    return m_WaTable.Wa_1807084924 != 0;
}

bool WaDisableSampleLz() const
{
    return (IGC_IS_FLAG_DISABLED(DisableWaSampleLZ) && m_WaTable.Wa_14013297064);
}

bool WaEnableA64WA() const
{
    if (IGC_IS_FLAG_ENABLED(EnableA64WA) && m_WaTable.Wa_14010595310) {
        return true;
    }
    return false;
}

//Only enable this WA for TGLLP+ because, in pre TGLLP projects, smov was replaced with two instructions which caused performance penalty.
bool enableMultiGRFAccessWA() const
{
    return (m_platformInfo.eProductFamily >= IGFX_TIGERLAKE_LP);
}

// Return true if platform has structured control-flow instructions and IGC wants to use them.
bool hasSCF() const
{
    bool doscf = true;
    return doscf;
}

const SCompilerHwCaps& GetCaps() { return m_caps; }

bool supportHeaderRTW() const
{
    return true;
}

bool preemptionSupported() const
{

    return GetPlatformFamily() >= IGFX_GEN9_CORE;
};

};

}//namespace IGC
