/*
    Copyright 2010 Google Inc.

    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.
 */


#include "GrMatrix.h"
#include "GrRect.h"
#include <stddef.h>

#if 0
#if GR_SCALAR_IS_FLOAT
    const GrScalar GrMatrix::gRESCALE(GR_Scalar1);
#else
    GR_STATIC_ASSERT(GR_SCALAR_IS_FIXED);
    // fixed point isn't supported right now
    GR_STATIC_ASSERT(false);
const GrScalar GrMatrix::gRESCALE(1 << 30);
#endif

const GrMatrix::MapProc GrMatrix::gMapProcs[] = {
// Scales are not both zero
    &GrMatrix::mapIdentity,
    &GrMatrix::mapScale,
    &GrMatrix::mapTranslate,
    &GrMatrix::mapScaleAndTranslate,
    &GrMatrix::mapSkew,
    &GrMatrix::mapScaleAndSkew,
    &GrMatrix::mapSkewAndTranslate,
    &GrMatrix::mapNonPerspective,
    // no optimizations for perspective matrices
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapPerspective,

// Scales are zero (every other is invalid because kScale_TypeBit must be set if
// kZeroScale_TypeBit is set)
    &GrMatrix::mapInvalid,
    &GrMatrix::mapZero,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapSetToTranslate,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapSwappedScale,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapSwappedScaleAndTranslate,

    // no optimizations for perspective matrices
    &GrMatrix::mapInvalid,
    &GrMatrix::mapZero,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapPerspective,
    &GrMatrix::mapInvalid,
    &GrMatrix::mapPerspective,
};

void GrMatrix::setIdentity() {
    fM[0] = GR_Scalar1; fM[1] = 0;          fM[2] = 0;
    fM[3] = 0;          fM[4] = GR_Scalar1; fM[5] = 0;
    fM[6] = 0;          fM[7] = 0;          fM[8] = gRESCALE;
    fTypeMask = 0;
}

void GrMatrix::setTranslate(GrScalar dx, GrScalar dy) {
    fM[0] = GR_Scalar1; fM[1] = 0;          fM[2] = dx;
    fM[3] = 0;          fM[4] = GR_Scalar1; fM[5] = dy;
    fM[6] = 0;          fM[7] = 0;          fM[8] = gRESCALE;
    fTypeMask = (0 != dx || 0 != dy) ? kTranslate_TypeBit : 0;
}

void GrMatrix::setScale(GrScalar sx, GrScalar sy) {
    fM[0] = sx; fM[1] = 0;  fM[2] = 0;
    fM[3] = 0;  fM[4] = sy; fM[5] = 0;
    fM[6] = 0;  fM[7] = 0;  fM[8] = gRESCALE;
    fTypeMask = (GR_Scalar1 != sx || GR_Scalar1 != sy) ? kScale_TypeBit : 0;
}

void GrMatrix::setSkew(GrScalar skx, GrScalar sky) {
    fM[0] = GR_Scalar1; fM[1] = skx;        fM[2] = 0;
    fM[3] = sky;        fM[4] = GR_Scalar1; fM[5] = 0;
    fM[6] = 0;          fM[7] = 0;          fM[8] = gRESCALE;
    fTypeMask = (0 != skx || 0 != sky) ? kSkew_TypeBit : 0;
}

void GrMatrix::setConcat(const GrMatrix& a, const GrMatrix& b) {
    if (a.isIdentity()) {
        if (this != &b) {
            for (int i = 0; i < 9; ++i) {
                fM[i] = b.fM[i];
            }
            fTypeMask = b.fTypeMask;
        }
        return;
    }

    if (b.isIdentity()) {
        GrAssert(!a.isIdentity());
        if (this != &a) {
            for (int i = 0; i < 9; ++i) {
                    fM[i] = a.fM[i];
            }
            fTypeMask = a.fTypeMask;
        }
        return;
    }

    // a and/or b could be this
    GrMatrix tmp;

    // could do more optimizations based on type bits. Hopefully this call is
    // low frequency.
    // TODO: make this work for fixed point
    if (!((b.fTypeMask | a.fTypeMask) & kPerspective_TypeBit)) {
        tmp.fM[0] = a.fM[0] * b.fM[0] + a.fM[1] * b.fM[3];
        tmp.fM[1] = a.fM[0] * b.fM[1] + a.fM[1] * b.fM[4];
        tmp.fM[2] = a.fM[0] * b.fM[2] + a.fM[1] * b.fM[5] + a.fM[2] * gRESCALE;

        tmp.fM[3] = a.fM[3] * b.fM[0] + a.fM[4] * b.fM[3];
        tmp.fM[4] = a.fM[3] * b.fM[1] + a.fM[4] * b.fM[4];
        tmp.fM[5] = a.fM[3] * b.fM[2] + a.fM[4] * b.fM[5] + a.fM[5] * gRESCALE;

        tmp.fM[6] = 0;
        tmp.fM[7] = 0;
        tmp.fM[8] = gRESCALE * gRESCALE;
    } else {
        tmp.fM[0] = a.fM[0] * b.fM[0] + a.fM[1] * b.fM[3] + a.fM[2] * b.fM[6];
        tmp.fM[1] = a.fM[0] * b.fM[1] + a.fM[1] * b.fM[4] + a.fM[2] * b.fM[7];
        tmp.fM[2] = a.fM[0] * b.fM[2] + a.fM[1] * b.fM[5] + a.fM[2] * b.fM[8];

        tmp.fM[3] = a.fM[3] * b.fM[0] + a.fM[4] * b.fM[3] + a.fM[5] * b.fM[6];
        tmp.fM[4] = a.fM[3] * b.fM[1] + a.fM[4] * b.fM[4] + a.fM[5] * b.fM[7];
        tmp.fM[5] = a.fM[3] * b.fM[2] + a.fM[4] * b.fM[5] + a.fM[5] * b.fM[8];

        tmp.fM[6] = a.fM[6] * b.fM[0] + a.fM[7] * b.fM[3] + a.fM[8] * b.fM[6];
        tmp.fM[7] = a.fM[6] * b.fM[1] + a.fM[7] * b.fM[4] + a.fM[8] * b.fM[7];
        tmp.fM[8] = a.fM[6] * b.fM[2] + a.fM[7] * b.fM[5] + a.fM[8] * b.fM[8];
    }
    *this = tmp;
    this->computeTypeMask();
}

void GrMatrix::preConcat(const GrMatrix& m) {
    setConcat(*this, m);
}

void GrMatrix::postConcat(const GrMatrix& m) {
    setConcat(m, *this);
}

double GrMatrix::determinant() const {
    if (fTypeMask & kPerspective_TypeBit) {
        return  fM[0]*((double)fM[4]*fM[8] - (double)fM[5]*fM[7]) +
                fM[1]*((double)fM[5]*fM[6] - (double)fM[3]*fM[8]) +
                fM[2]*((double)fM[3]*fM[7] - (double)fM[4]*fM[6]);
    } else {
        return (double)fM[0]*fM[4]*gRESCALE -
               (double)fM[1]*fM[3]*gRESCALE;
    }
}

bool GrMatrix::invert(GrMatrix* inverted) const {

    if (isIdentity()) {
        if (inverted != this) {
            inverted->setIdentity();
        }
        return true;
    }
    static const double MIN_DETERMINANT_SQUARED = 1.e-16;

    // could do more optimizations based on type bits. Hopefully this call is
    // low frequency.

    double det = determinant();

    // check if we can't be inverted
    if (det*det <= MIN_DETERMINANT_SQUARED) {
        return false;
    } else if (NULL == inverted) {
        return true;
    }

    double t[9];

    if (fTypeMask & kPerspective_TypeBit) {
        t[0] = ((double)fM[4]*fM[8] - (double)fM[5]*fM[7]);
        t[1] = ((double)fM[2]*fM[7] - (double)fM[1]*fM[8]);
        t[2] = ((double)fM[1]*fM[5] - (double)fM[2]*fM[4]);
        t[3] = ((double)fM[5]*fM[6] - (double)fM[3]*fM[8]);
        t[4] = ((double)fM[0]*fM[8] - (double)fM[2]*fM[6]);
        t[5] = ((double)fM[2]*fM[3] - (double)fM[0]*fM[5]);
        t[6] = ((double)fM[3]*fM[7] - (double)fM[4]*fM[6]);
        t[7] = ((double)fM[1]*fM[6] - (double)fM[0]*fM[7]);
        t[8] = ((double)fM[0]*fM[4] - (double)fM[1]*fM[3]);
        det = 1.0 / det;
        for (int i = 0; i < 9; ++i) {
            inverted->fM[i] = (GrScalar)(t[i] * det);
        }
    } else {
        t[0] =  (double)fM[4]*gRESCALE;
        t[1] = -(double)fM[1]*gRESCALE;
        t[2] =  (double)fM[1]*fM[5] - (double)fM[2]*fM[4];
        t[3] = -(double)fM[3]*gRESCALE;
        t[4] =  (double)fM[0]*gRESCALE;
        t[5] =  (double)fM[2]*fM[3] - (double)fM[0]*fM[5];
        //t[6] = 0.0;
        //t[7] = 0.0;
        t[8] = (double)fM[0]*fM[4] - (double)fM[1]*fM[3];
        det = 1.0 / det;
        for (int i = 0; i < 6; ++i) {
            inverted->fM[i] = (GrScalar)(t[i] * det);
        }
        inverted->fM[6] = 0;
        inverted->fM[7] = 0;
        inverted->fM[8] = (GrScalar)(t[8] * det);
    }
    inverted->computeTypeMask();
    return true;
}

void GrMatrix::mapRect(GrRect* dst, const GrRect& src) const {
    GrPoint srcPts[4], dstPts[4];
    srcPts[0].set(src.fLeft, src.fTop);
    srcPts[1].set(src.fRight, src.fTop);
    srcPts[2].set(src.fRight, src.fBottom);
    srcPts[3].set(src.fLeft, src.fBottom);
    this->mapPoints(dstPts, srcPts, 4);
    dst->setBounds(dstPts, 4);
}

bool GrMatrix::hasPerspective() const {
    GrAssert(!!(kPerspective_TypeBit & fTypeMask) ==
             (fM[kPersp0] != 0 || fM[kPersp1] != 0 || fM[kPersp2] != gRESCALE));
    return 0 != (kPerspective_TypeBit & fTypeMask);
}

bool GrMatrix::isIdentity() const {
    GrAssert((0 == fTypeMask) ==
             (GR_Scalar1 == fM[kScaleX] && 0          == fM[kSkewX]  && 0          == fM[kTransX] &&
              0          == fM[kSkewY]  && GR_Scalar1 == fM[kScaleY] && 0          == fM[kTransY] &&
              0          == fM[kPersp0] && 0          == fM[kPersp1] && gRESCALE == fM[kPersp2]));
    return (0 == fTypeMask);
}


bool GrMatrix::preservesAxisAlignment() const {

    // check if matrix is trans and scale only
    static const int gAllowedMask1 = kScale_TypeBit | kTranslate_TypeBit;

    if (!(~gAllowedMask1 & fTypeMask)) {
        return true;
    }

    // check matrix is trans and skew only (0 scale)
    static const int gAllowedMask2 = kScale_TypeBit | kSkew_TypeBit |
                                     kTranslate_TypeBit | kZeroScale_TypeBit;

    if (!(~gAllowedMask2 & fTypeMask) && (kZeroScale_TypeBit & fTypeMask)) {
        return true;
    }

    return false;
}

GrScalar GrMatrix::getMaxStretch() const {

    if (fTypeMask & kPerspective_TypeBit) {
        return -GR_Scalar1;
    }

    GrScalar stretch;

    if (isIdentity()) {
        stretch = GR_Scalar1;
    } else if (!(fTypeMask & kSkew_TypeBit)) {
        stretch = GrMax(GrScalarAbs(fM[kScaleX]), GrScalarAbs(fM[kScaleY]));
    } else if (fTypeMask & kZeroScale_TypeBit) {
        stretch = GrMax(GrScalarAbs(fM[kSkewX]), GrScalarAbs(fM[kSkewY]));
    } else {
        // ignore the translation part of the matrix, just look at 2x2 portion.
        // compute singular values, take largest abs value.
        // [a b; b c] = A^T*A
        GrScalar a = GrMul(fM[kScaleX], fM[kScaleX]) + GrMul(fM[kSkewY],  fM[kSkewY]);
        GrScalar b = GrMul(fM[kScaleX], fM[kSkewX]) +  GrMul(fM[kScaleY], fM[kSkewY]);
        GrScalar c = GrMul(fM[kSkewX],  fM[kSkewX]) +  GrMul(fM[kScaleY], fM[kScaleY]);
        // eigenvalues of A^T*A are the squared singular values of A.
        // characteristic equation is det((A^T*A) - l*I) = 0
        // l^2 - (a + c)l + (ac-b^2)
        // solve using quadratic equation (divisor is non-zero since l^2 has 1 coeff
        // and roots are guaraunteed to be pos and real).
        GrScalar largerRoot;
        GrScalar bSqd = GrMul(b,b);
        // TODO: fixed point tolerance value.
        if (bSqd < 1e-10) { // will be true if upper left 2x2 is orthogonal, which is common, so save some math
            largerRoot = GrMax(a, c);
        } else {
            GrScalar aminusc = a - c;
            GrScalar apluscdiv2 = (a + c) / 2;
            GrScalar x = sqrtf(GrMul(aminusc,aminusc) + GrMul(4,(bSqd))) / 2;
            largerRoot = apluscdiv2 + x;
        }

        stretch = sqrtf(largerRoot);
    }
#if GR_DEBUG && 0
    // test a bunch of vectors. None should be scaled by more than stretch
    // (modulo some error) and we should find a vector that is scaled by almost
    // stretch.
    GrPoint pt;
    GrScalar max = 0;
    for (int i = 0; i < 1000; ++i) {
        GrScalar x = (float)rand() / RAND_MAX;
        GrScalar y = sqrtf(1 - (x*x));
        pt.fX = fM[kScaleX]*x + fM[kSkewX]*y;
        pt.fY = fM[kSkewY]*x + fM[kScaleY]*y;
        GrScalar d = pt.distanceToOrigin();
        GrAssert(d <= (1.0001 * stretch));
        max = GrMax(max, pt.distanceToOrigin());
    }
    GrAssert((stretch - max) < .05*stretch);
#endif
    return stretch;
}

bool GrMatrix::operator == (const GrMatrix& m) const {
    if (fTypeMask != m.fTypeMask) {
        return false;
    }
    if (!fTypeMask) {
        return true;
    }
    for (int i = 0; i < 9; ++i) {
        if (m.fM[i] != fM[i]) {
            return false;
        }
    }
    return true;
}

bool GrMatrix::operator != (const GrMatrix& m) const {
    return !(*this == m);
}

////////////////////////////////////////////////////////////////////////////////
// Matrix transformation procs
//////

void GrMatrix::mapIdentity(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i] = src[i];
        }
    }
}

void GrMatrix::mapScale(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    for (uint32_t i = 0; i < count; ++i) {
        dst[i].fX = GrMul(src[i].fX, fM[kScaleX]);
        dst[i].fY = GrMul(src[i].fY, fM[kScaleY]);
    }
}


void GrMatrix::mapTranslate(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    for (uint32_t i = 0; i < count; ++i) {
        dst[i].fX = src[i].fX + fM[kTransX];
        dst[i].fY = src[i].fY + fM[kTransY];
    }
}

void GrMatrix::mapScaleAndTranslate(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    for (uint32_t i = 0; i < count; ++i) {
        dst[i].fX = GrMul(src[i].fX, fM[kScaleX]) + fM[kTransX];
        dst[i].fY = GrMul(src[i].fY, fM[kScaleY]) + fM[kTransY];
    }
}

void GrMatrix::mapSkew(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = src[i].fX + GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = src[i].fY + GrMul(src[i].fX, fM[kSkewY]);
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = src[i].fX + GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = src[i].fY + GrMul(src[i].fX, fM[kSkewY]);
            dst[i].fX = newX;
        }
    }
}

void GrMatrix::mapScaleAndSkew(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = GrMul(src[i].fX, fM[kScaleX]) + GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = GrMul(src[i].fY, fM[kScaleY]) + GrMul(src[i].fX, fM[kSkewY]);
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = GrMul(src[i].fX, fM[kScaleX]) + GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = GrMul(src[i].fY, fM[kScaleY]) + GrMul(src[i].fX, fM[kSkewY]);
            dst[i].fX = newX;
        }
    }
}

void GrMatrix::mapSkewAndTranslate(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = src[i].fX + GrMul(src[i].fY, fM[kSkewX]) + fM[kTransX];
            dst[i].fY = src[i].fY + GrMul(src[i].fX, fM[kSkewY]) + fM[kTransY];
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = src[i].fX + GrMul(src[i].fY, fM[kSkewX]) + fM[kTransX];
            dst[i].fY = src[i].fY + GrMul(src[i].fX, fM[kSkewY]) + fM[kTransY];
            dst[i].fX = newX;
        }
    }
}

void GrMatrix::mapNonPerspective(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = GrMul(fM[kScaleX], src[i].fX) + GrMul(fM[kSkewX], src[i].fY) + fM[kTransX];
            dst[i].fY = GrMul(fM[kSkewY], src[i].fX) + GrMul(fM[kScaleY], src[i].fY) + fM[kTransY];
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = GrMul(fM[kScaleX], src[i].fX) + GrMul(fM[kSkewX], src[i].fY) + fM[kTransX];
            dst[i].fY = GrMul(fM[kSkewY], src[i].fX) + GrMul(fM[kScaleY], src[i].fY) + fM[kTransY];
            dst[i].fX = newX;
        }
    }
}

void GrMatrix::mapPerspective(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    for (uint32_t i = 0; i < count; ++i) {
        GrScalar x, y, w;
        x = GrMul(fM[kScaleX], src[i].fX) + GrMul(fM[kSkewX], src[i].fY) + fM[kTransX];
        y = GrMul(fM[kSkewY], src[i].fX) + GrMul(fM[kScaleY], src[i].fY) + fM[kTransY];
        w = GrMul(fM[kPersp0], src[i].fX) + GrMul(fM[kPersp1], src[i].fY) + fM[kPersp2];
        // TODO need fixed point invert
        if (w) {
            w = 1 / w;
        }
        dst[i].fX = GrMul(x, w);
        dst[i].fY = GrMul(y, w);
    }
}

void GrMatrix::mapInvalid(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    GrAssert(0);
}

void GrMatrix::mapZero(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    memset(dst, 0, sizeof(GrPoint)*count);
}

void GrMatrix::mapSetToTranslate(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    for (uint32_t i = 0; i < count; ++i) {
        dst[i].fX = fM[kTransX];
        dst[i].fY = fM[kTransY];
    }
}

void GrMatrix::mapSwappedScale(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = GrMul(src[i].fX, fM[kSkewY]);
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = GrMul(src[i].fY, fM[kSkewX]);
            dst[i].fY = GrMul(src[i].fX, fM[kSkewY]);
            dst[i].fX = newX;
        }
    }
}

void GrMatrix::mapSwappedScaleAndTranslate(GrPoint* dst, const GrPoint* src, uint32_t count) const {
    if (src != dst) {
        for (uint32_t i = 0; i < count; ++i) {
            dst[i].fX = GrMul(src[i].fY, fM[kSkewX]) + fM[kTransX];
            dst[i].fY = GrMul(src[i].fX, fM[kSkewY]) + fM[kTransY];
        }
    } else {
        for (uint32_t i = 0; i < count; ++i) {
            GrScalar newX = GrMul(src[i].fY, fM[kSkewX]) + fM[kTransX];
            dst[i].fY = GrMul(src[i].fX, fM[kSkewY]) + fM[kTransY];
            dst[i].fX = newX;
        }
    }
}

///////////////////////////////////////////////////////////////////////////////
// Unit test
//////

#include "GrRandom.h"

#if GR_DEBUG
enum MatrixType {
    kRotate_MatrixType,
    kScaleX_MatrixType,
    kScaleY_MatrixType,
    kSkewX_MatrixType,
    kSkewY_MatrixType,
    kTranslateX_MatrixType,
    kTranslateY_MatrixType,
    kSwapScaleXY_MatrixType,
    kPersp_MatrixType,

    kMatrixTypeCount
};

static void create_matrix(GrMatrix* matrix, GrRandom& rand) {
    MatrixType type = (MatrixType)(rand.nextU() % kMatrixTypeCount);
    switch (type) {
        case kRotate_MatrixType: {
            float angle = rand.nextF() * 2 *3.14159265358979323846f;
            GrScalar cosa = GrFloatToScalar(cosf(angle));
            GrScalar sina = GrFloatToScalar(sinf(angle));
            matrix->setAll(cosa,      -sina,           0,
                           sina,       cosa,           0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kScaleX_MatrixType: {
            GrScalar scale = GrFloatToScalar(rand.nextF(-2, 2));
            matrix->setAll(scale,      0,              0,
                           0,          GR_Scalar1,     0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kScaleY_MatrixType: {
            GrScalar scale = GrFloatToScalar(rand.nextF(-2, 2));
            matrix->setAll(GR_Scalar1, 0,              0,
                           0,          scale,          0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kSkewX_MatrixType: {
            GrScalar skew = GrFloatToScalar(rand.nextF(-2, 2));
            matrix->setAll(GR_Scalar1, skew,           0,
                           0,          GR_Scalar1,     0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kSkewY_MatrixType: {
            GrScalar skew = GrFloatToScalar(rand.nextF(-2, 2));
            matrix->setAll(GR_Scalar1, 0,              0,
                           skew,       GR_Scalar1,     0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kTranslateX_MatrixType: {
            GrScalar trans = GrFloatToScalar(rand.nextF(-10, 10));
            matrix->setAll(GR_Scalar1, 0,              trans,
                           0,          GR_Scalar1,     0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kTranslateY_MatrixType: {
            GrScalar trans = GrFloatToScalar(rand.nextF(-10, 10));
            matrix->setAll(GR_Scalar1, 0,              0,
                           0,          GR_Scalar1,     trans,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kSwapScaleXY_MatrixType: {
            GrScalar xy = GrFloatToScalar(rand.nextF(-2, 2));
            GrScalar yx = GrFloatToScalar(rand.nextF(-2, 2));
            matrix->setAll(0,          xy,             0,
                           yx,         0,              0,
                           0,          0,              GrMatrix::I()[8]);
        } break;
        case kPersp_MatrixType: {
            GrScalar p0 = GrFloatToScalar(rand.nextF(-2, 2));
            GrScalar p1 = GrFloatToScalar(rand.nextF(-2, 2));
            GrScalar p2 = GrFloatToScalar(rand.nextF(-0.5f, 0.75f));
            matrix->setAll(GR_Scalar1, 0,              0,
                           0,          GR_Scalar1,     0,
                           p0,         p1,             GrMul(p2,GrMatrix::I()[8]));
        } break;
        default:
            GrAssert(0);
            break;
    }
}
#endif

void GrMatrix::UnitTest() {
    GrRandom rand;

    // Create a bunch of matrices and test point mapping, max stretch calc,
    // inversion and multiply-by-inverse.
#if GR_DEBUG
    for (int i = 0; i < 10000; ++i) {
        GrMatrix a, b;
        a.setIdentity();
        int num = rand.nextU() % 6;
        // force testing of I and swapXY
        if (0 == i) {
            num = 0;
            GrAssert(a.isIdentity());
        } else if (1 == i) {
            num = 0;
            a.setAll(0, GR_Scalar1, 0,
                     GR_Scalar1, 0, 0,
                     0, 0, I()[8]);
        }
        for (int j = 0; j < num; ++j) {
            create_matrix(&b, rand);
            a.preConcat(b);
        }

        GrScalar maxStretch = a.getMaxStretch();
        if (maxStretch > 0) {
            maxStretch = GrMul(GR_Scalar1 + GR_Scalar1 / 100, maxStretch);
        }
        GrPoint origin = a.mapPoint(GrPoint::Make(0,0));

        for (int j = 0; j < 9; ++j) {
            int mask, origMask = a.fTypeMask;
            GrScalar old = a[j];

            a.set(j, GR_Scalar1);
            mask = a.fTypeMask;
            a.computeTypeMask();
            GrAssert(mask == a.fTypeMask);

            a.set(j, 0);
            mask = a.fTypeMask;
            a.computeTypeMask();
            GrAssert(mask == a.fTypeMask);

            a.set(j, 10 * GR_Scalar1);
            mask = a.fTypeMask;
            a.computeTypeMask();
            GrAssert(mask == a.fTypeMask);

            a.set(j, old);
            GrAssert(a.fTypeMask == origMask);
        }

        for (int j = 0; j < 100; ++j) {
            GrPoint pt;
            pt.fX = GrFloatToScalar(rand.nextF(-10, 10));
            pt.fY = GrFloatToScalar(rand.nextF(-10, 10));

            GrPoint t0, t1, t2;
            t0 = a.mapPoint(pt);             // map to a new point
            t1 = pt;
            a.mapPoints(&t1, &t1, 1);        // in place
            a.mapPerspective(&t2, &pt, 1);   // full mult
            GrAssert(t0 == t1 && t1 == t2);
            if (maxStretch >= 0.f) {
                GrVec vec = origin - t0;
//                vec.setBetween(t0, origin);
                GrScalar stretch = vec.length() / pt.distanceToOrigin();
                GrAssert(stretch <= maxStretch);
            }
        }
        double det = a.determinant();
        if (fabs(det) > 1e-3 && a.invert(&b)) {
            GrMatrix c;
            c.setConcat(a,b);
            for (int i = 0; i < 9; ++i) {
                GrScalar diff = GrScalarAbs(c[i] - I()[i]);
                GrAssert(diff < (5*GR_Scalar1 / 100));
            }
        }
    }
#endif
}

///////////////////////////////////////////////////////////////////////////////
#endif

int Gr_clz(uint32_t n) {
    if (0 == n) {
        return 32;
    }

    int count = 0;
    if (0 == (n & 0xFFFF0000)) {
        count += 16;
        n <<= 16;
    }
    if (0 == (n & 0xFF000000)) {
        count += 8;
        n <<= 8;
    }
    if (0 == (n & 0xF0000000)) {
        count += 4;
        n <<= 4;
    }
    if (0 == (n & 0xC0000000)) {
        count += 2;
        n <<= 2;
    }
    if (0 == (n & 0x80000000)) {
        count += 1;
    }
    return count;
}
