
/*
 * Copyright 2016 Google Inc.
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

#ifndef TestContext_DEFINED
#define TestContext_DEFINED

#include "include/core/SkRefCnt.h"
#include "include/gpu/GrTypes.h"
#include "include/private/SkNoncopyable.h"
#include "include/private/SkTemplates.h"
#include "src/core/SkScopeExit.h"
#include "tools/gpu/FenceSync.h"

class GrContext;
struct GrContextOptions;

namespace sk_gpu_test {

class GpuTimer;
class FlushFinishTracker;

/**
 * An offscreen 3D context. This class is intended for Skia's internal testing needs and not
 * for general use.
 */
class TestContext : public SkNoncopyable {
public:
    virtual ~TestContext();

    bool fenceSyncSupport() const { return fFenceSupport; }

    bool gpuTimingSupport() const { return fGpuTimer != nullptr; }
    GpuTimer* gpuTimer() const { SkASSERT(fGpuTimer); return fGpuTimer.get(); }

    bool getMaxGpuFrameLag(int *maxFrameLag) const {
        if (!this->fenceSyncSupport()) {
            return false;
        }
        *maxFrameLag = kMaxFrameLag;
        return true;
    }

    void makeNotCurrent() const;
    void makeCurrent() const;

    /**
     * Like makeCurrent() but this returns an object that will restore the previous current
     * context in its destructor. Useful to undo the effect making this current before returning to
     * a caller that doesn't expect the current context to be changed underneath it.
     *
     * The returned object restores the current context of the same type (e.g. egl, glx, ...) in its
     * destructor. It is undefined behavior if that context is destroyed before the destructor
     * executes. If the concept of a current context doesn't make sense for this context type then
     * the returned object's destructor is a no-op.
     */
    SkScopeExit SK_WARN_UNUSED_RESULT makeCurrentAndAutoRestore() const;

    virtual GrBackendApi backend() = 0;

    virtual sk_sp<GrContext> makeGrContext(const GrContextOptions&);

    /**
     * This will flush work to the GPU. Additionally, if the platform supports fence syncs, we will
     * add a finished callback to our flush call. We allow ourselves to have kMaxFrameLag number of
     * unfinished flushes active on the GPU at a time. If we have 2 outstanding flushes then we will
     * wait on the CPU until one has finished.
     */
    void flushAndWaitOnSync(GrContext* context);

    /**
     * This notifies the context that we are deliberately testing abandoning
     * the context. It is useful for debugging contexts that would otherwise
     * test that GPU resources are properly deleted. It also allows a debugging
     * context to test that further API calls are not made by Skia GPU code.
     */
    virtual void testAbandon();

    /** Wait until all GPU work is finished. */
    virtual void finish() = 0;

protected:
    bool fFenceSupport = false;

    std::unique_ptr<GpuTimer>  fGpuTimer;

    TestContext();

    /** This should destroy the 3D context. */
    virtual void teardown();

    virtual void onPlatformMakeNotCurrent() const = 0;
    virtual void onPlatformMakeCurrent() const = 0;
    /**
     * Subclasses should implement such that the returned function will cause the current context
     * of this type to be made current again when it is called. It should additionally be the
     * case that if "this" is already current when this is called, then "this" is destroyed (thereby
     * setting the null context as current), and then the std::function is called the null context
     * should remain current.
     */
    virtual std::function<void()> onPlatformGetAutoContextRestore() const = 0;

private:
    enum {
        kMaxFrameLag = 3
    };

    sk_sp<FlushFinishTracker> fFinishTrackers[kMaxFrameLag - 1];
    int fCurrentFlushIdx = 0;

    typedef SkNoncopyable INHERITED;
};
}  // namespace sk_gpu_test
#endif
