Merge branch 'gl-colormapped-epolyflag' into 'next'

Fix uninitialized reads in PreparePolygon

See merge request STJr/SRB2!1392
This commit is contained in:
LJ Sonic 2021-04-25 14:19:24 -04:00
commit 02ee480abe
4 changed files with 119 additions and 63 deletions

View file

@ -229,14 +229,15 @@ enum EPolyFlags
PF_NoDepthTest = 0x00000200, // Disables the depth test mode
PF_Invisible = 0x00000400, // Disables write to color buffer
PF_Decal = 0x00000800, // Enables polygon offset
PF_Modulated = 0x00001000, // Modulation (multiply output with constant ARGB)
PF_Modulated = 0x00001000, // Modulation (multiply output with constant RGBA)
// When set, pass the color constant into the FSurfaceInfo -> PolyColor
PF_NoTexture = 0x00002000, // Disables texturing
PF_Corona = 0x00004000, // Tells the renderer we are drawing a corona
PF_Ripple = 0x00008000, // Water effect shader
PF_ColorMapped = 0x00008000, // Surface has "tint" and "fade" colors, which are sent as uniforms to a shader.
PF_RemoveYWrap = 0x00010000, // Forces clamp texture on Y
PF_ForceWrapX = 0x00020000, // Forces repeat texture on X
PF_ForceWrapY = 0x00040000 // Forces repeat texture on Y
PF_ForceWrapY = 0x00040000, // Forces repeat texture on Y
PF_Ripple = 0x00100000 // Water ripple effect. The current backend doesn't use it for anything.
};
@ -265,7 +266,6 @@ struct FTextureInfo
};
typedef struct FTextureInfo FTextureInfo;
// jimita 14032019
struct FLightInfo
{
FUINT light_level;
@ -281,7 +281,7 @@ struct FSurfaceInfo
RGBA_t PolyColor;
RGBA_t TintColor;
RGBA_t FadeColor;
FLightInfo LightInfo; // jimita 14032019
FLightInfo LightInfo;
};
typedef struct FSurfaceInfo FSurfaceInfo;

View file

@ -68,7 +68,6 @@ EXPORT void HWRAPI(DrawScreenFinalTexture) (int width, int height);
#define SCREENVERTS 10
EXPORT void HWRAPI(PostImgRedraw) (float points[SCREENVERTS][SCREENVERTS][2]);
// jimita
EXPORT boolean HWRAPI(CompileShaders) (void);
EXPORT void HWRAPI(CleanShaders) (void);
EXPORT void HWRAPI(SetShader) (int type);

View file

@ -173,6 +173,11 @@ boolean gl_shadersavailable = true;
// Lighting
// ==========================================================================
static boolean HWR_UseShader(void)
{
return (cv_glshaders.value && gl_shadersavailable);
}
void HWR_Lighting(FSurfaceInfo *Surface, INT32 light_level, extracolormap_t *colormap)
{
RGBA_t poly_color, tint_color, fade_color;
@ -182,7 +187,7 @@ void HWR_Lighting(FSurfaceInfo *Surface, INT32 light_level, extracolormap_t *col
fade_color.rgba = (colormap != NULL) ? (UINT32)colormap->fadergba : GL_DEFAULTFOG;
// Crappy backup coloring if you can't do shaders
if (!cv_glshaders.value || !gl_shadersavailable)
if (!HWR_UseShader())
{
// be careful, this may get negative for high lightlevel values.
float tint_alpha, fade_alpha;
@ -371,7 +376,7 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool
static FOutVector *planeVerts = NULL;
static UINT16 numAllocedPlaneVerts = 0;
int shader;
INT32 shader = SHADER_DEFAULT;
// no convex poly were generated for this subsector
if (!xsub->planepoly)
@ -568,12 +573,17 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool
else
PolyFlags |= PF_Masked|PF_Modulated;
if (HWR_UseShader())
{
if (PolyFlags & PF_Fog)
shader = SHADER_FOG; // fog shader
shader = SHADER_FOG;
else if (PolyFlags & PF_Ripple)
shader = SHADER_WATER; // water shader
shader = SHADER_WATER;
else
shader = SHADER_FLOOR; // floor shader
shader = SHADER_FLOOR;
PolyFlags |= PF_ColorMapped;
}
HWR_ProcessPolygon(&Surf, planeVerts, nrPlaneVerts, PolyFlags, shader, false);
@ -788,8 +798,17 @@ static void HWR_AddTransparentWall(FOutVector *wallVerts, FSurfaceInfo *pSurf, I
//
static void HWR_ProjectWall(FOutVector *wallVerts, FSurfaceInfo *pSurf, FBITFIELD blendmode, INT32 lightlevel, extracolormap_t *wallcolormap)
{
INT32 shader = SHADER_DEFAULT;
HWR_Lighting(pSurf, lightlevel, wallcolormap);
HWR_ProcessPolygon(pSurf, wallVerts, 4, blendmode|PF_Modulated|PF_Occlude, SHADER_WALL, false); // wall shader
if (HWR_UseShader())
{
shader = SHADER_WALL;
blendmode |= PF_ColorMapped;
}
HWR_ProcessPolygon(pSurf, wallVerts, 4, blendmode|PF_Modulated|PF_Occlude, shader, false);
}
// ==========================================================================
@ -2666,30 +2685,30 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling,
FBITFIELD blendmode, UINT8 lightlevel, levelflat_t *levelflat, sector_t *FOFsector,
UINT8 alpha, extracolormap_t *planecolormap)
{
float height; //constant y for all points on the convex flat polygon
FSurfaceInfo Surf;
FOutVector *v3d;
INT32 shader = SHADER_DEFAULT;
size_t nrPlaneVerts = polysector->numVertices;
INT32 i;
float height = FIXED_TO_FLOAT(fixedheight); // constant y for all points on the convex flat polygon
float flatxref, flatyref;
float fflatwidth = 64.0f, fflatheight = 64.0f;
INT32 flatflag = 63;
boolean texflat = false;
float scrollx = 0.0f, scrolly = 0.0f;
angle_t angle = 0;
FSurfaceInfo Surf;
fixed_t tempxs, tempyt;
size_t nrPlaneVerts;
static FOutVector *planeVerts = NULL;
static UINT16 numAllocedPlaneVerts = 0;
nrPlaneVerts = polysector->numVertices;
height = FIXED_TO_FLOAT(fixedheight);
if (nrPlaneVerts < 3) //not even a triangle ?
if (nrPlaneVerts < 3) // Not even a triangle?
return;
if (nrPlaneVerts > (size_t)UINT16_MAX) // FIXME: exceeds plVerts size
else if (nrPlaneVerts > (size_t)UINT16_MAX) // FIXME: exceeds plVerts size
{
CONS_Debug(DBG_RENDER, "polygon size of %s exceeds max value of %d vertices\n", sizeu1(nrPlaneVerts), UINT16_MAX);
return;
@ -2841,7 +2860,6 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling,
v3d->z = FIXED_TO_FLOAT(polysector->vertices[i]->y);
}
HWR_Lighting(&Surf, lightlevel, planecolormap);
if (blendmode & PF_Translucent)
@ -2852,7 +2870,13 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling,
else
blendmode |= PF_Masked|PF_Modulated;
HWR_ProcessPolygon(&Surf, planeVerts, nrPlaneVerts, blendmode, SHADER_FLOOR, false); // floor shader
if (HWR_UseShader())
{
shader = SHADER_FLOOR;
blendmode |= PF_ColorMapped;
}
HWR_ProcessPolygon(&Surf, planeVerts, nrPlaneVerts, blendmode, shader, false);
}
static void HWR_AddPolyObjectPlanes(void)
@ -3573,6 +3597,8 @@ static void HWR_DrawDropShadow(mobj_t *thing, fixed_t scale)
FSurfaceInfo sSurf;
float fscale; float fx; float fy; float offset;
extracolormap_t *colormap = NULL;
FBITFIELD blendmode = PF_Translucent|PF_Modulated;
INT32 shader = SHADER_DEFAULT;
UINT8 i;
SINT8 flip = P_MobjFlip(thing);
@ -3665,7 +3691,13 @@ static void HWR_DrawDropShadow(mobj_t *thing, fixed_t scale)
HWR_Lighting(&sSurf, 0, colormap);
sSurf.PolyColor.s.alpha = alpha;
HWR_ProcessPolygon(&sSurf, shadowVerts, 4, PF_Translucent|PF_Modulated, SHADER_SPRITE, false); // sprite shader
if (HWR_UseShader())
{
shader = SHADER_SPRITE;
blendmode |= PF_ColorMapped;
}
HWR_ProcessPolygon(&sSurf, shadowVerts, 4, blendmode, shader, false);
}
// This is expecting a pointer to an array containing 4 wallVerts for a sprite
@ -3713,6 +3745,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr)
boolean lightset = true;
FBITFIELD blend = 0;
FBITFIELD occlusion;
INT32 shader = SHADER_DEFAULT;
boolean use_linkdraw_hack = false;
UINT8 alpha;
@ -3833,6 +3866,12 @@ static void HWR_SplitSprite(gl_vissprite_t *spr)
if (!occlusion) use_linkdraw_hack = true;
}
if (HWR_UseShader())
{
shader = SHADER_SPRITE;
blend |= PF_ColorMapped;
}
alpha = Surf.PolyColor.s.alpha;
// Start with the lightlevel and colormap from the top of the sprite
@ -3941,7 +3980,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr)
Surf.PolyColor.s.alpha = alpha;
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, SHADER_SPRITE, false); // sprite shader
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, shader, false);
if (use_linkdraw_hack)
HWR_LinkDrawHackAdd(wallVerts, spr);
@ -3970,7 +4009,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr)
Surf.PolyColor.s.alpha = alpha;
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, SHADER_SPRITE, false); // sprite shader
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, shader, false);
if (use_linkdraw_hack)
HWR_LinkDrawHackAdd(wallVerts, spr);
@ -4220,6 +4259,7 @@ static void HWR_DrawSprite(gl_vissprite_t *spr)
}
{
INT32 shader = SHADER_DEFAULT;
FBITFIELD blend = 0;
FBITFIELD occlusion;
boolean use_linkdraw_hack = false;
@ -4270,7 +4310,13 @@ static void HWR_DrawSprite(gl_vissprite_t *spr)
if (!occlusion) use_linkdraw_hack = true;
}
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, SHADER_SPRITE, false); // sprite shader
if (HWR_UseShader())
{
shader = SHADER_SPRITE;
blend |= PF_ColorMapped;
}
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, shader, false);
if (use_linkdraw_hack)
HWR_LinkDrawHackAdd(wallVerts, spr);
@ -4281,6 +4327,7 @@ static void HWR_DrawSprite(gl_vissprite_t *spr)
// Sprite drawer for precipitation
static inline void HWR_DrawPrecipitationSprite(gl_vissprite_t *spr)
{
INT32 shader = SHADER_DEFAULT;
FBITFIELD blend = 0;
FOutVector wallVerts[4];
patch_t *gpatch;
@ -4369,7 +4416,13 @@ static inline void HWR_DrawPrecipitationSprite(gl_vissprite_t *spr)
blend = HWR_GetBlendModeFlag(spr->mobj->blendmode)|PF_Occlude;
}
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, SHADER_SPRITE, false); // sprite shader
if (HWR_UseShader())
{
shader = SHADER_SPRITE;
blend |= PF_ColorMapped;
}
HWR_ProcessPolygon(&Surf, wallVerts, 4, blend|PF_Modulated, shader, false);
}
#endif
@ -6465,24 +6518,29 @@ void HWR_RenderWall(FOutVector *wallVerts, FSurfaceInfo *pSurf, FBITFIELD blend,
FBITFIELD blendmode = blend;
UINT8 alpha = pSurf->PolyColor.s.alpha; // retain the alpha
int shader;
INT32 shader = SHADER_DEFAULT;
// Lighting is done here instead so that fog isn't drawn incorrectly on transparent walls after sorting
HWR_Lighting(pSurf, lightlevel, wallcolormap);
pSurf->PolyColor.s.alpha = alpha; // put the alpha back after lighting
shader = SHADER_WALL; // wall shader
if (blend & PF_Environment)
blendmode |= PF_Occlude; // PF_Occlude must be used for solid objects
if (fogwall)
if (HWR_UseShader())
{
blendmode |= PF_Fog;
shader = SHADER_FOG; // fog shader
if (fogwall)
shader = SHADER_FOG;
else
shader = SHADER_WALL;
blendmode |= PF_ColorMapped;
}
if (fogwall)
blendmode |= PF_Fog;
blendmode |= PF_Modulated; // No PF_Occlude means overlapping (incorrect) transparency
HWR_ProcessPolygon(pSurf, wallVerts, 4, blendmode, shader, false);
}
@ -6658,7 +6716,6 @@ void HWR_DrawScreenFinalTexture(int width, int height)
HWD.pfnDrawScreenFinalTexture(width, height);
}
// jimita 18032019
static inline UINT16 HWR_FindShaderDefs(UINT16 wadnum)
{
UINT16 i;

View file

@ -910,7 +910,6 @@ void SetupGLFunc4(void)
pgluBuild2DMipmaps = GetGLFunc("gluBuild2DMipmaps");
}
// jimita
EXPORT boolean HWRAPI(CompileShaders) (void)
{
#ifdef GL_SHADERS
@ -2176,33 +2175,35 @@ static void PreparePolygon(FSurfaceInfo *pSurf, FOutVector *pOutVerts, FBITFIELD
SetBlend(PolyFlags); //TODO: inline (#pragma..)
// PolyColor
if (pSurf)
{
// If Modulated, mix the surface colour to the texture
// If modulated, mix the surface colour to the texture
if (CurrentPolyFlags & PF_Modulated)
pglColor4ubv((GLubyte*)&pSurf->PolyColor.s);
// If the surface is either modulated or colormapped, or both
if (CurrentPolyFlags & (PF_Modulated | PF_ColorMapped))
{
// Poly color
poly.red = byte2float[pSurf->PolyColor.s.red];
poly.green = byte2float[pSurf->PolyColor.s.green];
poly.blue = byte2float[pSurf->PolyColor.s.blue];
poly.alpha = byte2float[pSurf->PolyColor.s.alpha];
pglColor4ubv((GLubyte*)&pSurf->PolyColor.s);
}
// Tint color
// Only if the surface is colormapped
if (CurrentPolyFlags & PF_ColorMapped)
{
tint.red = byte2float[pSurf->TintColor.s.red];
tint.green = byte2float[pSurf->TintColor.s.green];
tint.blue = byte2float[pSurf->TintColor.s.blue];
tint.alpha = byte2float[pSurf->TintColor.s.alpha];
// Fade color
fade.red = byte2float[pSurf->FadeColor.s.red];
fade.green = byte2float[pSurf->FadeColor.s.green];
fade.blue = byte2float[pSurf->FadeColor.s.blue];
fade.alpha = byte2float[pSurf->FadeColor.s.alpha];
}
}
// this test is added for new coronas' code (without depth buffer)
// I think I should do a separate function for drawing coronas, so it will be a little faster
@ -3015,7 +3016,6 @@ EXPORT void HWRAPI(SetTransform) (FTransform *stransform)
pglMatrixMode(GL_PROJECTION);
pglLoadIdentity();
// jimita 14042019
// Simulate Software's y-shearing
// https://zdoom.org/wiki/Y-shearing
if (shearing)