//
// Copyright 2002 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
#include <sstream>
#include <string>
#include <vector>
#include "GLSLANG/ShaderLang.h"
#include "angle_gl.h"
#include "gtest/gtest.h"

class ExpressionLimitTest : public testing::Test
{
  protected:
    static const int kMaxExpressionComplexity = 16;
    static const int kMaxCallStackDepth       = 16;
    static const int kMaxFunctionParameters   = 16;
    static const char *kExpressionTooComplex;
    static const char *kCallStackTooDeep;
    static const char *kHasRecursion;
    static const char *kTooManyParameters;
    static const char *kTooComplexSwitch;
    static const char *kGlobalVariableInit;

    virtual void SetUp()
    {
        memset(&resources, 0, sizeof(resources));

        GenerateResources(&resources);
    }

    // Set up the per compile resources
    static void GenerateResources(ShBuiltInResources *res)
    {
        sh::InitBuiltInResources(res);

        res->MaxVertexAttribs             = 8;
        res->MaxVertexUniformVectors      = 128;
        res->MaxVaryingVectors            = 8;
        res->MaxVertexTextureImageUnits   = 0;
        res->MaxCombinedTextureImageUnits = 8;
        res->MaxTextureImageUnits         = 8;
        res->MaxFragmentUniformVectors    = 16;
        res->MaxDrawBuffers               = 1;

        res->OES_standard_derivatives = 0;
        res->OES_EGL_image_external   = 0;

        res->MaxExpressionComplexity = kMaxExpressionComplexity;
        res->MaxCallStackDepth       = kMaxCallStackDepth;
        res->MaxFunctionParameters   = kMaxFunctionParameters;
    }

    static void GenerateLongExpression(int length, std::stringstream *ss)
    {
        for (int ii = 0; ii < length; ++ii)
        {
            *ss << "+ vec4(" << ii << ")";
        }
    }

    static std::string GenerateShaderWithLongExpression(int length)
    {
        static const char *shaderStart =
            R"(precision mediump float;
            uniform vec4 u_color;
            void main()
            {
               gl_FragColor = u_color
        )";

        std::stringstream ss;
        ss << shaderStart;
        GenerateLongExpression(length, &ss);
        ss << "; }";

        return ss.str();
    }

    static std::string GenerateShaderWithUnusedLongExpression(int length)
    {
        static const char *shaderStart =
            R"(precision mediump float;
            uniform vec4 u_color;
            void main()
            {
               gl_FragColor = u_color;
            }
            vec4 someFunction() {
              return u_color
        )";

        std::stringstream ss;

        ss << shaderStart;
        GenerateLongExpression(length, &ss);
        ss << "; }";

        return ss.str();
    }

    static void GenerateDeepFunctionStack(int length, std::stringstream *ss)
    {
        static const char *shaderStart =
            R"(precision mediump float;
            uniform vec4 u_color;
            vec4 function0()  {
              return u_color;
            }
        )";

        *ss << shaderStart;
        for (int ii = 0; ii < length; ++ii)
        {
            *ss << "vec4 function" << (ii + 1) << "() {\n"
                << "  return function" << ii << "();\n"
                << "}\n";
        }
    }

    static std::string GenerateShaderWithDeepFunctionStack(int length)
    {
        std::stringstream ss;

        GenerateDeepFunctionStack(length, &ss);

        ss << "void main() {\n"
           << "  gl_FragColor = function" << length << "();\n"
           << "}";

        return ss.str();
    }

    static std::string GenerateShaderWithUnusedDeepFunctionStack(int length)
    {
        std::stringstream ss;

        GenerateDeepFunctionStack(length, &ss);

        ss << "void main() {\n"
           << "  gl_FragColor = vec4(0,0,0,0);\n"
           << "}";

        return ss.str();
    }

    static std::string GenerateShaderWithFunctionParameters(int parameters)
    {
        std::stringstream ss;

        ss << "precision mediump float;\n"
           << "\n"
           << "float foo(";
        for (int i = 0; i < parameters; ++i)
        {
            ss << "float f" << i;
            if (i + 1 < parameters)
            {
                ss << ", ";
            }
        }
        ss << ")\n"
           << "{\n"
           << "    return f0;\n"
           << "}\n"
           << "\n"
           << "void main()\n"
           << "{\n"
           << "    gl_FragColor = vec4(0,0,0,0);\n"
           << "}";

        return ss.str();
    }

    static std::string GenerateShaderWithNestingInsideSwitch(int nesting)
    {
        std::stringstream shaderString;
        shaderString <<
            R"(#version 300 es
            uniform int u;

            void main()
            {
                int x;
                switch (u)
                {
                    case 0:
                        x = x)";
        for (int i = 0; i < nesting; ++i)
        {
            shaderString << " + x";
        }
        shaderString <<
            R"(;
                }  // switch (u)
            })";
        return shaderString.str();
    }

    static std::string GenerateShaderWithNestingInsideGlobalInitializer(int nesting)
    {
        std::stringstream shaderString;
        shaderString <<
            R"(uniform int u;
            int x = u)";

        for (int i = 0; i < nesting; ++i)
        {
            shaderString << " + u";
        }
        shaderString << R"(;
            void main()
            {
                gl_FragColor = vec4(0.0);
            })";
        return shaderString.str();
    }

    // Compiles a shader and if there's an error checks for a specific
    // substring in the error log. This way we know the error is specific
    // to the issue we are testing.
    bool CheckShaderCompilation(ShHandle compiler,
                                const char *source,
                                const ShCompileOptions &compileOptions,
                                const char *expected_error)
    {
        bool success = sh::Compile(compiler, &source, 1, compileOptions) != 0;
        if (success)
        {
            success = !expected_error;
        }
        else
        {
            std::string log = sh::GetInfoLog(compiler);
            if (expected_error)
                success = log.find(expected_error) != std::string::npos;

            EXPECT_TRUE(success) << log << "\n----shader----\n" << source;
        }
        return success;
    }

    ShBuiltInResources resources;
};

const char *ExpressionLimitTest::kExpressionTooComplex = "Expression too complex";
const char *ExpressionLimitTest::kCallStackTooDeep     = "Call stack too deep";
const char *ExpressionLimitTest::kHasRecursion =
    "Recursive function call in the following call chain";
const char *ExpressionLimitTest::kTooManyParameters = "Function has too many parameters";
const char *ExpressionLimitTest::kTooComplexSwitch =
    "too complex expressions inside a switch statement";
const char *ExpressionLimitTest::kGlobalVariableInit =
    "global variable initializers must be constant expressions";

TEST_F(ExpressionLimitTest, ExpressionComplexity)
{
    ShShaderSpec spec       = SH_WEBGL_SPEC;
    ShShaderOutput output   = SH_ESSL_OUTPUT;
    ShHandle vertexCompiler = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions          = {};
    compileOptions.limitExpressionComplexity = true;

    // Test expression under the limit passes.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithLongExpression(kMaxExpressionComplexity - 10).c_str(),
        compileOptions, nullptr));
    // Test expression over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithLongExpression(kMaxExpressionComplexity + 10).c_str(),
        compileOptions, kExpressionTooComplex));
    // Test expression over the limit without a limit does not fail.
    compileOptions.limitExpressionComplexity = false;
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithLongExpression(kMaxExpressionComplexity + 10).c_str(),
        compileOptions, nullptr));
    sh::Destruct(vertexCompiler);
}

TEST_F(ExpressionLimitTest, UnusedExpressionComplexity)
{
    ShShaderSpec spec       = SH_WEBGL_SPEC;
    ShShaderOutput output   = SH_ESSL_OUTPUT;
    ShHandle vertexCompiler = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions          = {};
    compileOptions.limitExpressionComplexity = true;

    // Test expression under the limit passes.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler,
        GenerateShaderWithUnusedLongExpression(kMaxExpressionComplexity - 10).c_str(),
        compileOptions, nullptr));
    // Test expression over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler,
        GenerateShaderWithUnusedLongExpression(kMaxExpressionComplexity + 10).c_str(),
        compileOptions, kExpressionTooComplex));
    // Test expression over the limit without a limit does not fail.
    compileOptions.limitExpressionComplexity = false;
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler,
        GenerateShaderWithUnusedLongExpression(kMaxExpressionComplexity + 10).c_str(),
        compileOptions, nullptr));
    sh::Destruct(vertexCompiler);
}

TEST_F(ExpressionLimitTest, CallStackDepth)
{
    ShShaderSpec spec       = SH_WEBGL_SPEC;
    ShShaderOutput output   = SH_ESSL_OUTPUT;
    ShHandle vertexCompiler = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions    = {};
    compileOptions.limitCallStackDepth = true;

    // Test call stack under the limit passes.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithDeepFunctionStack(kMaxCallStackDepth - 10).c_str(),
        compileOptions, nullptr));
    // Test call stack over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithDeepFunctionStack(kMaxCallStackDepth + 10).c_str(),
        compileOptions, kCallStackTooDeep));
    // Test call stack over the limit without limit does not fail.
    compileOptions.limitCallStackDepth = false;
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithDeepFunctionStack(kMaxCallStackDepth + 10).c_str(),
        compileOptions, nullptr));
    sh::Destruct(vertexCompiler);
}

TEST_F(ExpressionLimitTest, UnusedCallStackDepth)
{
    ShShaderSpec spec       = SH_WEBGL_SPEC;
    ShShaderOutput output   = SH_ESSL_OUTPUT;
    ShHandle vertexCompiler = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions    = {};
    compileOptions.limitCallStackDepth = true;

    // Test call stack under the limit passes.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithUnusedDeepFunctionStack(kMaxCallStackDepth - 10).c_str(),
        compileOptions, nullptr));
    // Test call stack over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithUnusedDeepFunctionStack(kMaxCallStackDepth + 10).c_str(),
        compileOptions, kCallStackTooDeep));
    // Test call stack over the limit without limit does not fail.
    compileOptions.limitCallStackDepth = false;
    EXPECT_TRUE(CheckShaderCompilation(
        vertexCompiler, GenerateShaderWithUnusedDeepFunctionStack(kMaxCallStackDepth + 10).c_str(),
        compileOptions, nullptr));
    sh::Destruct(vertexCompiler);
}

TEST_F(ExpressionLimitTest, Recursion)
{
    ShShaderSpec spec       = SH_WEBGL_SPEC;
    ShShaderOutput output   = SH_ESSL_OUTPUT;
    ShHandle vertexCompiler = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions = {};

    static const char *shaderWithRecursion0 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            return someFunc();
        }

        void main() {
            gl_FragColor = u_color * someFunc();
        }
    )";

    static const char *shaderWithRecursion1 =
        R"(precision mediump float;
        uniform vec4 u_color;

        vec4 someFunc();

        vec4 someFunc1()  {
            return someFunc();
        }

        vec4 someFunc()  {
            return someFunc1();
        }

        void main() {
            gl_FragColor = u_color * someFunc();
        }
    )";

    static const char *shaderWithRecursion2 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            if (u_color.x > 0.5) {
                return someFunc();
            } else {
                return vec4(1);
            }
        }

        void main() {
            gl_FragColor = someFunc();
        }
    )";

    static const char *shaderWithRecursion3 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            if (u_color.x > 0.5) {
                return vec4(1);
            } else {
                return someFunc();
            }
        }

        void main() {
            gl_FragColor = someFunc();
        }
    )";

    static const char *shaderWithRecursion4 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            return (u_color.x > 0.5) ? vec4(1) : someFunc();
        }

        void main() {
            gl_FragColor = someFunc();
        }
    )";

    static const char *shaderWithRecursion5 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            return (u_color.x > 0.5) ? someFunc() : vec4(1);
        }

        void main() {
            gl_FragColor = someFunc();
        }
    )";

    static const char *shaderWithRecursion6 =
        R"(precision mediump float;
        uniform vec4 u_color;
        vec4 someFunc()  {
            return someFunc();
        }

        void main() {
            gl_FragColor = u_color;
        }
    )";

    static const char *shaderWithNoRecursion =
        R"(precision mediump float;
        uniform vec4 u_color;

        vec3 rgb(int r, int g, int b) {
            return vec3(float(r) / 255.0, float(g) / 255.0, float(b) / 255.0);
        }

        void main() {
            vec3 hairColor0 = rgb(151, 200, 234);
            vec3 faceColor2 = rgb(183, 148, 133);
            gl_FragColor = u_color + vec4(hairColor0 + faceColor2, 0);
        }
    )";

    static const char *shaderWithRecursion7 =
        R"(precision mediump float;
        uniform vec4 u_color;

        vec4 function2() {
            return u_color;
        }

        vec4 function1() {
            vec4 a = function2();
            vec4 b = function1();
            return a + b;
        }

        void main() {
            gl_FragColor = function1();
        }
    )";

    static const char *shaderWithRecursion8 =
        R"(precision mediump float;
        uniform vec4 u_color;

        vec4 function1();

        vec4 function3() {
            return function1();
        }

        vec4 function2() {
            return function3();
        }

        vec4 function1() {
            return function2();
        }

        void main() {
            gl_FragColor = function1();
        }
    )";

    // Check simple recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion0, compileOptions,
                                       kHasRecursion));
    // Check simple recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion1, compileOptions,
                                       kHasRecursion));
    // Check if recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion2, compileOptions,
                                       kHasRecursion));
    // Check if recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion3, compileOptions,
                                       kHasRecursion));
    // Check ternary recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion4, compileOptions,
                                       kHasRecursion));
    // Check ternary recursions fails.
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion5, compileOptions,
                                       kHasRecursion));

    // Check some more forms of recursion
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion6, compileOptions,
                                       kHasRecursion));
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion7, compileOptions,
                                       kHasRecursion));
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion8, compileOptions,
                                       kHasRecursion));
    // Check unused recursions fails if limiting call stack
    // since we check all paths.
    compileOptions.limitCallStackDepth = true;
    EXPECT_TRUE(CheckShaderCompilation(vertexCompiler, shaderWithRecursion6, compileOptions,
                                       kHasRecursion));

    // Check unused recursions passes.
    EXPECT_TRUE(
        CheckShaderCompilation(vertexCompiler, shaderWithNoRecursion, compileOptions, nullptr));
    // Check unused recursions passes if limiting call stack.
    EXPECT_TRUE(
        CheckShaderCompilation(vertexCompiler, shaderWithNoRecursion, compileOptions, nullptr));
    sh::Destruct(vertexCompiler);
}

TEST_F(ExpressionLimitTest, FunctionParameterCount)
{
    ShShaderSpec spec     = SH_WEBGL_SPEC;
    ShShaderOutput output = SH_ESSL_OUTPUT;
    ShHandle compiler     = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions          = {};
    compileOptions.limitExpressionComplexity = true;

    // Test parameters under the limit succeeds.
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithFunctionParameters(kMaxFunctionParameters).c_str(),
        compileOptions, nullptr));
    // Test parameters over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithFunctionParameters(kMaxFunctionParameters + 1).c_str(),
        compileOptions, kTooManyParameters));
    // Test parameters over the limit without limit does not fail.
    compileOptions.limitExpressionComplexity = false;
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithFunctionParameters(kMaxFunctionParameters + 1).c_str(),
        compileOptions, nullptr));
    sh::Destruct(compiler);
}

TEST_F(ExpressionLimitTest, NestingInsideSwitch)
{
    ShShaderSpec spec     = SH_WEBGL2_SPEC;
    ShShaderOutput output = SH_ESSL_OUTPUT;
    ShHandle compiler     = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions          = {};
    compileOptions.limitExpressionComplexity = true;

    // Test nesting over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithNestingInsideSwitch(kMaxExpressionComplexity + 1).c_str(),
        compileOptions, kExpressionTooComplex));
    // Test that nesting way over the limit doesn't cause stack overflow but is handled
    // gracefully.
    EXPECT_TRUE(CheckShaderCompilation(compiler,
                                       GenerateShaderWithNestingInsideSwitch(5000).c_str(),
                                       compileOptions, kTooComplexSwitch));
    // Test nesting over the limit without limit does not fail.
    compileOptions.limitExpressionComplexity = false;
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithNestingInsideSwitch(kMaxExpressionComplexity + 1).c_str(),
        compileOptions, nullptr));
    sh::Destruct(compiler);
}

TEST_F(ExpressionLimitTest, NestingInsideGlobalInitializer)
{
    ShShaderSpec spec     = SH_WEBGL_SPEC;
    ShShaderOutput output = SH_ESSL_OUTPUT;
    ShHandle compiler     = sh::ConstructCompiler(GL_FRAGMENT_SHADER, spec, output, &resources);
    ShCompileOptions compileOptions          = {};
    compileOptions.limitExpressionComplexity = true;

    // Test nesting over the limit fails.
    EXPECT_TRUE(CheckShaderCompilation(
        compiler,
        GenerateShaderWithNestingInsideGlobalInitializer(kMaxExpressionComplexity + 1).c_str(),
        compileOptions, kExpressionTooComplex));
    // Test that nesting way over the limit doesn't cause stack overflow but is handled
    // gracefully.
    EXPECT_TRUE(CheckShaderCompilation(
        compiler, GenerateShaderWithNestingInsideGlobalInitializer(5000).c_str(), compileOptions,
        kGlobalVariableInit));
    // Test nesting over the limit without limit does not fail.
    compileOptions.limitExpressionComplexity = false;
    EXPECT_TRUE(CheckShaderCompilation(
        compiler,
        GenerateShaderWithNestingInsideGlobalInitializer(kMaxExpressionComplexity + 1).c_str(),
        compileOptions, nullptr));
    sh::Destruct(compiler);
}
