begin to wrap all float divides

Bug: skia:7607 skia:6134
Change-Id: Id126e92816bef1df1372bd531238cda9f3b36fab
Reviewed-on: https://skia-review.googlesource.com/106261
Reviewed-by: Mike Klein <mtklein@chromium.org>
Commit-Queue: Mike Reed <reed@google.com>
diff --git a/include/core/SkScalar.h b/include/core/SkScalar.h
index 936a006..9c015e5 100644
--- a/include/core/SkScalar.h
+++ b/include/core/SkScalar.h
@@ -134,10 +134,11 @@
 
 static inline SkScalar SkScalarSquare(SkScalar x) { return x * x; }
 
-#define SkScalarInvert(x)       (SK_Scalar1 / (x))
-#define SkScalarFastInvert(x)   (SK_Scalar1 / (x))
-#define SkScalarAve(a, b)       (((a) + (b)) * SK_ScalarHalf)
-#define SkScalarHalf(a)         ((a) * SK_ScalarHalf)
+#define SkScalarDiv(numer, denom)   sk_ieee_float_divide(numer, denom)
+#define SkScalarInvert(x)           sk_ieee_float_divide(SK_Scalar1, (x))
+#define SkScalarFastInvert(x)       sk_ieee_float_divide(SK_Scalar1, (x))
+#define SkScalarAve(a, b)           (((a) + (b)) * SK_ScalarHalf)
+#define SkScalarHalf(a)             ((a) * SK_ScalarHalf)
 
 #define SkDegreesToRadians(degrees) ((degrees) * (SK_ScalarPI / 180))
 #define SkRadiansToDegrees(radians) ((radians) * (180 / SK_ScalarPI))
diff --git a/include/private/SkFloatingPoint.h b/include/private/SkFloatingPoint.h
index bbb1179..a2e6ee5 100644
--- a/include/private/SkFloatingPoint.h
+++ b/include/private/SkFloatingPoint.h
@@ -190,4 +190,14 @@
 #define SK_FLT_DECIMAL_DIG 9
 #endif
 
+// IEEE defines how float divide behaves for non-finite values and zero-denoms, but C does not
+// so we have a helper that suppresses the possible undefined-behavior warnings.
+
+#ifdef __clang__
+__attribute__((no_sanitize("float-divide-by-zero")))
+#endif
+static inline float sk_ieee_float_divide(float numer, float denom) {
+    return numer / denom;
+}
+
 #endif
diff --git a/src/core/SkMatrix.cpp b/src/core/SkMatrix.cpp
index 9a70fbb..778d77c 100644
--- a/src/core/SkMatrix.cpp
+++ b/src/core/SkMatrix.cpp
@@ -6,6 +6,7 @@
  */
 
 #include "SkFloatBits.h"
+#include "SkMathPriv.h"
 #include "SkMatrixPriv.h"
 #include "SkNx.h"
 #include "SkPaint.h"
@@ -1363,32 +1364,32 @@
 
     /* check if abs(x2) > abs(y2) */
     if ( x2 > 0 ? y2 > 0 ? x2 > y2 : x2 > -y2 : y2 > 0 ? -x2 > y2 : x2 < y2) {
-        float denom = (x1 * y2 / x2) - y1;
+        float denom = sk_ieee_float_divide(x1 * y2, x2) - y1;
         if (checkForZero(denom)) {
             return false;
         }
         a1 = (((x0 - x1) * y2 / x2) - y0 + y1) / denom;
     } else {
-        float denom = x1 - (y1 * x2 / y2);
+        float denom = x1 - sk_ieee_float_divide(y1 * x2, y2);
         if (checkForZero(denom)) {
             return false;
         }
-        a1 = (x0 - x1 - ((y0 - y1) * x2 / y2)) / denom;
+        a1 = (x0 - x1 - sk_ieee_float_divide((y0 - y1) * x2, y2)) / denom;
     }
 
     /* check if abs(x1) > abs(y1) */
     if ( x1 > 0 ? y1 > 0 ? x1 > y1 : x1 > -y1 : y1 > 0 ? -x1 > y1 : x1 < y1) {
-        float denom = y2 - (x2 * y1 / x1);
+        float denom = y2 - sk_ieee_float_divide(x2 * y1, x1);
         if (checkForZero(denom)) {
             return false;
         }
-        a2 = (y0 - y2 - ((x0 - x2) * y1 / x1)) / denom;
+        a2 = (y0 - y2 - sk_ieee_float_divide((x0 - x2) * y1, x1)) / denom;
     } else {
-        float denom = (y2 * x1 / y1) - x2;
+        float denom = sk_ieee_float_divide(y2 * x1, y1) - x2;
         if (checkForZero(denom)) {
             return false;
         }
-        a2 = (((y0 - y2) * x1 / y1) - x0 + x2) / denom;
+        a2 = (sk_ieee_float_divide((y0 - y2) * x1, y1) - x0 + x2) / denom;
     }
 
     float invScale = SkScalarInvert(scale.fX);
diff --git a/src/effects/SkEmbossMaskFilter.cpp b/src/effects/SkEmbossMaskFilter.cpp
index 9fa26c5..9f4a54a8b 100644
--- a/src/effects/SkEmbossMaskFilter.cpp
+++ b/src/effects/SkEmbossMaskFilter.cpp
@@ -14,8 +14,27 @@
 #include "SkWriteBuffer.h"
 #include "SkString.h"
 
+static void normalize3(SkScalar dst[3], const SkScalar src[3]) {
+    SkScalar mag = SkScalarSquare(src[0]) + SkScalarSquare(src[1]) + SkScalarSquare(src[2]);
+    SkScalar scale = SkScalarInvert(SkScalarSqrt(mag));
+
+    for (int i = 0; i < 3; i++) {
+        dst[i] = src[i] * scale;
+    }
+}
+
 sk_sp<SkMaskFilter> SkEmbossMaskFilter::Make(SkScalar blurSigma, const Light& light) {
-    return sk_sp<SkMaskFilter>(new SkEmbossMaskFilter(blurSigma, light));
+    if (!SkScalarIsFinite(blurSigma) || blurSigma <= 0) {
+        return nullptr;
+    }
+
+    Light newLight = light;
+    normalize3(newLight.fDirection, light.fDirection);
+    if (SkScalarsAreFinite(newLight.fDirection, 3)) {
+        return nullptr;
+    }
+
+    return sk_sp<SkMaskFilter>(new SkEmbossMaskFilter(blurSigma, newLight));
 }
 
 #ifdef SK_SUPPORT_LEGACY_EMBOSSMASKFILTER
@@ -40,18 +59,11 @@
 
 ///////////////////////////////////////////////////////////////////////////////
 
-static void normalize(SkScalar v[3]) {
-    SkScalar mag = SkScalarSquare(v[0]) + SkScalarSquare(v[1]) + SkScalarSquare(v[2]);
-    mag = SkScalarSqrt(mag);
-
-    for (int i = 0; i < 3; i++) {
-        v[i] /= mag;
-    }
-}
-
 SkEmbossMaskFilter::SkEmbossMaskFilter(SkScalar blurSigma, const Light& light)
-    : fLight(light), fBlurSigma(blurSigma) {
-    normalize(fLight.fDirection);
+    : fLight(light), fBlurSigma(blurSigma)
+{
+    SkASSERT(fBlurSigma > 0);
+    SkASSERT(SkScalarsAreFinite(fLight.fDirection, 3));
 }
 
 SkMask::Format SkEmbossMaskFilter::getFormat() const {