#include "CrashHandler.h"
// #include "OverwriteLine.h"
#include "Resources.h"
#include "SkBitmap.h"
#include "SkCanvas.h"
#include "SkColor.h"
#include "SkColorPriv.h"
#include "SkCommandLineFlags.h"
#include "SkDevice.h"
#include "SkForceLinking.h"
#include "SkGraphics.h"
#include "SkImageDecoder.h"
#include "SkImageEncoder.h"
#include "SkOSFile.h"
#include "SkPathOpsDebug.h"
#include "SkPicture.h"
#include "SkRTConf.h"
#include "SkTSort.h"
#include "SkStream.h"
#include "SkString.h"
#include "SkTArray.h"
#include "SkTDArray.h"
#include "SkTemplates.h"
#include "SkThreadPool.h"
#include "SkTime.h"

__SK_FORCE_IMAGE_DECODER_LINKING;

/* add local exceptions here */
/* TODO : add command flag interface */
const struct SkipOverTest {
    int directory;
    const char* filename;
    bool blamePathOps;
} skipOver[] = {
    { 2, "http___www_groupon_sg_.skp", false},  // SkAAClip::Builder::addRun SkASSERT(fBounds.contains(x, y));
    { 6, "http___www_googleventures_com_.skp", true},  // addTCoincident SkASSERT(test->fT < 1);
    { 7, "http___www_foxsports_nl_.skp", true},  // (no repro on mac) addT SkASSERT(this != other || fVerb == SkPath::kCubic_Verb)
    {13, "http___www_modernqigong_com_.skp", false},  // SkAAClip::Builder::addRun SkASSERT(fBounds.contains(x, y));
    {14, "http___www_devbridge_com_.skp", true},  // checkSmallCoincidence SkASSERT(!next->fSmall || checkMultiple);
    {16, "http___www_1023world_net_.skp", true},  // bitmap decode assert (corrupt skp?)
    {19, "http___www_alamdi_com_.skp", true},  // cubic/quad intersection
    {26, "http___www_liveencounters_net_.skp", true},  // (no repro on mac) checkSmall addT:549 (line, expects cubic)
    {28, "http___www_encros_fr_.skp", false},  // SkAAClip::Builder::addRun SkASSERT(fBounds.contains(x, y));
    {37, "http___www_familysurvivalprotocol_wordpress_com_.skp", true},  // bumpSpan SkASSERT(span->fOppValue >= 0);
    {39, "http___sufeinet_com_.skp", false}, // bitmap decode assert (corrupt skp?)
    {41, "http___www_rano360_com_.skp", true}, // checkSmallCoincidence SkASSERT(!next->fSmall || checkMultiple);
    {44, "http___www_firstunitedbank_com_.skp", true},  // addTCancel SkASSERT(oIndex > 0);
    {46, "http___www_shinydemos_com_.skp", true},  // addSimpleAngle SkASSERT(index == count() - 2);
    {48, "http___www_familysurvivalprotocol_com_.skp", true},  // bumpSpan SkASSERT "span->fOppValue >= 0"
    {57, "http___www_lptemp_com_.skp", true}, // addTCoincident oPeek = &other->fTs[++oPeekIndex];
    {71, "http___www_1milyonkahraman_org_.skp", true},  // addTCoincident SkASSERT(test->fT < 1);
    {88, "http___www_apuntesdelechuza_wordpress_com_.skp", true},  // bumpSpan SkASSERT "span->fOppValue >= 0"
    {89, "http___www_mobilizedconsulting_com_.skp", true}, // addTCancel SkASSERT(oIndex > 0);
    {93, "http___www_simple_living_in_suffolk_co_uk_.skp", true},  // bumpSpan SkASSERT "span->fOppValue >= 0"
};

size_t skipOverCount = sizeof(skipOver) / sizeof(skipOver[0]);


/* customize file in/out here */
/* TODO : add command flag interface */
#define CHROME_VERSION "1e5dfa4-4a995df"
#define SUMMARY_RUN 1

#ifdef SK_BUILD_FOR_WIN
    #define DRIVE_SPEC "D:"
    #define PATH_SLASH "\\"
#else
    #define DRIVE_SPEC ""
    #define PATH_SLASH "/"
#endif

#define IN_DIR_PRE  DRIVE_SPEC PATH_SLASH "skps"   PATH_SLASH "slave"
#define OUT_DIR_PRE DRIVE_SPEC PATH_SLASH "skpOut" PATH_SLASH "slave"
#define OUT_DIR_SUM DRIVE_SPEC PATH_SLASH "skpOut" PATH_SLASH "summary"
#define DIR_POST               PATH_SLASH "All"    PATH_SLASH CHROME_VERSION

static const char outOpDir[]     = "opClip";
static const char outOldDir[]    = "oldClip";
static const char outStatusDir[] = "statusTest";

static SkString get_in_path(int dirNo, const char* filename) {
    SkString path;
    SkASSERT(dirNo);
    path.appendf("%s%d%s", IN_DIR_PRE, dirNo, DIR_POST);
    if (!sk_exists(path.c_str())) {
        SkDebugf("could not read %s\n", path.c_str());
        return SkString();
    }
    if (filename) {
        path.appendf("%s%s", PATH_SLASH, filename);
        if (!sk_exists(path.c_str())) {        
            SkDebugf("could not read %s\n", path.c_str());
            return SkString();
        }
    }
    return path;
}
    
static void make_recursive_dir(const SkString& path) {
    if (sk_exists(path.c_str())) {
        return;
    }
    const char* pathStr = path.c_str();
    int last = (int) path.size();
    do {
        while (last > 0 && pathStr[--last] != PATH_SLASH[0])
            ;
        SkASSERT(last > 0);
        SkString shorter(pathStr, last);
        if (sk_mkdir(shorter.c_str())) {
            break;
        }
    } while (true);
    do {
        while (last < (int) path.size() && pathStr[++last] != PATH_SLASH[0])
            ;
        SkString shorter(pathStr, last);
        SkAssertResult(sk_mkdir(shorter.c_str()));
    } while (last < (int) path.size());
}

static SkString get_out_path(int dirNo, const char* dirName) {
    SkString path;
    SkASSERT(dirNo);
    SkASSERT(dirName);
    path.appendf("%s%d%s%s%s", OUT_DIR_PRE, dirNo, DIR_POST, PATH_SLASH, dirName);
    make_recursive_dir(path);
    return path;
}
  
static SkString get_sum_path(const char* dirName) {
    SkString path;
    SkASSERT(dirName);
    path.appendf("%s%d%s%s", OUT_DIR_SUM, SUMMARY_RUN, PATH_SLASH, dirName);
    SkDebugf("%s\n", path.c_str());
    make_recursive_dir(path);
    return path;
}

static SkString make_png_name(const char* filename) {
    SkString pngName = SkString(filename);
    pngName.remove(pngName.size() - 3, 3);
    pngName.append("png");
    return pngName;
}

////////////////////////////////////////////////////////

enum TestStep {
    kCompareBits,
    kEncodeFiles,
};

enum {
    kMaxLength = 256,
    kMaxFiles = 128,
    kSmallLimit = 1000,
};

struct TestResult {
    void init(int dirNo) {
        fDirNo = dirNo;
        sk_bzero(fFilename, sizeof(fFilename));
        fTestStep = kCompareBits;
        fScale = 1;
    }
    
    void init(int dirNo, const SkString& filename) {
        fDirNo = dirNo;
        strcpy(fFilename, filename.c_str());
        fTestStep = kCompareBits;
        fScale = 1;       
    }

    SkString status() {
        SkString outStr;
        outStr.printf("%s %d %d\n", fFilename, fPixelError, fTime);
        return outStr;
    }

    SkString progress() {
        SkString outStr;
        outStr.printf("dir=%d %s ", fDirNo, fFilename);
        if (fPixelError) {
            outStr.appendf(" err=%d", fPixelError);
        }
        if (fTime) {
            outStr.appendf(" time=%d", fTime);
        }
        if (fScale != 1) {
            outStr.appendf(" scale=%d", fScale);
        }
        outStr.appendf("\n");
        return outStr;

    }

    void test(int dirNo, const SkString& filename) {
        init(dirNo);
        strcpy(fFilename, filename.c_str());
        testOne();
    }

    void testOne();
    
    char fFilename[kMaxLength];
    TestStep fTestStep;
    int fDirNo;
    int fPixelError;
    int fTime;
    int fScale;
};

class SortByPixel : public TestResult {
public:
    bool operator<(const SortByPixel& rh) const {
        return fPixelError < rh.fPixelError;
    }
};

class SortByTime : public TestResult {
public:
    bool operator<(const SortByTime& rh) const {
        return fTime < rh.fTime;
    }
};

class SortByName : public TestResult {
public:
    bool operator<(const SortByName& rh) const {
        return strcmp(fFilename, rh.fFilename) < 0;
    }
};

struct TestState {
    void init(int dirNo) {
        fResult.init(dirNo);
    }

    SkTDArray<SortByPixel> fPixelWorst;
    SkTDArray<SortByTime> fSlowest;
    TestResult fResult;
};

struct TestRunner {
    TestRunner(int threadCount)
        : fNumThreads(threadCount) {
    }

    ~TestRunner();
    void render();
    int fNumThreads;
    SkTDArray<class TestRunnable*> fRunnables;
};

class TestRunnable : public SkRunnable {
public:
    virtual void run() SK_OVERRIDE {
        SkGraphics::SetTLSFontCacheLimit(1 * 1024 * 1024);
        (*fTestFun)(&fState);
    }

    TestState fState;
    void (*fTestFun)(TestState*);
};


class TestRunnableDir : public TestRunnable {
public:
    TestRunnableDir(void (*testFun)(TestState*), int dirNo, TestRunner* runner) {
        fState.init(dirNo);
        fTestFun = testFun;
    }

};

class TestRunnableFile : public TestRunnable {
public:
    TestRunnableFile(void (*testFun)(TestState*), int dirNo, const char* name, TestRunner* runner) {
        fState.init(dirNo);
        strcpy(fState.fResult.fFilename, name);
        fTestFun = testFun;
    }
};

class TestRunnableEncode : public TestRunnableFile {
public:
    TestRunnableEncode(void (*testFun)(TestState*), int dirNo, const char* name, TestRunner* runner)
        : TestRunnableFile(testFun, dirNo, name, runner) {
        fState.fResult.fTestStep = kEncodeFiles;
    }
};

TestRunner::~TestRunner() {
    for (int index = 0; index < fRunnables.count(); index++) {
        SkDELETE(fRunnables[index]);
    }
}

void TestRunner::render() {
    SkThreadPool pool(fNumThreads);
    for (int index = 0; index < fRunnables.count(); ++ index) {
        pool.add(fRunnables[index]);
    }
}

////////////////////////////////////////////////


static int similarBits(const SkBitmap& gr, const SkBitmap& sk) {
    const int kRowCount = 3;
    const int kThreshold = 3;
    int width = SkTMin(gr.width(), sk.width());
    if (width < kRowCount) {
        return true;
    }
    int height = SkTMin(gr.height(), sk.height());
    if (height < kRowCount) {
        return true;
    }
    int errorTotal = 0;
    SkTArray<int, true> errorRows;
    errorRows.push_back_n(width * kRowCount);
    SkAutoLockPixels autoGr(gr);
    SkAutoLockPixels autoSk(sk);
    for (int y = 0; y < height; ++y) {
        SkPMColor* grRow = gr.getAddr32(0, y);
        SkPMColor* skRow = sk.getAddr32(0, y);
        int* base = &errorRows[0];
        int* cOut = &errorRows[y % kRowCount];
        for (int x = 0; x < width; ++x) {
            SkPMColor grColor = grRow[x];
            SkPMColor skColor = skRow[x];
            int dr = SkGetPackedR32(grColor) - SkGetPackedR32(skColor);
            int dg = SkGetPackedG32(grColor) - SkGetPackedG32(skColor);
            int db = SkGetPackedB32(grColor) - SkGetPackedB32(skColor);
            int error = cOut[x] = SkTMax(SkAbs32(dr), SkTMax(SkAbs32(dg), SkAbs32(db)));
            if (error < kThreshold || x < 2) {
                continue;
            }
            if (base[x - 2] < kThreshold
                    || base[width + x - 2] < kThreshold
                    || base[width * 2 + x - 2] < kThreshold
                    || base[x - 1] < kThreshold
                    || base[width + x - 1] < kThreshold
                    || base[width * 2 + x - 1] < kThreshold
                    || base[x] < kThreshold
                    || base[width + x] < kThreshold
                    || base[width * 2 + x] < kThreshold) {
                continue;
            }
            errorTotal += error;
        }
    }
    return errorTotal;
}

static bool addError(TestState* data, const TestResult& testResult) {
    if (testResult.fPixelError <= 0 && testResult.fTime <= 0) {
        return false;
    }
    int worstCount = data->fPixelWorst.count();
    int pixelError = testResult.fPixelError;
    if (pixelError > 0) {
        for (int index = 0; index < worstCount; ++index) {
            if (pixelError > data->fPixelWorst[index].fPixelError) {
                data->fPixelWorst[index] = *(SortByPixel*) &testResult;
                return true;
            }
        }
    }
    int slowCount = data->fSlowest.count();
    int time = testResult.fTime;
    if (time > 0) {
        for (int index = 0; index < slowCount; ++index) {
            if (time > data->fSlowest[index].fTime) {
                data->fSlowest[index] = *(SortByTime*) &testResult;
                return true;
            }
        }
    }
    if (pixelError > 0 && worstCount < kMaxFiles) {
        *data->fPixelWorst.append() = *(SortByPixel*) &testResult;
        return true;
    }
    if (time > 0 && slowCount < kMaxFiles) {
        *data->fSlowest.append() = *(SortByTime*) &testResult;
        return true;
    }
    return false;
}

static SkMSec timePict(SkPicture* pic, SkCanvas* canvas) {
    canvas->save();
    int pWidth = pic->width();
    int pHeight = pic->height();
    const int maxDimension = 1000;
    const int slices = 3;
    int xInterval = SkTMax(pWidth - maxDimension, 0) / (slices - 1);
    int yInterval = SkTMax(pHeight - maxDimension, 0) / (slices - 1);
    SkRect rect = {0, 0, SkIntToScalar(SkTMin(maxDimension, pWidth)),
            SkIntToScalar(SkTMin(maxDimension, pHeight))};
    canvas->clipRect(rect);
    SkMSec start = SkTime::GetMSecs();
    for (int x = 0; x < slices; ++x) {
        for (int y = 0; y < slices; ++y) {
            pic->draw(canvas);
            canvas->translate(0, SkIntToScalar(yInterval));
        }
        canvas->translate(SkIntToScalar(xInterval), SkIntToScalar(-yInterval * slices));
    }
    SkMSec end = SkTime::GetMSecs();
    canvas->restore();
    return end - start;
}

static void drawPict(SkPicture* pic, SkCanvas* canvas, int scale) {
    canvas->clear(SK_ColorWHITE);
    if (scale != 1) {
        canvas->save();
        canvas->scale(1.0f / scale, 1.0f / scale);
    }
    pic->draw(canvas);
    if (scale != 1) {
        canvas->restore();
    }
}

static void writePict(const SkBitmap& bitmap, const char* outDir, const char* pngName) {
    SkString outFile = get_sum_path(outDir);
    outFile.appendf("%s%s", PATH_SLASH, pngName);
    if (!SkImageEncoder::EncodeFile(outFile.c_str(), bitmap, SkImageEncoder::kPNG_Type, 100)) {
        SkDebugf("unable to encode gr %s (width=%d height=%d)\n", pngName,
                    bitmap.width(), bitmap.height());
    }
}

void TestResult::testOne() {
    SkPicture* pic = NULL;
    {
    #if DEBUG_SHOW_TEST_NAME
        if (fTestStep == kCompareBits) {
            SkString testName(fFilename);
            const char http[] = "http";
            if (testName.startsWith(http)) {
                testName.remove(0, sizeof(http) - 1);
            }
            while (testName.startsWith("_")) {
                testName.remove(0, 1);
            }
            const char dotSkp[] = ".skp";
            if (testName.endsWith(dotSkp)) {
                size_t len = testName.size();
                testName.remove(len - (sizeof(dotSkp) - 1), sizeof(dotSkp) - 1);
            }
            testName.prepend("skp");
            testName.append("1");
            strncpy(DEBUG_FILENAME_STRING, testName.c_str(), DEBUG_FILENAME_STRING_LENGTH);
        } else if (fTestStep == kEncodeFiles) {
            strncpy(DEBUG_FILENAME_STRING, "", DEBUG_FILENAME_STRING_LENGTH);
        }
    #endif
        SkString path = get_in_path(fDirNo, fFilename);
        SkFILEStream stream(path.c_str());
        if (!stream.isValid()) {
            SkDebugf("invalid stream %s\n", path.c_str());
            goto finish;
        }
        pic = SkPicture::CreateFromStream(&stream, &SkImageDecoder::DecodeMemory);
        if (!pic) {
            SkDebugf("unable to decode %s\n", fFilename);
            goto finish;
        }
        int width = pic->width();
        int height = pic->height();
        SkBitmap oldBitmap, opBitmap;
        fScale = 1;
        while (width / fScale > 32767 || height / fScale > 32767) {
            ++fScale;
        }
        do {
            int dimX = (width + fScale - 1) / fScale;
            int dimY = (height + fScale - 1) / fScale;
            if (oldBitmap.allocN32Pixels(dimX, dimY) &&
                opBitmap.allocN32Pixels(dimX, dimY)) {
                break;
            }
            SkDebugf("-%d-", fScale);
        } while (++fScale < 256);
        if (fScale >= 256) {
            SkDebugf("unable to allocate bitmap for %s (w=%d h=%d)\n", fFilename,
                    width, height);
            goto finish;
        }
        oldBitmap.eraseColor(SK_ColorWHITE);
        SkCanvas oldCanvas(oldBitmap);
        oldCanvas.setAllowSimplifyClip(false);
        opBitmap.eraseColor(SK_ColorWHITE);
        SkCanvas opCanvas(opBitmap);
        opCanvas.setAllowSimplifyClip(true);
        drawPict(pic, &oldCanvas, fScale);
        drawPict(pic, &opCanvas, fScale);
        if (fTestStep == kCompareBits) {
            fPixelError = similarBits(oldBitmap, opBitmap);
            int oldTime = timePict(pic, &oldCanvas);
            int opTime = timePict(pic, &opCanvas);
            fTime = SkTMax(0, oldTime - opTime);
        } else if (fTestStep == kEncodeFiles) {
            SkString pngStr = make_png_name(fFilename);
            const char* pngName = pngStr.c_str();
            writePict(oldBitmap, outOldDir, pngName);
            writePict(opBitmap, outOpDir, pngName);
        }
    }
finish:
    if (pic) {
        pic->unref();
    }
}

DEFINE_string2(match, m, "PathOpsSkpClipThreaded",
        "[~][^]substring[$] [...] of test name to run.\n"
        "Multiple matches may be separated by spaces.\n"
        "~ causes a matching test to always be skipped\n"
        "^ requires the start of the test to match\n"
        "$ requires the end of the test to match\n"
        "^ and $ requires an exact match\n"
        "If a test does not match any list entry,\n"
        "it is skipped unless some list entry starts with ~");
DEFINE_string2(dir, d, NULL, "range of directories (e.g., 1-100)");
DEFINE_string2(skp, s, NULL, "skp to test");
DEFINE_bool2(single, z, false, "run tests on a single thread internally.");
DEFINE_int32(testIndex, 0, "override local test index (PathOpsSkpClipOneOff only).");
DEFINE_int32(threads, SkThreadPool::kThreadPerCore,
        "Run threadsafe tests on a threadpool with this many threads.");
DEFINE_bool2(verbose, v, false, "enable verbose output.");

static bool verbose() {
    return FLAGS_verbose;
}

static int getThreadCount() {
    return FLAGS_single ? 1 : FLAGS_threads;
}

class Dirs {
public:
    Dirs() {
        reset();
        sk_bzero(fRun, sizeof(fRun));
        fSet = false;
    }

    int first() const {
        int index = 0;
        while (++index < kMaxDir) {
            if (fRun[index]) {
                return index;
            }
        }
        SkASSERT(0);
        return -1;
    }

    int last() const {
        int index = kMaxDir;
        while (--index > 0 && !fRun[index])
            ;
        return index;
    }

    int next() {
        while (++fIndex < kMaxDir) {
            if (fRun[fIndex]) {
                return fIndex;
            }
        }
        return -1;
    }

    void reset() {
        fIndex = -1;
    }

    void set(int start, int end) {
        while (start < end) {
            fRun[start++] = 1;
        }
        fSet = true;
    }

    void setDefault() {
        if (!fSet) {
            set(1, 100);
        }
    }

private:
    enum {
         kMaxDir = 101
    };
    char fRun[kMaxDir];
    int fIndex;
    bool fSet;
} gDirs;

class Filenames {
public:
    Filenames()
        : fIndex(-1) {
    }

    const char* next() {
        while (fNames && ++fIndex < fNames->count()) {
            return (*fNames)[fIndex];
        }
        return NULL;
    }
    
    void set(const SkCommandLineFlags::StringArray& names) {
        fNames = &names;
    }

private:
    int fIndex;
    const SkCommandLineFlags::StringArray* fNames;
} gNames;

static bool buildTestDir(int dirNo, int firstDirNo, 
        SkTDArray<TestResult>* tests, SkTDArray<SortByName*>* sorted) {
    SkString dirName = get_out_path(dirNo, outStatusDir);
    if (!dirName.size()) {
        return false;
    }
    SkOSFile::Iter iter(dirName.c_str(), "skp");
    SkString filename;
    while (iter.next(&filename)) {
        TestResult test;
        test.init(dirNo);
        SkString spaceFile(filename);
        char* spaces = spaceFile.writable_str();
        int spaceSize = (int) spaceFile.size();
        for (int index = 0; index < spaceSize; ++index) {
            if (spaces[index] == '.') {
                spaces[index] = ' ';
            }
        }
        int success = sscanf(spaces, "%s %d %d skp", test.fFilename,
                &test.fPixelError, &test.fTime);
        if (success < 3) {
            SkDebugf("failed to scan %s matched=%d\n", filename.c_str(), success);
            return false;
        }
        *tests[dirNo - firstDirNo].append() = test;
    }
    if (!sorted) {
        return true;
    }
    SkTDArray<TestResult>& testSet = tests[dirNo - firstDirNo];
    int count = testSet.count();
    for (int index = 0; index < count; ++index) {
        *sorted[dirNo - firstDirNo].append() = (SortByName*) &testSet[index];
    }
    if (sorted[dirNo - firstDirNo].count()) {
        SkTQSort<SortByName>(sorted[dirNo - firstDirNo].begin(),
                sorted[dirNo - firstDirNo].end() - 1);
        if (verbose()) {
            SkDebugf("+");
        }
    }
    return true;
}

static void testSkpClip(TestState* data) {
    data->fResult.testOne();
    SkString statName(data->fResult.fFilename);
    SkASSERT(statName.endsWith(".skp"));
    statName.remove(statName.size() - 4, 4);
    statName.appendf(".%d.%d.skp", data->fResult.fPixelError, data->fResult.fTime);
    SkString statusFile = get_out_path(data->fResult.fDirNo, outStatusDir);
    if (!statusFile.size()) {
        SkDebugf("failed to create %s", statusFile.c_str());
        return;
    }
    statusFile.appendf("%s%s", PATH_SLASH, statName.c_str());
    SkFILE* file = sk_fopen(statusFile.c_str(), kWrite_SkFILE_Flag);
    if (!file) {
            SkDebugf("failed to create %s", statusFile.c_str());
            return;
    }
    sk_fclose(file);
    if (verbose()) {
        if (data->fResult.fPixelError || data->fResult.fTime) {
            SkDebugf("%s", data->fResult.progress().c_str());
        } else {
            SkDebugf(".");
        }
    }
}

bool Less(const SortByName& a, const SortByName& b);
bool Less(const SortByName& a, const SortByName& b) {
    return a < b;
}

static bool doOneDir(TestState* state, bool threaded) {
    int dirNo = state->fResult.fDirNo;
    SkString dirName = get_in_path(dirNo, NULL);
    if (!dirName.size()) {
        return false;
    }
    SkTDArray<TestResult> tests[1];
    SkTDArray<SortByName*> sorted[1];
    if (!buildTestDir(dirNo, dirNo, tests, sorted)) {
        return false;
    }
    SkOSFile::Iter iter(dirName.c_str(), "skp");
    SkString filename;
    while (iter.next(&filename)) {
        for (size_t index = 0; index < skipOverCount; ++index) {
            if (skipOver[index].directory == dirNo
                    && strcmp(filename.c_str(), skipOver[index].filename) == 0) {
                goto checkEarlyExit;
            }
        }
        {
            SortByName name;
            name.init(dirNo);
            strncpy(name.fFilename, filename.c_str(), filename.size() - 4);  // drop .skp
            int count = sorted[0].count();
            int idx = SkTSearch<SortByName, Less>(sorted[0].begin(), count, &name, sizeof(&name));
            if (idx >= 0) {
                SortByName* found = sorted[0][idx];
                (void) addError(state, *found);
                continue;
            }
            TestResult test;
            test.init(dirNo, filename);
            state->fResult = test;
            testSkpClip(state);
#if 0 // artificially limit to a few while debugging code
            static int debugLimit = 0;
            if (++debugLimit == 5) {
                return true;
            }
#endif
        }
checkEarlyExit:
        ;
    }
    return true;
}

static void initTest() {
#if !defined SK_BUILD_FOR_WIN && !defined SK_BUILD_FOR_MAC
    SK_CONF_SET("images.jpeg.suppressDecoderWarnings", true);
    SK_CONF_SET("images.png.suppressDecoderWarnings", true);
#endif
}

static void testSkpClipEncode(TestState* data) {
    data->fResult.testOne();
    if (verbose()) {
        SkDebugf("+");
    }
}

static void encodeFound(TestState& state) {
    if (verbose()) {
        if (state.fPixelWorst.count()) {
            SkTDArray<SortByPixel*> worst;
            for (int index = 0; index < state.fPixelWorst.count(); ++index) {
                *worst.append() = &state.fPixelWorst[index];
            }
            SkTQSort<SortByPixel>(worst.begin(), worst.end() - 1);
            for (int index = 0; index < state.fPixelWorst.count(); ++index) {
                const TestResult& result = *worst[index];
                SkDebugf("%d %s pixelError=%d\n", result.fDirNo, result.fFilename, result.fPixelError);
            }
        }
        if (state.fSlowest.count()) {
            SkTDArray<SortByTime*> slowest;
            for (int index = 0; index < state.fSlowest.count(); ++index) {
                *slowest.append() = &state.fSlowest[index];
            }
            if (slowest.count() > 0) {
                SkTQSort<SortByTime>(slowest.begin(), slowest.end() - 1);
                for (int index = 0; index < slowest.count(); ++index) {
                    const TestResult& result = *slowest[index];
                    SkDebugf("%d %s time=%d\n", result.fDirNo, result.fFilename, result.fTime);
                }
            }
        }
    }
    int threadCount = getThreadCount();
    TestRunner testRunner(threadCount);
    for (int index = 0; index < state.fPixelWorst.count(); ++index) {
        const TestResult& result = state.fPixelWorst[index];
        SkString filename(result.fFilename);
        if (!filename.endsWith(".skp")) {
            filename.append(".skp");
        }
        *testRunner.fRunnables.append() = SkNEW_ARGS(TestRunnableEncode,
                (&testSkpClipEncode, result.fDirNo, filename.c_str(), &testRunner));
    }
    testRunner.render();
}

class Test {
public:
    Test() {}
    virtual ~Test() {}

    const char* getName() { onGetName(&fName); return fName.c_str(); }
    void run() { onRun(); }

protected:
    virtual void onGetName(SkString*) = 0;
    virtual void onRun() = 0;

private:
    SkString    fName;
};

typedef SkTRegistry<Test*(*)(void*)> TestRegistry;

#define DEF_TEST(name)                                        \
    static void test_##name();                       \
    class name##Class : public Test {                                   \
    public:                                                             \
        static Test* Factory(void*) { return SkNEW(name##Class); }      \
    protected:                                                          \
        virtual void onGetName(SkString* name) SK_OVERRIDE {            \
            name->set(#name);                                           \
        }                                                               \
        virtual void onRun() SK_OVERRIDE { test_##name(); } \
    };                                                                  \
    static TestRegistry gReg_##name##Class(name##Class::Factory);       \
    static void test_##name()

DEF_TEST(PathOpsSkpClip) {
    gDirs.setDefault();
    initTest();
    SkTArray<TestResult, true> errors;
    TestState state;
    state.init(0);
    int dirNo;
    gDirs.reset();
    while ((dirNo = gDirs.next()) > 0) {
        if (verbose()) {
            SkDebugf("dirNo=%d\n", dirNo);
        }
        state.fResult.fDirNo = dirNo;
        if (!doOneDir(&state, false)) {
            break;
        }
    }
    encodeFound(state);
}

static void testSkpClipMain(TestState* data) {
        (void) doOneDir(data, true);
}

DEF_TEST(PathOpsSkpClipThreaded) {
    gDirs.setDefault();
    initTest();
    int threadCount = getThreadCount();
    TestRunner testRunner(threadCount);
    int dirNo;
    gDirs.reset();
    while ((dirNo = gDirs.next()) > 0) {
        *testRunner.fRunnables.append() = SkNEW_ARGS(TestRunnableDir,
                (&testSkpClipMain, dirNo, &testRunner));
    }
    testRunner.render();
    TestState state;
    state.init(0);
    gDirs.reset();
    while ((dirNo = gDirs.next()) > 0) {
        TestState& testState = testRunner.fRunnables[dirNo - 1]->fState;
        SkASSERT(testState.fResult.fDirNo == dirNo);
        for (int inner = 0; inner < testState.fPixelWorst.count(); ++inner) {
            addError(&state, testState.fPixelWorst[inner]);
        }
        for (int inner = 0; inner < testState.fSlowest.count(); ++inner) {
            addError(&state, testState.fSlowest[inner]);
        }
    }
    encodeFound(state);
}
 
static bool buildTests(SkTDArray<TestResult>* tests, SkTDArray<SortByName*>* sorted) {
    int firstDirNo = gDirs.first();
    int dirNo;
    while ((dirNo = gDirs.next()) > 0) {
        if (!buildTestDir(dirNo, firstDirNo, tests, sorted)) {
            return false;
        }
    }
    return true;
}

DEF_TEST(PathOpsSkpClipUberThreaded) {
    gDirs.setDefault();
    const int firstDirNo = gDirs.next();
    const int lastDirNo = gDirs.last();
    initTest();
    int dirCount = lastDirNo - firstDirNo + 1;
    SkAutoTDeleteArray<SkTDArray<TestResult> > tests(new SkTDArray<TestResult>[dirCount]);
    SkAutoTDeleteArray<SkTDArray<SortByName*> > sorted(new SkTDArray<SortByName*>[dirCount]);
    if (!buildTests(tests.get(), sorted.get())) {
        return;
    }
    int threadCount = getThreadCount();
    TestRunner testRunner(threadCount);
    int dirNo;
    gDirs.reset();
    while ((dirNo = gDirs.next()) > 0) {
        SkString dirName = get_in_path(dirNo, NULL);
        if (!dirName.size()) {
            continue;
        }
        SkOSFile::Iter iter(dirName.c_str(), "skp");
        SkString filename;
        while (iter.next(&filename)) {
            for (size_t index = 0; index < skipOverCount; ++index) {
                if (skipOver[index].directory == dirNo
                        && strcmp(filename.c_str(), skipOver[index].filename) == 0) {
                    goto checkEarlyExit;
                }
            }
            {
                SortByName name;
                name.init(dirNo);
                strncpy(name.fFilename, filename.c_str(), filename.size() - 4);  // drop .skp
                int count = sorted.get()[dirNo - firstDirNo].count();
                if (SkTSearch<SortByName, Less>(sorted.get()[dirNo - firstDirNo].begin(),
                        count, &name, sizeof(&name)) < 0) {
                    *testRunner.fRunnables.append() = SkNEW_ARGS(TestRunnableFile,
                            (&testSkpClip, dirNo, filename.c_str(), &testRunner));
                }
            }
    checkEarlyExit:
            ;
        }

    }
    testRunner.render();
    SkAutoTDeleteArray<SkTDArray<TestResult> > results(new SkTDArray<TestResult>[dirCount]);
    if (!buildTests(results.get(), NULL)) {
        return;
    }
    SkTDArray<TestResult> allResults;
    for (int dirNo = firstDirNo; dirNo <= lastDirNo; ++dirNo) {
        SkTDArray<TestResult>& array = results.get()[dirNo - firstDirNo];
        allResults.append(array.count(), array.begin());
    }
    int allCount = allResults.count();
    SkTDArray<SortByPixel*> pixels;
    SkTDArray<SortByTime*> times;
    for (int index = 0; index < allCount; ++index) {
        *pixels.append() = (SortByPixel*) &allResults[index];
        *times.append() = (SortByTime*) &allResults[index];
    }
    TestState state;
    if (pixels.count()) {
        SkTQSort<SortByPixel>(pixels.begin(), pixels.end() - 1);
        for (int inner = 0; inner < kMaxFiles; ++inner) {
            *state.fPixelWorst.append() = *pixels[allCount - inner - 1];
        }
    }
    if (times.count()) {
        SkTQSort<SortByTime>(times.begin(), times.end() - 1);
        for (int inner = 0; inner < kMaxFiles; ++inner) {
            *state.fSlowest.append() = *times[allCount - inner - 1];
        }
    }
    encodeFound(state);
}

DEF_TEST(PathOpsSkpClipOneOff) {
    const int testIndex = FLAGS_testIndex;
    int dirNo = gDirs.next();
    if (dirNo < 0) {
        dirNo = skipOver[testIndex].directory;
    }
    const char* skp = gNames.next();
    if (!skp) {
        skp = skipOver[testIndex].filename;
    }
    initTest();
    SkAssertResult(get_in_path(dirNo, skp).size());
    SkString filename(skp);
    TestResult state;
    state.test(dirNo, filename);
    if (verbose()) {
        SkDebugf("%s", state.status().c_str());
    }
    state.fTestStep = kEncodeFiles;
    state.testOne();
}

DEF_TEST(PathOpsTestSkipped) {
    for (size_t index = 0; index < skipOverCount; ++index) {
        const SkipOverTest& skip = skipOver[index];
        if (!skip.blamePathOps) {
            continue;
        }
        int dirNo = skip.directory;
        const char* skp = skip.filename;
        initTest();
        SkAssertResult(get_in_path(dirNo, skp).size());
        SkString filename(skp);
        TestResult state;
        state.test(dirNo, filename);
        if (verbose()) {
            SkDebugf("%s", state.status().c_str());
        }
        state.fTestStep = kEncodeFiles;
        state.testOne();
    }
}

DEF_TEST(PathOpsCopyFails) {
    FLAGS_verbose = true;
    for (size_t index = 0; index < skipOverCount; ++index) {
        int dirNo = skipOver[index].directory;
        SkDebugf("mkdir -p " IN_DIR_PRE "%d" DIR_POST "\n", dirNo);
    }
    for (size_t index = 0; index < skipOverCount; ++index) {
        int dirNo = skipOver[index].directory;
        const char* filename = skipOver[index].filename;
        SkDebugf("rsync -av cary-linux.cnc:/tera" PATH_SLASH "skps" PATH_SLASH "slave"
            "%d" DIR_POST "/%s " IN_DIR_PRE "%d" DIR_POST "\n", dirNo, filename, dirNo);
    }
}

template TestRegistry* TestRegistry::gHead;

class Iter {
public:
    Iter() { this->reset(); }
    void reset() { fReg = TestRegistry::Head(); }

    Test* next() {
        if (fReg) {
            TestRegistry::Factory fact = fReg->factory();
            fReg = fReg->next();
            Test* test = fact(NULL);
            return test;
        }
        return NULL;
    }

private:
    const TestRegistry* fReg;
};

int tool_main(int argc, char** argv);
int tool_main(int argc, char** argv) {
    SetupCrashHandler();
    SkCommandLineFlags::SetUsage("");
    SkCommandLineFlags::Parse(argc, argv);
    SkGraphics::Init();
    SkString header("PathOps SkpClip:");
    if (!FLAGS_match.isEmpty()) {
        header.appendf(" --match");
        for (int index = 0; index < FLAGS_match.count(); ++index) {
            header.appendf(" %s", FLAGS_match[index]);
        }
    }
    if (!FLAGS_dir.isEmpty()) {
        int count = FLAGS_dir.count();
        for (int i = 0; i < count; ++i) {
            const char* range = FLAGS_dir[i];
            const char* dash = strchr(range, '-');
            if (!dash) {
                dash = strchr(range, ',');
            }
            int first = atoi(range);
            int last = dash ? atoi(dash + 1) : first;
            if (!first || !last) {
                SkDebugf("couldn't parse --dir %s\n", range);
                return 1;
            }
            gDirs.set(first, last);
        }
    }
    if (!FLAGS_skp.isEmpty()) {
        gNames.set(FLAGS_skp);
    }
#ifdef SK_DEBUG
    header.append(" SK_DEBUG");
#else
    header.append(" SK_RELEASE");
#endif
    header.appendf(" skia_arch_width=%d", (int)sizeof(void*) * 8);
    if (FLAGS_verbose) {
        header.appendf("\n");
    }
    SkDebugf(header.c_str());
    Iter iter;
    Test* test;
    while ((test = iter.next()) != NULL) {
        SkAutoTDelete<Test> owned(test);
        if (!SkCommandLineFlags::ShouldSkip(FLAGS_match, test->getName())) {
            test->run();
        }
    }
    SkGraphics::Term();
    return 0;
}

#if !defined(SK_BUILD_FOR_IOS) && !defined(SK_BUILD_FOR_NACL)
int main(int argc, char * const argv[]) {
    return tool_main(argc, (char**) argv);
}
#endif
