Replicate D3D's div by 0 behavior for RCP/RSQ (GLSL Edition)
authorCaleb Cornett <caleb.cornett@outlook.com>
Thu, 05 Dec 2019 12:11:01 -0500
changeset 1221 012dec2787aa
parent 1220 048797e6aae1
child 1222 c6e847dd9d4b
Replicate D3D's div by 0 behavior for RCP/RSQ (GLSL Edition)
profiles/mojoshader_profile.h
profiles/mojoshader_profile_glsl.c
--- a/profiles/mojoshader_profile.h	Fri Nov 29 15:41:54 2019 -0500
+++ b/profiles/mojoshader_profile.h	Thu Dec 05 12:11:01 2019 -0500
@@ -160,6 +160,7 @@
     int glsl_generated_lit_helper;
     int glsl_generated_texlod_setup;
     int glsl_generated_texm3x3spec_helper;
+    int glsl_need_max_float;
     int arb1_wrote_position;
     // !!! FIXME: move these into SUPPORT_PROFILE sections.
 
--- a/profiles/mojoshader_profile_glsl.c	Fri Nov 29 15:41:54 2019 -0500
+++ b/profiles/mojoshader_profile_glsl.c	Thu Dec 05 12:11:01 2019 -0500
@@ -641,6 +641,8 @@
     if (shader_is_vertex(ctx))
         output_line(ctx, "uniform float vpFlip;");
 #endif
+    if (ctx->glsl_need_max_float)
+        output_line(ctx, "const float FLT_MAX = 1e38;");
     pop_output(ctx);
 } // emit_GLSL_finalize
 
@@ -1199,7 +1201,8 @@
 {
     char src0[64]; make_GLSL_srcarg_string_masked(ctx, 0, src0, sizeof (src0));
     char code[128];
-    make_GLSL_destarg_assign(ctx, code, sizeof (code), "1.0 / %s", src0);
+    ctx->glsl_need_max_float = 1;
+    make_GLSL_destarg_assign(ctx, code, sizeof (code), "(%s == 0.0) ? FLT_MAX : 1.0 / %s", src0, src0);
     output_line(ctx, "%s", code);
 } // emit_GLSL_RCP
 
@@ -1207,7 +1210,8 @@
 {
     char src0[64]; make_GLSL_srcarg_string_masked(ctx, 0, src0, sizeof (src0));
     char code[128];
-    make_GLSL_destarg_assign(ctx, code, sizeof (code), "inversesqrt(%s)", src0);
+    ctx->glsl_need_max_float = 1;
+    make_GLSL_destarg_assign(ctx, code, sizeof (code), "(%s == 0.0) ? FLT_MAX : inversesqrt(abs(%s))", src0, src0);
     output_line(ctx, "%s", code);
 } // emit_GLSL_RSQ