// Copyright 2016 The SwiftShader Authors. All Rights Reserved.
//
// 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.

#ifndef sw_Surface_hpp
#define sw_Surface_hpp

#include "Color.hpp"
#include "Main/Config.hpp"
#include "Common/Resource.hpp"

namespace sw
{
	class Resource;

	template <typename T> struct RectT
	{
		RectT() {}
		RectT(T x0i, T y0i, T x1i, T y1i) : x0(x0i), y0(y0i), x1(x1i), y1(y1i) {}

		void clip(T minX, T minY, T maxX, T maxY)
		{
			x0 = clamp(x0, minX, maxX);
			y0 = clamp(y0, minY, maxY);
			x1 = clamp(x1, minX, maxX);
			y1 = clamp(y1, minY, maxY);
		}

		T width() const  { return x1 - x0; }
		T height() const { return y1 - y0; }

		T x0;   // Inclusive
		T y0;   // Inclusive
		T x1;   // Exclusive
		T y1;   // Exclusive
	};

	typedef RectT<int> Rect;
	typedef RectT<float> RectF;

	template<typename T> struct SliceRectT : public RectT<T>
	{
		SliceRectT() : slice(0) {}
		SliceRectT(const RectT<T>& rect) : RectT<T>(rect), slice(0) {}
		SliceRectT(const RectT<T>& rect, int s) : RectT<T>(rect), slice(s) {}
		SliceRectT(T x0, T y0, T x1, T y1, int s) : RectT<T>(x0, y0, x1, y1), slice(s) {}
		int slice;
	};

	typedef SliceRectT<int> SliceRect;
	typedef SliceRectT<float> SliceRectF;

	enum Format : unsigned char
	{
		FORMAT_NULL,

		FORMAT_A8,
		FORMAT_R8I,
		FORMAT_R8UI,
		FORMAT_R8_SNORM,
		FORMAT_R8,
		FORMAT_R16I,
		FORMAT_R16UI,
		FORMAT_R32I,
		FORMAT_R32UI,
		FORMAT_R3G3B2,
		FORMAT_A8R3G3B2,
		FORMAT_X4R4G4B4,
		FORMAT_A4R4G4B4,
		FORMAT_R4G4B4A4,
		FORMAT_R5G6B5,
		FORMAT_R8G8B8,
		FORMAT_B8G8R8,
		FORMAT_X8R8G8B8,
		FORMAT_A8R8G8B8,
		FORMAT_X8B8G8R8I,
		FORMAT_X8B8G8R8UI,
		FORMAT_X8B8G8R8_SNORM,
		FORMAT_X8B8G8R8,
		FORMAT_A8B8G8R8I,
		FORMAT_A8B8G8R8UI,
		FORMAT_A8B8G8R8_SNORM,
		FORMAT_A8B8G8R8,
		FORMAT_SRGB8_X8,
		FORMAT_SRGB8_A8,
		FORMAT_X1R5G5B5,
		FORMAT_A1R5G5B5,
		FORMAT_R5G5B5A1,
		FORMAT_G8R8I,
		FORMAT_G8R8UI,
		FORMAT_G8R8_SNORM,
		FORMAT_G8R8,
		FORMAT_G16R16,
		FORMAT_G16R16I,
		FORMAT_G16R16UI,
		FORMAT_G32R32I,
		FORMAT_G32R32UI,
		FORMAT_A2R10G10B10,
		FORMAT_A2B10G10R10,
		FORMAT_A2B10G10R10UI,
		FORMAT_A16B16G16R16,
		FORMAT_X16B16G16R16I,
		FORMAT_X16B16G16R16UI,
		FORMAT_A16B16G16R16I,
		FORMAT_A16B16G16R16UI,
		FORMAT_X32B32G32R32I,
		FORMAT_X32B32G32R32UI,
		FORMAT_A32B32G32R32I,
		FORMAT_A32B32G32R32UI,
		// Paletted formats
		FORMAT_P8,
		FORMAT_A8P8,
		// Compressed formats
		FORMAT_DXT1,
		FORMAT_DXT3,
		FORMAT_DXT5,
		FORMAT_ATI1,
		FORMAT_ATI2,
		FORMAT_ETC1,
		FORMAT_R11_EAC,
		FORMAT_SIGNED_R11_EAC,
		FORMAT_RG11_EAC,
		FORMAT_SIGNED_RG11_EAC,
		FORMAT_RGB8_ETC2,
		FORMAT_SRGB8_ETC2,
		FORMAT_RGB8_PUNCHTHROUGH_ALPHA1_ETC2,
		FORMAT_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2,
		FORMAT_RGBA8_ETC2_EAC,
		FORMAT_SRGB8_ALPHA8_ETC2_EAC,
		FORMAT_RGBA_ASTC_4x4_KHR,
		FORMAT_RGBA_ASTC_5x4_KHR,
		FORMAT_RGBA_ASTC_5x5_KHR,
		FORMAT_RGBA_ASTC_6x5_KHR,
		FORMAT_RGBA_ASTC_6x6_KHR,
		FORMAT_RGBA_ASTC_8x5_KHR,
		FORMAT_RGBA_ASTC_8x6_KHR,
		FORMAT_RGBA_ASTC_8x8_KHR,
		FORMAT_RGBA_ASTC_10x5_KHR,
		FORMAT_RGBA_ASTC_10x6_KHR,
		FORMAT_RGBA_ASTC_10x8_KHR,
		FORMAT_RGBA_ASTC_10x10_KHR,
		FORMAT_RGBA_ASTC_12x10_KHR,
		FORMAT_RGBA_ASTC_12x12_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_4x4_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_5x4_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_5x5_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_6x5_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_6x6_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_8x5_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_8x6_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_8x8_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_10x5_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_10x6_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_10x8_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_10x10_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_12x10_KHR,
		FORMAT_SRGB8_ALPHA8_ASTC_12x12_KHR,
		// Floating-point formats
		FORMAT_A16F,
		FORMAT_R16F,
		FORMAT_G16R16F,
		FORMAT_B16G16R16F,
		FORMAT_X16B16G16R16F,
		FORMAT_A16B16G16R16F,
		FORMAT_X16B16G16R16F_UNSIGNED,
		FORMAT_A32F,
		FORMAT_R32F,
		FORMAT_G32R32F,
		FORMAT_B32G32R32F,
		FORMAT_X32B32G32R32F,
		FORMAT_A32B32G32R32F,
		FORMAT_X32B32G32R32F_UNSIGNED,
		// Bump map formats
		FORMAT_V8U8,
		FORMAT_L6V5U5,
		FORMAT_Q8W8V8U8,
		FORMAT_X8L8V8U8,
		FORMAT_A2W10V10U10,
		FORMAT_V16U16,
		FORMAT_A16W16V16U16,
		FORMAT_Q16W16V16U16,
		// Luminance formats
		FORMAT_L8,
		FORMAT_A4L4,
		FORMAT_L16,
		FORMAT_A8L8,
		FORMAT_L16F,
		FORMAT_A16L16F,
		FORMAT_L32F,
		FORMAT_A32L32F,
		// Depth/stencil formats
		FORMAT_D16,
		FORMAT_D32,
		FORMAT_D24X8,
		FORMAT_D24S8,
		FORMAT_D24FS8,
		FORMAT_D32F,                 // Quad layout
		FORMAT_D32FS8,               // Quad layout
		FORMAT_D32F_COMPLEMENTARY,   // Quad layout, 1 - z
		FORMAT_D32FS8_COMPLEMENTARY, // Quad layout, 1 - z
		FORMAT_D32F_LOCKABLE,        // Linear layout
		FORMAT_D32FS8_TEXTURE,       // Linear layout, no PCF
		FORMAT_D32F_SHADOW,          // Linear layout, PCF
		FORMAT_D32FS8_SHADOW,        // Linear layout, PCF
		FORMAT_DF24S8,
		FORMAT_DF16S8,
		FORMAT_INTZ,
		FORMAT_S8,
		// Quad layout framebuffer
		FORMAT_X8G8R8B8Q,
		FORMAT_A8G8R8B8Q,
		// YUV formats
		FORMAT_YV12_BT601,
		FORMAT_YV12_BT709,
		FORMAT_YV12_JFIF,    // Full-swing BT.601

		FORMAT_LAST = FORMAT_YV12_JFIF
	};

	enum Lock
	{
		LOCK_UNLOCKED,
		LOCK_READONLY,
		LOCK_WRITEONLY,
		LOCK_READWRITE,
		LOCK_DISCARD,
		LOCK_UPDATE   // Write access which doesn't dirty the buffer, because it's being updated with the sibling's data.
	};

	class [[clang::lto_visibility_public]] Surface
	{
	private:
		struct Buffer
		{
			friend Surface;

		private:
			void write(int x, int y, int z, const Color<float> &color);
			void write(int x, int y, const Color<float> &color);
			void write(void *element, const Color<float> &color);
			Color<float> read(int x, int y, int z) const;
			Color<float> read(int x, int y) const;
			Color<float> read(void *element) const;
			Color<float> sample(float x, float y, float z) const;
			Color<float> sample(float x, float y, int layer) const;

			void *lockRect(int x, int y, int z, Lock lock);
			void unlockRect();

			void *buffer;
			int width;
			int height;
			int depth;
			short border;
			short samples;

			int bytes;
			int pitchB;
			int pitchP;
			int sliceB;
			int sliceP;

			Format format;
			AtomicInt lock;

			bool dirty;   // Sibling internal/external buffer doesn't match.
		};

	protected:
		Surface(int width, int height, int depth, Format format, void *pixels, int pitch, int slice);
		Surface(Resource *texture, int width, int height, int depth, int border, int samples, Format format, bool lockable, bool renderTarget, int pitchP = 0);

	public:
		static Surface *create(int width, int height, int depth, Format format, void *pixels, int pitch, int slice);
		static Surface *create(Resource *texture, int width, int height, int depth, int border, int samples, Format format, bool lockable, bool renderTarget, int pitchP = 0);

		virtual ~Surface() = 0;

		inline void *lock(int x, int y, int z, Lock lock, Accessor client, bool internal = false);
		inline void unlock(bool internal = false);
		inline int getWidth() const;
		inline int getHeight() const;
		inline int getDepth() const;
		inline int getBorder() const;
		inline Format getFormat(bool internal = false) const;
		inline int getPitchB(bool internal = false) const;
		inline int getPitchP(bool internal = false) const;
		inline int getSliceB(bool internal = false) const;
		inline int getSliceP(bool internal = false) const;

		void *lockExternal(int x, int y, int z, Lock lock, Accessor client);
		void unlockExternal();
		inline Format getExternalFormat() const;
		inline int getExternalPitchB() const;
		inline int getExternalPitchP() const;
		inline int getExternalSliceB() const;
		inline int getExternalSliceP() const;

		virtual void *lockInternal(int x, int y, int z, Lock lock, Accessor client) = 0;
		virtual void unlockInternal() = 0;
		inline Format getInternalFormat() const;
		inline int getInternalPitchB() const;
		inline int getInternalPitchP() const;
		inline int getInternalSliceB() const;
		inline int getInternalSliceP() const;

		void *lockStencil(int x, int y, int front, Accessor client);
		void unlockStencil();
		inline Format getStencilFormat() const;
		inline int getStencilPitchB() const;
		inline int getStencilSliceB() const;

		void sync();                      // Wait for lock(s) to be released.
		virtual bool requiresSync() const { return false; }
		inline bool isUnlocked() const;   // Only reliable after sync().

		inline int getSamples() const;
		inline int getMultiSampleCount() const;
		inline int getSuperSampleCount() const;

		bool isEntire(const Rect& rect) const;
		Rect getRect() const;
		void clearDepth(float depth, int x0, int y0, int width, int height);
		void clearStencil(unsigned char stencil, unsigned char mask, int x0, int y0, int width, int height);
		void fill(const Color<float> &color, int x0, int y0, int width, int height);

		Color<float> readExternal(int x, int y, int z) const;
		Color<float> readExternal(int x, int y) const;
		Color<float> sampleExternal(float x, float y, float z) const;
		Color<float> sampleExternal(float x, float y) const;
		void writeExternal(int x, int y, int z, const Color<float> &color);
		void writeExternal(int x, int y, const Color<float> &color);

		void copyInternal(const Surface* src, int x, int y, float srcX, float srcY, bool filter);
		void copyInternal(const Surface* src, int x, int y, int z, float srcX, float srcY, float srcZ, bool filter);

		enum Edge { TOP, BOTTOM, RIGHT, LEFT };
		void copyCubeEdge(Edge dstEdge, Surface *src, Edge srcEdge);
		void computeCubeCorner(int x0, int y0, int x1, int y1);

		bool hasStencil() const;
		bool hasDepth() const;
		bool hasPalette() const;
		bool isRenderTarget() const;

		bool hasDirtyContents() const;
		void markContentsClean();
		inline bool isExternalDirty() const;
		Resource *getResource();

		static int bytes(Format format);
		static int pitchB(int width, int border, Format format, bool target);
		static int pitchP(int width, int border, Format format, bool target);
		static int sliceB(int width, int height, int border, Format format, bool target);
		static int sliceP(int width, int height, int border, Format format, bool target);
		static size_t size(int width, int height, int depth, int border, int samples, Format format);

		static bool isStencil(Format format);
		static bool isDepth(Format format);
		static bool hasQuadLayout(Format format);
		static bool isPalette(Format format);

		static bool isFloatFormat(Format format);
		static bool isUnsignedComponent(Format format, int component);
		static bool isSRGBreadable(Format format);
		static bool isSRGBwritable(Format format);
		static bool isSRGBformat(Format format);
		static bool isCompressed(Format format);
		static bool isSignedNonNormalizedInteger(Format format);
		static bool isUnsignedNonNormalizedInteger(Format format);
		static bool isNonNormalizedInteger(Format format);
		static bool isNormalizedInteger(Format format);
		static int componentCount(Format format);

		static void setTexturePalette(unsigned int *palette);

	private:
		sw::Resource *resource;

		typedef unsigned char byte;
		typedef unsigned short word;
		typedef unsigned int dword;
		typedef uint64_t qword;

		struct DXT1
		{
			word c0;
			word c1;
			dword lut;
		};

		struct DXT3
		{
			qword a;

			word c0;
			word c1;
			dword lut;
		};

		struct DXT5
		{
			union
			{
				struct
				{
					byte a0;
					byte a1;
				};

				qword alut;   // Skip first 16 bit
			};

			word c0;
			word c1;
			dword clut;
		};

		struct ATI2
		{
			union
			{
				struct
				{
					byte y0;
					byte y1;
				};

				qword ylut;   // Skip first 16 bit
			};

			union
			{
				struct
				{
					byte x0;
					byte x1;
				};

				qword xlut;   // Skip first 16 bit
			};
		};

		struct ATI1
		{
			union
			{
				struct
				{
					byte r0;
					byte r1;
				};

				qword rlut;   // Skip first 16 bit
			};
		};

		static void decodeR8G8B8(Buffer &destination, Buffer &source);
		static void decodeX1R5G5B5(Buffer &destination, Buffer &source);
		static void decodeA1R5G5B5(Buffer &destination, Buffer &source);
		static void decodeX4R4G4B4(Buffer &destination, Buffer &source);
		static void decodeA4R4G4B4(Buffer &destination, Buffer &source);
		static void decodeP8(Buffer &destination, Buffer &source);

		static void decodeDXT1(Buffer &internal, Buffer &external);
		static void decodeDXT3(Buffer &internal, Buffer &external);
		static void decodeDXT5(Buffer &internal, Buffer &external);
		static void decodeATI1(Buffer &internal, Buffer &external);
		static void decodeATI2(Buffer &internal, Buffer &external);
		static void decodeEAC(Buffer &internal, Buffer &external, int nbChannels, bool isSigned);
		static void decodeETC2(Buffer &internal, Buffer &external, int nbAlphaBits, bool isSRGB);
		static void decodeASTC(Buffer &internal, Buffer &external, int xSize, int ySize, int zSize, bool isSRGB);

		static void update(Buffer &destination, Buffer &source);
		static void genericUpdate(Buffer &destination, Buffer &source);
		static void *allocateBuffer(int width, int height, int depth, int border, int samples, Format format);
		static void memfill4(void *buffer, int pattern, int bytes);

		bool identicalBuffers() const;
		Format selectInternalFormat(Format format) const;

		void resolve();

		Buffer external;
		Buffer internal;
		Buffer stencil;

		const bool lockable;
		const bool renderTarget;

		bool dirtyContents;   // Sibling surfaces need updating (mipmaps / cube borders).
		unsigned int paletteUsed;

		static unsigned int *palette;   // FIXME: Not multi-device safe
		static unsigned int paletteID;

		bool hasParent;
		bool ownExternal;
	};
}

#undef min
#undef max

namespace sw
{
	void *Surface::lock(int x, int y, int z, Lock lock, Accessor client, bool internal)
	{
		return internal ? lockInternal(x, y, z, lock, client) : lockExternal(x, y, z, lock, client);
	}

	void Surface::unlock(bool internal)
	{
		return internal ? unlockInternal() : unlockExternal();
	}

	int Surface::getWidth() const
	{
		return external.width;
	}

	int Surface::getHeight() const
	{
		return external.height;
	}

	int Surface::getDepth() const
	{
		return external.depth;
	}

	int Surface::getBorder() const
	{
		return internal.border;
	}

	Format Surface::getFormat(bool internal) const
	{
		return internal ? getInternalFormat() : getExternalFormat();
	}

	int Surface::getPitchB(bool internal) const
	{
		return internal ? getInternalPitchB() : getExternalPitchB();
	}

	int Surface::getPitchP(bool internal) const
	{
		return internal ? getInternalPitchP() : getExternalPitchP();
	}

	int Surface::getSliceB(bool internal) const
	{
		return internal ? getInternalSliceB() : getExternalSliceB();
	}

	int Surface::getSliceP(bool internal) const
	{
		return internal ? getInternalSliceP() : getExternalSliceP();
	}

	Format Surface::getExternalFormat() const
	{
		return external.format;
	}

	int Surface::getExternalPitchB() const
	{
		return external.pitchB;
	}

	int Surface::getExternalPitchP() const
	{
		return external.pitchP;
	}

	int Surface::getExternalSliceB() const
	{
		return external.sliceB;
	}

	int Surface::getExternalSliceP() const
	{
		return external.sliceP;
	}

	Format Surface::getInternalFormat() const
	{
		return internal.format;
	}

	int Surface::getInternalPitchB() const
	{
		return internal.pitchB;
	}

	int Surface::getInternalPitchP() const
	{
		return internal.pitchP;
	}

	int Surface::getInternalSliceB() const
	{
		return internal.sliceB;
	}

	int Surface::getInternalSliceP() const
	{
		return internal.sliceP;
	}

	Format Surface::getStencilFormat() const
	{
		return stencil.format;
	}

	int Surface::getStencilPitchB() const
	{
		return stencil.pitchB;
	}

	int Surface::getStencilSliceB() const
	{
		return stencil.sliceB;
	}

	int Surface::getSamples() const
	{
		return internal.samples;
	}

	int Surface::getMultiSampleCount() const
	{
		return sw::min((int)internal.samples, 4);
	}

	int Surface::getSuperSampleCount() const
	{
		return internal.samples > 4 ? internal.samples / 4 : 1;
	}

	bool Surface::isUnlocked() const
	{
		return external.lock == LOCK_UNLOCKED &&
		       internal.lock == LOCK_UNLOCKED &&
		       stencil.lock == LOCK_UNLOCKED;
	}

	bool Surface::isExternalDirty() const
	{
		return external.buffer && external.buffer != internal.buffer && external.dirty;
	}
}

#endif   // sw_Surface_hpp
