Add support for 'alternative' image view min lod calculation

According to ''Image Level(s) Selection" in spec, the image view
minLod value can be used as-is, or floor()-ed.

This change runs verification in affected test twice, once requiring
'preferred' method, falling back to 'alternative' if 'preferred' method fails.

Components: Vulkan

VK-GL-CTS Issue: 3556

Affects: dEQP-VK.texture.*min_lod*

Change-Id: I3af08485dbd99ad8d666c6f19aac3456130c375d
diff --git a/external/vulkancts/modules/vulkan/texture/vktTextureMipmapTests.cpp b/external/vulkancts/modules/vulkan/texture/vktTextureMipmapTests.cpp
index 305d11d..5fe42d7 100644
--- a/external/vulkancts/modules/vulkan/texture/vktTextureMipmapTests.cpp
+++ b/external/vulkancts/modules/vulkan/texture/vktTextureMipmapTests.cpp
@@ -1053,11 +1053,8 @@
 		const tcu::IVec4		formatBitDepth	= getTextureFormatBitDepth(vk::mapVkFormat(VK_FORMAT_R8G8B8A8_UNORM));
 		const tcu::PixelFormat	pixelFormat		(formatBitDepth[0], formatBitDepth[1], formatBitDepth[2], formatBitDepth[3]);
 		const bool				isTrilinear		= m_minFilter == Sampler::NEAREST_MIPMAP_LINEAR || m_minFilter == Sampler::LINEAR_MIPMAP_LINEAR;
-		tcu::Surface			referenceFrame	(viewportWidth, viewportHeight);
-		tcu::Surface			errorMask		(viewportWidth, viewportHeight);
 		tcu::LookupPrecision	lookupPrec;
 		tcu::LodPrecision		lodPrec;
-		int						numFailedPixels	= 0;
 
 		lookupPrec.coordBits		= tcu::IVec3(20, 20, 0);
 		lookupPrec.uvwBits			= tcu::IVec3(16, 16, 0); // Doesn't really matter since pixels are unicolored.
@@ -1066,51 +1063,68 @@
 		lodPrec.derivateBits		= 10;
 		lodPrec.lodBits				= 8;
 
-		for (int gridY = 0; gridY < gridHeight; gridY++)
+		auto compareAndLogImages = [&] (tcu::ImageViewMinLodMode imageViewLodMode = tcu::IMAGEVIEWMINLODMODE_PREFERRED)
 		{
-			for (int gridX = 0; gridX < gridWidth; gridX++)
+			tcu::Surface			referenceFrame	(viewportWidth, viewportHeight);
+			tcu::Surface			errorMask		(viewportWidth, viewportHeight);
+
+			int						numFailedPixels = 0;
+
+			for (int gridY = 0; gridY < gridHeight; gridY++)
 			{
-				const int	curX		= cellWidth*gridX;
-				const int	curY		= cellHeight*gridY;
-				const int	curW		= gridX+1 == gridWidth ? (viewportWidth-curX) : cellWidth;
-				const int	curH		= gridY+1 == gridHeight ? (viewportHeight-curY) : cellHeight;
-				const int	cellNdx		= gridY*gridWidth + gridX;
+				for (int gridX = 0; gridX < gridWidth; gridX++)
+				{
+					const int	curX		= cellWidth*gridX;
+					const int	curY		= cellHeight*gridY;
+					const int	curW		= gridX+1 == gridWidth ? (viewportWidth-curX) : cellWidth;
+					const int	curH		= gridY+1 == gridHeight ? (viewportHeight-curY) : cellHeight;
+					const int	cellNdx		= gridY*gridWidth + gridX;
 
-				getReferenceParams(refParams,cellNdx);
+					getReferenceParams(refParams,cellNdx);
 
-				// Compute texcoord.
-				if (refParams.samplerType == glu::TextureTestUtil::SAMPLERTYPE_FETCH_FLOAT)
-					getBasicTexCoord2DImageViewMinLodIntTexCoord(texCoord);
-				else
-					getBasicTexCoord2D(texCoord, cellNdx);
+					refParams.imageViewMinLodMode = imageViewLodMode;
 
-				// Render ideal result
-				sampleTexture(tcu::SurfaceAccess(referenceFrame, pixelFormat, curX, curY, curW, curH),
-							  refTexture, &texCoord[0], refParams);
+					// Compute texcoord.
+					if (refParams.samplerType == glu::TextureTestUtil::SAMPLERTYPE_FETCH_FLOAT)
+						getBasicTexCoord2DImageViewMinLodIntTexCoord(texCoord);
+					else
+						getBasicTexCoord2D(texCoord, cellNdx);
 
-				// Compare this cell
-				numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
-															tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
-															tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
-															m_texture->getTexture(), &texCoord[0], refParams,
-															lookupPrec, lodPrec, m_context.getTestContext().getWatchDog());
+					// Render ideal result
+					sampleTexture(tcu::SurfaceAccess(referenceFrame, pixelFormat, curX, curY, curW, curH),
+								  refTexture, &texCoord[0], refParams);
+
+					// Compare this cell
+					numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
+																tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
+																tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
+																m_texture->getTexture(), &texCoord[0], refParams,
+																lookupPrec, lodPrec, m_context.getTestContext().getWatchDog());
+				}
 			}
-		}
 
-		if (numFailedPixels > 0)
-			m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
+			if (numFailedPixels > 0)
+			{
+				m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
+													<< TestLog::Image("ErrorMask", "Error mask", errorMask);
+			}
+			return numFailedPixels;
+		};
 
 		m_context.getTestContext().getLog() << TestLog::ImageSet("Result", "Verification result")
 											<< TestLog::Image("Rendered", "Rendered image", renderedFrame);
 
-		if (numFailedPixels > 0)
-		{
-			m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
-												<< TestLog::Image("ErrorMask", "Error mask", errorMask);
-		}
+		int numFailedPixels = compareAndLogImages();
 
+		if (numFailedPixels > 0 && refParams.imageViewMinLod > 0.0f)
+		{
+			numFailedPixels = compareAndLogImages(tcu::IMAGEVIEWMINLODMODE_ALTERNATIVE);
+		}
 		m_context.getTestContext().getLog() << TestLog::EndImageSet;
 
+		if (numFailedPixels > 0)
+			m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
+
 		{
 			const bool isOk = numFailedPixels == 0;
 			return isOk ? tcu::TestStatus::pass("pass") : tcu::TestStatus::fail("fail");
@@ -1315,9 +1329,6 @@
 	{
 		const tcu::IVec4		formatBitDepth		= getTextureFormatBitDepth(mapVkFormat(VK_FORMAT_R8G8B8A8_UNORM));
 		const tcu::PixelFormat	pixelFormat			(formatBitDepth[0], formatBitDepth[1], formatBitDepth[2], formatBitDepth[3]);
-		tcu::Surface			referenceFrame		(viewportWidth, viewportHeight);
-		tcu::Surface			errorMask			(viewportWidth, viewportHeight);
-		int						numFailedPixels		= 0;
 		tcu::LookupPrecision	lookupPrec;
 		tcu::LodPrecision		lodPrec;
 
@@ -1334,44 +1345,59 @@
 		lodPrec.derivateBits				= 10;
 		lodPrec.lodBits						= 6;
 
-		for (int cellNdx = 0; cellNdx < (int)gridLayout.size(); cellNdx++)
+		auto compareAndLogImages = [&](tcu::ImageViewMinLodMode imageViewLodMode = tcu::IMAGEVIEWMINLODMODE_PREFERRED)
 		{
-			const int				curX		= gridLayout[cellNdx].x();
-			const int				curY		= gridLayout[cellNdx].y();
-			const int				curW		= gridLayout[cellNdx].z();
-			const int				curH		= gridLayout[cellNdx].w();
-			const tcu::CubeFace		cubeFace	= (tcu::CubeFace)(cellNdx % tcu::CUBEFACE_LAST);
+			tcu::Surface			referenceFrame(viewportWidth, viewportHeight);
+			tcu::Surface			errorMask(viewportWidth, viewportHeight);
+			int						numFailedPixels = 0;
 
-			computeQuadTexCoordCube(texCoord, cubeFace);
-			getReferenceParams(refParams, cellNdx);
-
-			// Render ideal reference.
+			for (int cellNdx = 0; cellNdx < (int)gridLayout.size(); cellNdx++)
 			{
-				tcu::SurfaceAccess idealDst(referenceFrame, pixelFormat, curX, curY, curW, curH);
-				sampleTexture(idealDst, refTexture, &texCoord[0], refParams);
+				const int				curX		= gridLayout[cellNdx].x();
+				const int				curY		= gridLayout[cellNdx].y();
+				const int				curW		= gridLayout[cellNdx].z();
+				const int				curH		= gridLayout[cellNdx].w();
+				const tcu::CubeFace		cubeFace	= (tcu::CubeFace)(cellNdx % tcu::CUBEFACE_LAST);
+
+				computeQuadTexCoordCube(texCoord, cubeFace);
+				getReferenceParams(refParams, cellNdx);
+
+				refParams.imageViewMinLodMode = imageViewLodMode;
+
+				// Render ideal reference.
+				{
+					tcu::SurfaceAccess idealDst(referenceFrame, pixelFormat, curX, curY, curW, curH);
+					sampleTexture(idealDst, refTexture, &texCoord[0], refParams);
+				}
+
+				// Compare this cell
+				numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
+															tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
+															tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
+															m_texture->getTexture(), &texCoord[0], refParams,
+															lookupPrec, lodPrec,  m_context.getTestContext().getWatchDog());
 			}
+			if (numFailedPixels > 0)
+			{
+				m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
+													<< TestLog::Image("ErrorMask", "Error mask", errorMask);
+			}
+			return numFailedPixels;
+		};
 
-			// Compare this cell
-			numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
-														tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
-														tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
-														m_texture->getTexture(), &texCoord[0], refParams,
-														lookupPrec, lodPrec,  m_context.getTestContext().getWatchDog());
-		}
+		m_context.getTestContext().getLog() << TestLog::ImageSet("Result", "Verification result")
+											<< TestLog::Image("Rendered", "Rendered image", renderedFrame);
 
-		if (numFailedPixels > 0)
-			 m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
+		int numFailedPixels = compareAndLogImages();
 
-		 m_context.getTestContext().getLog() << TestLog::ImageSet("Result", "Verification result")
-											 << TestLog::Image("Rendered", "Rendered image", renderedFrame);
-
-		if (numFailedPixels > 0)
+		if (numFailedPixels > 0 && refParams.imageViewMinLod > 0.0f)
 		{
-			 m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
-												 << TestLog::Image("ErrorMask", "Error mask", errorMask);
+			numFailedPixels = compareAndLogImages(tcu::IMAGEVIEWMINLODMODE_ALTERNATIVE);
 		}
+		m_context.getTestContext().getLog() << TestLog::EndImageSet;
 
-		 m_context.getTestContext().getLog() << TestLog::EndImageSet;
+		if (numFailedPixels > 0)
+			m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
 
 		{
 			const bool isOk = numFailedPixels == 0;
@@ -1584,11 +1610,8 @@
 		const tcu::IVec4		formatBitDepth	= getTextureFormatBitDepth(mapVkFormat(VK_FORMAT_R8G8B8A8_UNORM));
 		const tcu::PixelFormat	pixelFormat		(formatBitDepth[0], formatBitDepth[1], formatBitDepth[2], formatBitDepth[3]);
 		const bool				isTrilinear		= m_minFilter == Sampler::NEAREST_MIPMAP_LINEAR || m_minFilter == Sampler::LINEAR_MIPMAP_LINEAR;
-		tcu::Surface			referenceFrame	(viewportWidth, viewportHeight);
-		tcu::Surface			errorMask		(viewportWidth, viewportHeight);
 		tcu::LookupPrecision	lookupPrec;
 		tcu::LodPrecision		lodPrec;
-		int						numFailedPixels	= 0;
 
 		lookupPrec.coordBits		= tcu::IVec3(20, 20, 20);
 		lookupPrec.uvwBits			= tcu::IVec3(16, 16, 16); // Doesn't really matter since pixels are unicolored.
@@ -1597,53 +1620,67 @@
 		lodPrec.derivateBits		= 10;
 		lodPrec.lodBits				= 8;
 
-		for (int gridY = 0; gridY < gridHeight; gridY++)
+		auto compareAndLogImages = [&](tcu::ImageViewMinLodMode imageViewLodMode = tcu::IMAGEVIEWMINLODMODE_PREFERRED)
 		{
-			for (int gridX = 0; gridX < gridWidth; gridX++)
+			tcu::Surface			referenceFrame	(viewportWidth, viewportHeight);
+			tcu::Surface			errorMask		(viewportWidth, viewportHeight);
+			int						numFailedPixels = 0;
+
+			for (int gridY = 0; gridY < gridHeight; gridY++)
 			{
-				const int	curX		= cellWidth*gridX;
-				const int	curY		= cellHeight*gridY;
-				const int	curW		= gridX+1 == gridWidth ? (viewportWidth-curX) : cellWidth;
-				const int	curH		= gridY+1 == gridHeight ? (viewportHeight-curY) : cellHeight;
-				const int	cellNdx		= gridY*gridWidth + gridX;
+				for (int gridX = 0; gridX < gridWidth; gridX++)
+				{
+					const int	curX		= cellWidth*gridX;
+					const int	curY		= cellHeight*gridY;
+					const int	curW		= gridX+1 == gridWidth ? (viewportWidth-curX) : cellWidth;
+					const int	curH		= gridY+1 == gridHeight ? (viewportHeight-curY) : cellHeight;
+					const int	cellNdx		= gridY*gridWidth + gridX;
 
-				getReferenceParams(refParams, cellNdx);
+					getReferenceParams(refParams, cellNdx);
 
-				// Compute texcoord.
-				if (refParams.samplerType == glu::TextureTestUtil::SAMPLERTYPE_FETCH_FLOAT)
-					getBasicTexCoord3DImageViewMinlodIntTexCoord(texCoord);
-				else
-					getBasicTexCoord3D(texCoord, cellNdx);
+					refParams.imageViewMinLodMode = imageViewLodMode;
 
-				// Render ideal result
-				sampleTexture(tcu::SurfaceAccess(referenceFrame, pixelFormat, curX, curY, curW, curH),
-							  refTexture, &texCoord[0], refParams);
+					// Compute texcoord.
+					if (refParams.samplerType == glu::TextureTestUtil::SAMPLERTYPE_FETCH_FLOAT)
+						getBasicTexCoord3DImageViewMinlodIntTexCoord(texCoord);
+					else
+						getBasicTexCoord3D(texCoord, cellNdx);
 
-				// Compare this cell
-				numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
-															tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
-															tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
-															m_texture->getTexture(), &texCoord[0], refParams,
-															lookupPrec, lodPrec, m_context.getTestContext().getWatchDog());
+					// Render ideal result
+					sampleTexture(tcu::SurfaceAccess(referenceFrame, pixelFormat, curX, curY, curW, curH),
+								  refTexture, &texCoord[0], refParams);
+
+					// Compare this cell
+					numFailedPixels += computeTextureLookupDiff(tcu::getSubregion(renderedFrame.getAccess(), curX, curY, curW, curH),
+																tcu::getSubregion(referenceFrame.getAccess(), curX, curY, curW, curH),
+																tcu::getSubregion(errorMask.getAccess(), curX, curY, curW, curH),
+																m_texture->getTexture(), &texCoord[0], refParams,
+																lookupPrec, lodPrec, m_context.getTestContext().getWatchDog());
+				}
 			}
-		}
+			if (numFailedPixels > 0)
+			{
+				m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
+													<< TestLog::Image("ErrorMask", "Error mask", errorMask);
+			}
 
-		if (numFailedPixels > 0)
-		{
-			m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
-		}
+			return numFailedPixels;
+		};
 
 		m_context.getTestContext().getLog() << TestLog::ImageSet("Result", "Verification result")
 											<< TestLog::Image("Rendered", "Rendered image", renderedFrame);
 
-		if (numFailedPixels > 0)
-		{
-			m_context.getTestContext().getLog() << TestLog::Image("Reference", "Ideal reference", referenceFrame)
-												<< TestLog::Image("ErrorMask", "Error mask", errorMask);
-		}
+		int numFailedPixels = compareAndLogImages();
 
+		if (numFailedPixels > 0 && refParams.imageViewMinLod > 0.0f)
+		{
+			numFailedPixels = compareAndLogImages(tcu::IMAGEVIEWMINLODMODE_ALTERNATIVE);
+		}
 		m_context.getTestContext().getLog() << TestLog::EndImageSet;
 
+		if (numFailedPixels > 0)
+			m_context.getTestContext().getLog() << TestLog::Message << "ERROR: Image verification failed, found " << numFailedPixels << " invalid pixels!" << TestLog::EndMessage;
+
 		{
 			const bool isOk = numFailedPixels == 0;
 			return isOk ? tcu::TestStatus::pass("pass") : tcu::TestStatus::fail("fail");
diff --git a/framework/common/tcuTexture.cpp b/framework/common/tcuTexture.cpp
index 35bf764..fbbf924 100644
--- a/framework/common/tcuTexture.cpp
+++ b/framework/common/tcuTexture.cpp
@@ -588,6 +588,11 @@
 	}
 }
 
+float getImageViewMinLod(ImageViewMinLod& l)
+{
+	return (l.mode == IMAGEVIEWMINLODMODE_PREFERRED) ? l.value : deFloatFloor(l.value);
+}
+
 } // anonymous
 
 bool isValid (TextureFormat format)
@@ -2535,7 +2540,7 @@
 	bool					magnified;
 	// minLodRelative is used to calculate the image level to sample from, when VK_EXT_image_view_min_lod extension is enabled.
 	// The value is relative to baseLevel as the Texture*View was created as the baseLevel being level[0].
-	const float				minLodRelative	= (minLodParams != DE_NULL) ? minLodParams->minLod - (float)minLodParams->baseLevel : 0.0f;
+	const float				minLodRelative	= (minLodParams != DE_NULL) ? getImageViewMinLod(minLodParams->minLod) - (float)minLodParams->baseLevel : 0.0f;
 
 	if (es2 && sampler.magFilter == Sampler::LINEAR &&
 		(sampler.minFilter == Sampler::NEAREST_MIPMAP_NEAREST || sampler.minFilter == Sampler::NEAREST_MIPMAP_LINEAR))
@@ -2634,7 +2639,7 @@
 {
 	// minLodRelative is used to calculate the image level to sample from, when VK_EXT_image_view_min_lod extension is enabled.
 	// The value is relative to baseLevel as the Texture*View was created as the baseLevel being level[0].
-	const float				minLodRelative	= (minLodParams != DE_NULL) ? minLodParams->minLod - (float)minLodParams->baseLevel : 0.0f;
+	const float				minLodRelative	= (minLodParams != DE_NULL) ? getImageViewMinLod(minLodParams->minLod) - (float)minLodParams->baseLevel : 0.0f;
 	bool					magnified	= lod <= sampler.lodThreshold;
 	Sampler::FilterMode		filterMode	= magnified ? sampler.magFilter : sampler.minFilter;
 
@@ -3078,7 +3083,7 @@
 {
 	// minLodRelative is used to calculate the image level to sample from, when VK_EXT_image_view_min_lod extension is enabled.
 	// The value is relative to baseLevel as the Texture*View was created as the baseLevel being level[0].
-	const float				minLodRelative	= (minLodParams != DE_NULL) ? minLodParams->minLod - (float)minLodParams->baseLevel : 0.0f;
+	const float				minLodRelative	= (minLodParams != DE_NULL) ? getImageViewMinLod(minLodParams->minLod) - (float)minLodParams->baseLevel : 0.0f;
 	bool					magnified	= lod <= sampler.lodThreshold;
 	Sampler::FilterMode		filterMode	= magnified ? sampler.magFilter : sampler.minFilter;
 
diff --git a/framework/common/tcuTexture.hpp b/framework/common/tcuTexture.hpp
index 7500dad..35bd0b1 100644
--- a/framework/common/tcuTexture.hpp
+++ b/framework/common/tcuTexture.hpp
@@ -477,11 +477,23 @@
 /*--------------------------------------------------------------------*//*!
  * \brief VK_EXT_image_view_min_lod
  *//*--------------------------------------------------------------------*/
+enum ImageViewMinLodMode
+{
+	IMAGEVIEWMINLODMODE_PREFERRED,		//!< use image view min lod as-is
+	IMAGEVIEWMINLODMODE_ALTERNATIVE,	//!< use floor of image view min lod, as in 'Image Level(s) Selection' in VK spec (v 1.3.206)
+};
+
+struct ImageViewMinLod
+{
+	float				value;
+	ImageViewMinLodMode	mode;
+};
+
 struct ImageViewMinLodParams
 {
-	int		baseLevel;
-	float	minLod;
-	bool	intTexCoord;
+	int				baseLevel;
+	ImageViewMinLod	minLod;
+	bool			intTexCoord;
 };
 
 Vec4	sampleLevelArray1D				(const ConstPixelBufferAccess* levels, int numLevels, const Sampler& sampler, float s, int level, float lod);
diff --git a/framework/opengl/gluTextureTestUtil.cpp b/framework/opengl/gluTextureTestUtil.cpp
index 1476e4dd..c581565 100644
--- a/framework/opengl/gluTextureTestUtil.cpp
+++ b/framework/opengl/gluTextureTestUtil.cpp
@@ -561,7 +561,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		params.baseLevel,								// int		baseLevel;
-		params.imageViewMinLod,							// float	minLod;
+		{
+			params.imageViewMinLod,							// float	minLod;
+			params.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
 		params.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
 	};
 
@@ -580,8 +583,11 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		params.baseLevel,								// int		baseLevel;
-		params.imageViewMinLod,							// float	minLod;
-		params.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
+		{
+			params.imageViewMinLod,							// float	minLod;
+			params.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
+		params.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool		intTexCoord;
 	};
 
 	const tcu::Texture2DView	view	= getSubView(src, params.baseLevel, params.maxLevel, params.imageViewMinLod != 0.0f ? &minLodParams : DE_NULL);
@@ -698,7 +704,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		params.baseLevel,								// int		baseLevel;
-		params.imageViewMinLod,							// float	minLod;
+		{
+			params.imageViewMinLod,							// float	minLod;
+			params.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
 		params.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
 	};
 
@@ -900,7 +909,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		params.baseLevel,								// int		baseLevel;
-		params.imageViewMinLod,							// float	minLod;
+		{
+			params.imageViewMinLod,							// float	minLod;
+			params.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
 		params.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
 	};
 
@@ -1396,7 +1408,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		sampleParams.baseLevel,								// int		baseLevel;
-		sampleParams.imageViewMinLod,						// float	minLod;
+		{
+			sampleParams.imageViewMinLod,							// float	minLod;
+			sampleParams.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
 		sampleParams.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
 	};
 
@@ -1611,7 +1626,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		sampleParams.baseLevel,								// int		baseLevel;
-		sampleParams.imageViewMinLod,						// float	minLod;
+		{
+			sampleParams.imageViewMinLod,					// float	minLod;
+			sampleParams.imageViewMinLodMode,				// ImageViewMinLodMode
+		},
 		sampleParams.samplerType == SAMPLERTYPE_FETCH_FLOAT	// bool	intTexCoord;
 	};
 
@@ -1805,7 +1823,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		sampleParams.baseLevel,									// int		baseLevel;
-		sampleParams.imageViewMinLod,							// float	minLod;
+		{
+			sampleParams.imageViewMinLod,						// float	minLod;
+			sampleParams.imageViewMinLodMode,					// ImageViewMinLodMode
+		},
 		sampleParams.samplerType == SAMPLERTYPE_FETCH_FLOAT		// bool	intTexCoord;
 	};
 
@@ -2284,7 +2305,10 @@
 	tcu::ImageViewMinLodParams	minLodParams =
 	{
 		sampleParams.baseLevel,									// int		baseLevel;
-		sampleParams.imageViewMinLod,							// float	minLod;
+		{
+			sampleParams.imageViewMinLod,							// float	minLod;
+			sampleParams.imageViewMinLodMode,						// ImageViewMinLodMode
+		},
 		sampleParams.samplerType == SAMPLERTYPE_FETCH_FLOAT		// bool	intTexCoord;
 	};
 
diff --git a/framework/opengl/gluTextureTestUtil.hpp b/framework/opengl/gluTextureTestUtil.hpp
index 4aae60a..492c078 100644
--- a/framework/opengl/gluTextureTestUtil.hpp
+++ b/framework/opengl/gluTextureTestUtil.hpp
@@ -119,45 +119,48 @@
 struct ReferenceParams : public RenderParams
 {
 	ReferenceParams (TextureType texType_)
-		: RenderParams		(texType_)
-		, sampler			()
-		, lodMode			(LODMODE_EXACT)
-		, minLod			(-1000.0f)
-		, maxLod			(1000.0f)
-		, baseLevel			(0)
-		, maxLevel			(1000)
-		, unnormal			(false)
-		, float16TexCoord	(false)
-		, imageViewMinLod (0.0f)
-		, lodTexelFetch  (0)
+		: RenderParams			(texType_)
+		, sampler				()
+		, lodMode				(LODMODE_EXACT)
+		, minLod				(-1000.0f)
+		, maxLod				(1000.0f)
+		, baseLevel				(0)
+		, maxLevel				(1000)
+		, unnormal				(false)
+		, float16TexCoord		(false)
+		, imageViewMinLod		(0.0f)
+		, imageViewMinLodMode	(tcu::IMAGEVIEWMINLODMODE_PREFERRED)
+		, lodTexelFetch			(0)
 	{
 	}
 
 	ReferenceParams (TextureType texType_, const tcu::Sampler& sampler_, LodMode lodMode_ = LODMODE_EXACT)
-		: RenderParams		(texType_)
-		, sampler			(sampler_)
-		, lodMode			(lodMode_)
-		, minLod			(-1000.0f)
-		, maxLod			(1000.0f)
-		, baseLevel			(0)
-		, maxLevel			(1000)
-		, unnormal			(false)
-		, float16TexCoord	(false)
-		, imageViewMinLod (0.0f)
-		, lodTexelFetch  (0)
+		: RenderParams			(texType_)
+		, sampler				(sampler_)
+		, lodMode				(lodMode_)
+		, minLod				(-1000.0f)
+		, maxLod				(1000.0f)
+		, baseLevel				(0)
+		, maxLevel				(1000)
+		, unnormal				(false)
+		, float16TexCoord		(false)
+		, imageViewMinLod		(0.0f)
+		, imageViewMinLodMode	(tcu::IMAGEVIEWMINLODMODE_PREFERRED)
+		, lodTexelFetch			(0)
 	{
 	}
 
-	tcu::Sampler		sampler;
-	LodMode				lodMode;
-	float				minLod;
-	float				maxLod;
-	int					baseLevel;
-	int					maxLevel;
-	bool				unnormal;
-	bool				float16TexCoord;
-	float				imageViewMinLod;
-	int					lodTexelFetch;
+	tcu::Sampler				sampler;
+	LodMode						lodMode;
+	float						minLod;
+	float						maxLod;
+	int							baseLevel;
+	int							maxLevel;
+	bool						unnormal;
+	bool						float16TexCoord;
+	float						imageViewMinLod;
+	tcu::ImageViewMinLodMode	imageViewMinLodMode;
+	int							lodTexelFetch;
 };