/****************************************************************************
**
** Copyright (C) 2017 Klaralvdalens Datakonsult AB (KDAB).
** Contact: https://www.qt.io/licensing/
**
** This file is part of the QtGui module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 3 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL3 included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 3 requirements
** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 2.0 or (at your option) the GNU General
** Public license version 3 or any later version approved by the KDE Free
** Qt Foundation. The licenses are as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-2.0.html and
** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
****************************************************************************/

#include "qshadergenerator_p.h"

#include "qshaderlanguage_p.h"
#include <QRegularExpression>

#include <cctype>
#include <qshaderprogram_p.h>

QT_BEGIN_NAMESPACE
namespace Qt3DRender {
Q_LOGGING_CATEGORY(ShaderGenerator, "ShaderGenerator", QtWarningMsg)

namespace
{
    QByteArray toGlsl(QShaderLanguage::StorageQualifier qualifier, const QShaderFormat &format) noexcept
    {
        if (format.version().majorVersion() <= 2 && format.api() != QShaderFormat::RHI) {
            // Note we're assuming fragment shader only here, it'd be different
            // values for vertex shader, will need to be fixed properly at some
            // point but isn't necessary yet (this problem already exists in past
            // commits anyway)
            switch (qualifier) {
            case QShaderLanguage::Const:
                return "const";
            case QShaderLanguage::Input:
                if (format.shaderType() == QShaderFormat::Vertex)
                    return "attribute";
                else
                    return "varying";
            case QShaderLanguage::Output:
                return ""; // Although fragment shaders for <=2 only have fixed outputs
            case QShaderLanguage::Uniform:
                return "uniform";
            case QShaderLanguage::BuiltIn:
                return "//";
            }
        } else {
            switch (qualifier) {
            case QShaderLanguage::Const:
                return "const";
            case QShaderLanguage::Input:
                return "in";
            case QShaderLanguage::Output:
                return "out";
            case QShaderLanguage::Uniform:
                return "uniform";
            case QShaderLanguage::BuiltIn:
                return "//";
            }
        }

        Q_UNREACHABLE();
    }

    QByteArray toGlsl(QShaderLanguage::VariableType type) noexcept
    {
        switch (type) {
        case QShaderLanguage::Bool:
            return "bool";
        case QShaderLanguage::Int:
            return "int";
        case QShaderLanguage::Uint:
            return "uint";
        case QShaderLanguage::Float:
            return "float";
        case QShaderLanguage::Double:
            return "double";
        case QShaderLanguage::Vec2:
            return "vec2";
        case QShaderLanguage::Vec3:
            return "vec3";
        case QShaderLanguage::Vec4:
            return "vec4";
        case QShaderLanguage::DVec2:
            return "dvec2";
        case QShaderLanguage::DVec3:
            return "dvec3";
        case QShaderLanguage::DVec4:
            return "dvec4";
        case QShaderLanguage::BVec2:
            return "bvec2";
        case QShaderLanguage::BVec3:
            return "bvec3";
        case QShaderLanguage::BVec4:
            return "bvec4";
        case QShaderLanguage::IVec2:
            return "ivec2";
        case QShaderLanguage::IVec3:
            return "ivec3";
        case QShaderLanguage::IVec4:
            return "ivec4";
        case QShaderLanguage::UVec2:
            return "uvec2";
        case QShaderLanguage::UVec3:
            return "uvec3";
        case QShaderLanguage::UVec4:
            return "uvec4";
        case QShaderLanguage::Mat2:
            return "mat2";
        case QShaderLanguage::Mat3:
            return "mat3";
        case QShaderLanguage::Mat4:
            return "mat4";
        case QShaderLanguage::Mat2x2:
            return "mat2x2";
        case QShaderLanguage::Mat2x3:
            return "mat2x3";
        case QShaderLanguage::Mat2x4:
            return "mat2x4";
        case QShaderLanguage::Mat3x2:
            return "mat3x2";
        case QShaderLanguage::Mat3x3:
            return "mat3x3";
        case QShaderLanguage::Mat3x4:
            return "mat3x4";
        case QShaderLanguage::Mat4x2:
            return "mat4x2";
        case QShaderLanguage::Mat4x3:
            return "mat4x3";
        case QShaderLanguage::Mat4x4:
            return "mat4x4";
        case QShaderLanguage::DMat2:
            return "dmat2";
        case QShaderLanguage::DMat3:
            return "dmat3";
        case QShaderLanguage::DMat4:
            return "dmat4";
        case QShaderLanguage::DMat2x2:
            return "dmat2x2";
        case QShaderLanguage::DMat2x3:
            return "dmat2x3";
        case QShaderLanguage::DMat2x4:
            return "dmat2x4";
        case QShaderLanguage::DMat3x2:
            return "dmat3x2";
        case QShaderLanguage::DMat3x3:
            return "dmat3x3";
        case QShaderLanguage::DMat3x4:
            return "dmat3x4";
        case QShaderLanguage::DMat4x2:
            return "dmat4x2";
        case QShaderLanguage::DMat4x3:
            return "dmat4x3";
        case QShaderLanguage::DMat4x4:
            return "dmat4x4";
        case QShaderLanguage::Sampler1D:
            return "sampler1D";
        case QShaderLanguage::Sampler2D:
            return "sampler2D";
        case QShaderLanguage::Sampler3D:
            return "sampler3D";
        case QShaderLanguage::SamplerCube:
            return "samplerCube";
        case QShaderLanguage::Sampler2DRect:
            return "sampler2DRect";
        case QShaderLanguage::Sampler2DMs:
            return "sampler2DMS";
        case QShaderLanguage::SamplerBuffer:
            return "samplerBuffer";
        case QShaderLanguage::Sampler1DArray:
            return "sampler1DArray";
        case QShaderLanguage::Sampler2DArray:
            return "sampler2DArray";
        case QShaderLanguage::Sampler2DMsArray:
            return "sampler2DMSArray";
        case QShaderLanguage::SamplerCubeArray:
            return "samplerCubeArray";
        case QShaderLanguage::Sampler1DShadow:
            return "sampler1DShadow";
        case QShaderLanguage::Sampler2DShadow:
            return "sampler2DShadow";
        case QShaderLanguage::Sampler2DRectShadow:
            return "sampler2DRectShadow";
        case QShaderLanguage::Sampler1DArrayShadow:
            return "sampler1DArrayShadow";
        case QShaderLanguage::Sampler2DArrayShadow:
            return "sample2DArrayShadow";
        case QShaderLanguage::SamplerCubeShadow:
            return "samplerCubeShadow";
        case QShaderLanguage::SamplerCubeArrayShadow:
            return "samplerCubeArrayShadow";
        case QShaderLanguage::ISampler1D:
            return "isampler1D";
        case QShaderLanguage::ISampler2D:
            return "isampler2D";
        case QShaderLanguage::ISampler3D:
            return "isampler3D";
        case QShaderLanguage::ISamplerCube:
            return "isamplerCube";
        case QShaderLanguage::ISampler2DRect:
            return "isampler2DRect";
        case QShaderLanguage::ISampler2DMs:
            return "isampler2DMS";
        case QShaderLanguage::ISamplerBuffer:
            return "isamplerBuffer";
        case QShaderLanguage::ISampler1DArray:
            return "isampler1DArray";
        case QShaderLanguage::ISampler2DArray:
            return "isampler2DArray";
        case QShaderLanguage::ISampler2DMsArray:
            return "isampler2DMSArray";
        case QShaderLanguage::ISamplerCubeArray:
            return "isamplerCubeArray";
        case QShaderLanguage::USampler1D:
            return "usampler1D";
        case QShaderLanguage::USampler2D:
            return "usampler2D";
        case QShaderLanguage::USampler3D:
            return "usampler3D";
        case QShaderLanguage::USamplerCube:
            return "usamplerCube";
        case QShaderLanguage::USampler2DRect:
            return "usampler2DRect";
        case QShaderLanguage::USampler2DMs:
            return "usampler2DMS";
        case QShaderLanguage::USamplerBuffer:
            return "usamplerBuffer";
        case QShaderLanguage::USampler1DArray:
            return "usampler1DArray";
        case QShaderLanguage::USampler2DArray:
            return "usampler2DArray";
        case QShaderLanguage::USampler2DMsArray:
            return "usampler2DMSArray";
        case QShaderLanguage::USamplerCubeArray:
            return "usamplerCubeArray";
        }

        Q_UNREACHABLE();
    }

    QByteArray replaceParameters(const QByteArray &original, const QShaderNode &node,
                                 const QShaderFormat &format) noexcept
    {
        QByteArray result = original;

        const QStringList parameterNames = node.parameterNames();
        for (const QString &parameterName : parameterNames) {
            const QByteArray placeholder = QByteArray(QByteArrayLiteral("$") + parameterName.toUtf8());
            const QVariant parameter = node.parameter(parameterName);
            if (parameter.userType() == qMetaTypeId<QShaderLanguage::StorageQualifier>()) {
                const QShaderLanguage::StorageQualifier qualifier =
                        qvariant_cast<QShaderLanguage::StorageQualifier>(parameter);
                const QByteArray value = toGlsl(qualifier, format);
                result.replace(placeholder, value);
            } else if (parameter.userType() == qMetaTypeId<QShaderLanguage::VariableType>()) {
                const QShaderLanguage::VariableType type =
                        qvariant_cast<QShaderLanguage::VariableType>(parameter);
                const QByteArray value = toGlsl(type);
                result.replace(placeholder, value);
            } else {
                const QByteArray value = parameter.toString().toUtf8();
                result.replace(placeholder, value);
            }
        }

        return result;
    }

    struct ShaderGenerationState
    {
        ShaderGenerationState(const QShaderGenerator &gen,
                              QVector<QShaderGraph::Statement> statements)
            : generator { gen }, statements { statements }
        {

        }

        const QShaderGenerator &generator;
        QVector<QShaderGraph::Statement> statements;
        QByteArrayList code;
    };

    class GLSL45HeaderWriter
    {
    public:
        void writeHeader(ShaderGenerationState &state)
        {
            const auto &format = state.generator.format;
            auto &code = state.code;
            for (const QShaderGraph::Statement &statement : state.statements) {
                const QShaderNode &node = statement.node;
                const QByteArrayList &headerSnippets = node.rule(format).headerSnippets;
                for (const QByteArray &snippet : headerSnippets) {
                    auto replacedSnippet = replaceParameters(snippet, node, format).trimmed();

                    if (replacedSnippet.startsWith(QByteArrayLiteral("add-input"))) {
                        onInOut(code, replacedSnippet);
                    } else if (replacedSnippet.startsWith(QByteArrayLiteral("add-uniform"))) {
                        onNamedUniform(ubo, replacedSnippet);
                    } else if (replacedSnippet.startsWith(QByteArrayLiteral("add-sampler"))) {
                        onNamedSampler(code, replacedSnippet);
                    } else if (replacedSnippet.startsWith(QByteArrayLiteral("#pragma include "))) {
                        onInclude(code, replacedSnippet);
                    } else {
                        code << replacedSnippet;
                    }
                }
            }

            if (!ubo.isEmpty()) {
                code << QByteArrayLiteral("layout(std140, binding = ")
                                + QByteArray::number(currentBinding++)
                                + QByteArrayLiteral(") uniform qt3d_shadergraph_generated_uniforms {");
                code << ubo;
                code << "};";
            }
        }

    private:
        void onInOut(QByteArrayList &code, const QByteArray &snippet) noexcept
        {
            const auto split = snippet.split(' ');
            if (split.size() < 4) {
                qDebug() << "Invalid header snippet: " << snippet;
                return;
            }
            const auto &qualifier = split[1];
            const auto &type = split[2];
            const auto &name = split[3];

            if (qualifier == QByteArrayLiteral("in")) {
                code << (QByteArrayLiteral("layout(location = ")
                         + QByteArray::number(currentInputLocation++) + QByteArrayLiteral(") in ")
                         + type + ' ' + name + QByteArrayLiteral(";"));
            } else if (qualifier == QByteArrayLiteral("out")) {
                code << (QByteArrayLiteral("layout(location = ")
                         + QByteArray::number(currentOutputLocation++) + QByteArrayLiteral(") out ")
                         + type + ' ' + name + QByteArrayLiteral(";"));
            } else if (qualifier == QByteArrayLiteral("uniform")) {
                ubo << (type + ' ' + name + ';');
            }
        }

        void onNamedUniform(QByteArrayList &ubo, const QByteArray &snippet) noexcept
        {
            const auto split = snippet.split(' ');
            if (split.size() < 3) {
                qDebug() << "Invalid header snippet: " << snippet;
                return;
            }

            const auto &type = split[1];
            const auto &name = split[2];

            ubo << (type + ' ' + name + ';');
        }

        void onNamedSampler(QByteArrayList &code, const QByteArray &snippet) noexcept
        {
            const auto split = snippet.split(' ');
            if (split.size() < 3) {
                qDebug() << "Invalid header snippet: " << snippet;
                return;
            }
            const auto binding = QByteArray::number(currentBinding++);
            const auto &type = split[1];
            const auto &name = split[2];

            code << (QByteArrayLiteral("layout(binding = ") + binding + QByteArrayLiteral(") uniform ")
                     + type + ' ' + name + QByteArrayLiteral(";"));
        }

        void onInclude(QByteArrayList &code, const QByteArray &snippet) noexcept
        {
            const auto filepath = QString::fromUtf8(snippet.mid(strlen("#pragma include ")));
            QString deincluded = QString::fromUtf8(QShaderProgramPrivate::deincludify(filepath));

            // This lambda will replace all occurrences of a string (e.g. "binding = auto") by another,
            // with the incremented int passed as argument (e.g. "binding = 1", "binding = 2" ...)
            const auto replaceAndIncrement = [&deincluded](const QRegularExpression &regexp,
                                                           int &variable,
                                                           const QString &replacement) noexcept {
                int matchStart = 0;
                do {
                    matchStart = deincluded.indexOf(regexp, matchStart);
                    if (matchStart != -1) {
                        const auto match = regexp.match(deincluded.midRef(matchStart));
                        const auto length = match.capturedLength(0);

                        deincluded.replace(matchStart, length, replacement.arg(variable++));
                    }
                } while (matchStart != -1);
            };

            // 1. Handle uniforms
            {
                thread_local const QRegularExpression bindings(
                        QStringLiteral("binding\\s?+=\\s?+auto"));

                replaceAndIncrement(bindings, currentBinding, QStringLiteral("binding = %1"));
            }

            // 2. Handle inputs
            {
                thread_local const QRegularExpression inLocations(
                        QStringLiteral("location\\s?+=\\s?+auto\\s?+\\)\\s?+in\\s+"));

                replaceAndIncrement(inLocations, currentInputLocation,
                                    QStringLiteral("location = %1) in "));
            }

            // 3. Handle outputs
            {
                thread_local const QRegularExpression outLocations(
                        QStringLiteral("location\\s?+=\\s?+auto\\s?+\\)\\s?+out\\s+"));

                replaceAndIncrement(outLocations, currentOutputLocation,
                                    QStringLiteral("location = %1) out "));
            }

            code << deincluded.toUtf8();
        }

        int currentInputLocation { 0 };
        int currentOutputLocation { 0 };
        int currentBinding { 2 };
        QByteArrayList ubo;
    };

    struct GLSLHeaderWriter
    {
        void writeHeader(ShaderGenerationState &state)
        {
            const auto &format = state.generator.format;
            auto &code = state.code;
            for (const QShaderGraph::Statement &statement : state.statements) {
                const QShaderNode &node = statement.node;
                const QByteArrayList &headerSnippets = node.rule(format).headerSnippets;
                for (const QByteArray &snippet : headerSnippets) {
                    code << replaceParameters(snippet, node, format);
                }
            }
        }
    };

    QByteArray versionString(const QShaderFormat &format) noexcept
    {
        if (!format.isValid())
            return {};

        switch (format.api()) {
        case QShaderFormat::RHI: {
            return QByteArrayLiteral("#version 450");
        }
        case QShaderFormat::VulkanFlavoredGLSL: {
            const int major = format.version().majorVersion();
            const int minor = format.version().minorVersion();
            return (QByteArrayLiteral("#version ") + QByteArray::number(major * 100 + minor * 10));
        }
        default: {
            const bool isGLES = format.api() == QShaderFormat::OpenGLES;
            const int major = format.version().majorVersion();
            const int minor = format.version().minorVersion();

            const int version = major == 2 && isGLES ? 100
                              : major == 3 && isGLES ? 300
                              : major == 2 ? 100 + 10 * (minor + 1)
                              : major == 3 && minor <= 2 ? 100 + 10 * (minor + 3)
                              : major * 100 + minor * 10;

            const QByteArray profile =
                    isGLES && version > 100 ? QByteArrayLiteral(" es")
                    : version >= 150 && format.api() == QShaderFormat::OpenGLCoreProfile ? QByteArrayLiteral(" core")
                    : version >= 150 && format.api() == QShaderFormat::OpenGLCompatibilityProfile ? QByteArrayLiteral(" compatibility")
                    : QByteArray();

            return (QByteArrayLiteral("#version ") + QByteArray::number(version) + profile);
        }
        }
    }
}

QByteArray QShaderGenerator::createShaderCode(const QStringList &enabledLayers) const
{
    const QVector<QShaderNode> nodes = graph.nodes();
    const auto statements = graph.createStatements(enabledLayers);
    ShaderGenerationState state(*this, statements);
    QByteArrayList &code = state.code;

    code << versionString(format);
    code << QByteArray();

    if (format.api() == QShaderFormat::VulkanFlavoredGLSL || format.api() == QShaderFormat::RHI) {
        GLSL45HeaderWriter builder;
        builder.writeHeader(state);
    } else {
        GLSLHeaderWriter builder;
        builder.writeHeader(state);
    }

    code << QByteArray();
    code << QByteArrayLiteral("void main()");
    code << QByteArrayLiteral("{");

    const QRegularExpression temporaryVariableToAssignmentRegExp(
            QStringLiteral("([^;]*\\s+(v\\d+))\\s*=\\s*([^;]*);"));
    const QRegularExpression temporaryVariableInAssignmentRegExp(QStringLiteral("\\W*(v\\d+)\\W*"));
    const QRegularExpression statementRegExp(QStringLiteral("\\s*(\\w+)\\s*=\\s*([^;]*);"));

    struct Variable;

    struct Assignment
    {
        QString expression;
        QVector<Variable *> referencedVariables;
    };

    struct Variable
    {
        enum Type { GlobalInput, TemporaryAssignment, Output };

        QString name;
        QString declaration;
        int referenceCount = 0;
        Assignment assignment;
        Type type = TemporaryAssignment;
        bool substituted = false;

        static void substitute(Variable *v)
        {
            if (v->substituted)
                return;

            qCDebug(ShaderGenerator)
                    << "Begin Substituting " << v->name << " = " << v->assignment.expression;
            for (Variable *ref : qAsConst(v->assignment.referencedVariables)) {
                // Recursively substitute
                Variable::substitute(ref);

                // Replace all variables referenced only once in the assignment
                // by their actual expression
                if (ref->referenceCount == 1 || ref->type == Variable::GlobalInput) {
                    const QRegularExpression r(QStringLiteral("(.*\\b)(%1)(\\b.*)").arg(ref->name));
                    if (v->assignment.referencedVariables.size() == 1)
                        v->assignment.expression.replace(
                                r, QStringLiteral("\\1%2\\3").arg(ref->assignment.expression));
                    else
                        v->assignment.expression.replace(
                                r, QStringLiteral("(\\1%2\\3)").arg(ref->assignment.expression));
                }
            }
            qCDebug(ShaderGenerator)
                    << "Done Substituting " << v->name << " = " << v->assignment.expression;
            v->substituted = true;
        }
    };

    struct LineContent
    {
        QByteArray rawContent;
        Variable *var = nullptr;
    };

    // Table to store temporary variables that should be replaced:
    // - If variable references a a global variables
    //   -> we will use the global variable directly
    // - If variable references a function results
    //   -> will be kept only if variable is referenced more than once.
    // This avoids having vec3 v56 = vertexPosition; when we could
    // just use vertexPosition directly.
    // The added benefit is when having arrays, we don't try to create
    // mat4 v38 = skinningPalelette[100] which would be invalid
    QVector<Variable> temporaryVariables;
    // Reserve more than enough space to ensure no reallocation will take place
    temporaryVariables.reserve(nodes.size() * 8);

    QVector<LineContent> lines;

    auto createVariable = [&] () -> Variable * {
        Q_ASSERT(temporaryVariables.capacity() > 0);
        temporaryVariables.resize(temporaryVariables.size() + 1);
        return &temporaryVariables.last();
    };

    auto findVariable = [&] (const QString &name) -> Variable * {
        const auto end = temporaryVariables.end();
        auto it = std::find_if(temporaryVariables.begin(), end,
                               [=] (const Variable &a) { return a.name == name; });
        if (it != end)
            return &(*it);
        return nullptr;
    };

    auto gatherTemporaryVariablesFromAssignment = [&](Variable *v,
                                                      const QString &assignmentContent) {
        QRegularExpressionMatchIterator subMatchIt =
                temporaryVariableInAssignmentRegExp.globalMatch(assignmentContent);
        while (subMatchIt.hasNext()) {
            const QRegularExpressionMatch subMatch = subMatchIt.next();
            const QString variableName = subMatch.captured(1);

            // Variable we care about should already exists -> an expression cannot reference a
            // variable that hasn't been defined
            Variable *u = findVariable(variableName);
            Q_ASSERT(u);

            // Increase reference count for u
            ++u->referenceCount;
            // Insert u as reference for variable v
            v->assignment.referencedVariables.push_back(u);
        }
    };

    for (const QShaderGraph::Statement &statement : statements) {
        const QShaderNode node = statement.node;
        QByteArray line = node.rule(format).substitution;
        const QVector<QShaderNodePort> ports = node.ports();

        struct VariableReplacement
        {
            QByteArray placeholder;
            QByteArray variable;
        };

        QVector<VariableReplacement> variableReplacements;

        // Generate temporary variable names vN
        for (const QShaderNodePort &port : ports) {
            const QString portName = port.name;
            const QShaderNodePort::Direction portDirection = port.direction;
            const bool isInput = port.direction == QShaderNodePort::Input;

            const int portIndex = statement.portIndex(portDirection, portName);

            Q_ASSERT(portIndex >= 0);

            const int variableIndex =
                    isInput ? statement.inputs.at(portIndex) : statement.outputs.at(portIndex);
            if (variableIndex < 0)
                continue;

            VariableReplacement replacement;
            replacement.placeholder = QByteArrayLiteral("$") + portName.toUtf8();
            replacement.variable = QByteArrayLiteral("v") + QByteArray::number(variableIndex);

            variableReplacements.append(std::move(replacement));
        }

        int begin = 0;
        while ((begin = line.indexOf('$', begin)) != -1) {
            int end = begin + 1;
            char endChar = line.at(end);
            const int size = line.size();
            while (end < size && (std::isalnum(endChar) || endChar == '_')) {
                ++end;
                endChar = line.at(end);
            }

            const int placeholderLength = end - begin;

            const QByteArray variableName = line.mid(begin, placeholderLength);
            const auto replacementIt =
                    std::find_if(variableReplacements.cbegin(), variableReplacements.cend(),
                                 [&variableName](const VariableReplacement &replacement) {
                                     return variableName == replacement.placeholder;
                                 });

            if (replacementIt != variableReplacements.cend()) {
                line.replace(begin, placeholderLength, replacementIt->variable);
                begin += replacementIt->variable.length();
            } else {
                begin = end;
            }
        }

        // Substitute variable names by generated vN variable names
        const QByteArray substitutionedLine = replaceParameters(line, node, format);

        QRegularExpressionMatchIterator matches;

        switch (node.type()) {
        case QShaderNode::Input:
        case QShaderNode::Output:
            matches = statementRegExp.globalMatch(QString::fromUtf8(substitutionedLine));
            break;
        case QShaderNode::Function:
            matches = temporaryVariableToAssignmentRegExp.globalMatch(
                    QString::fromUtf8(substitutionedLine));
            break;
        case QShaderNode::Invalid:
            break;
        }

        while (matches.hasNext()) {
            QRegularExpressionMatch match = matches.next();

            Variable *v = nullptr;

            switch (node.type()) {
            // Record name of temporary variable that possibly references a global input
            // We will replace the temporary variables by the matching global variables later
            case QShaderNode::Input: {
                const QString localVariable = match.captured(1);
                const QString globalVariable = match.captured(2);

                v = createVariable();
                v->name = localVariable;
                v->type = Variable::GlobalInput;

                Assignment assignment;
                assignment.expression = globalVariable;
                v->assignment = assignment;
                break;
            }

            case QShaderNode::Function: {
                const QString localVariableDeclaration = match.captured(1);
                const QString localVariableName = match.captured(2);
                const QString assignmentContent = match.captured(3);

                // Add new variable -> it cannot exist already
                v = createVariable();
                v->name = localVariableName;
                v->declaration = localVariableDeclaration;
                v->assignment.expression = assignmentContent;

                // Find variables that may be referenced in the assignment
                gatherTemporaryVariablesFromAssignment(v, assignmentContent);
                break;
            }

            case QShaderNode::Output: {
                const QString outputDeclaration = match.captured(1);
                const QString assignmentContent = match.captured(2);

                v = createVariable();
                v->name = outputDeclaration;
                v->declaration = outputDeclaration;
                v->type = Variable::Output;

                Assignment assignment;
                assignment.expression = assignmentContent;
                v->assignment = assignment;

                // Find variables that may be referenced in the assignment
                gatherTemporaryVariablesFromAssignment(v, assignmentContent);
                break;
            }
            case QShaderNode::Invalid:
                break;
            }

            LineContent lineContent;
            lineContent.rawContent = QByteArray(QByteArrayLiteral("    ") + substitutionedLine);
            lineContent.var = v;
            lines << lineContent;
        }
    }

    // Go through all lines
    // Perform substitution of line with temporary variables substitution
    for (LineContent &lineContent : lines) {
        Variable *v = lineContent.var;
        qCDebug(ShaderGenerator) << lineContent.rawContent;
        if (v != nullptr) {
            Variable::substitute(v);

            qCDebug(ShaderGenerator)
                    << "Line " << lineContent.rawContent << "is assigned to temporary" << v->name;

            // Check number of occurrences a temporary variable is referenced
            if (v->referenceCount == 1 || v->type == Variable::GlobalInput) {
                // If it is referenced only once, no point in creating a temporary
                // Clear content for current line
                lineContent.rawContent.clear();
                // We assume expression that were referencing vN will have vN properly substituted
            } else {
                lineContent.rawContent = QStringLiteral("    %1 = %2;")
                                                 .arg(v->declaration)
                                                 .arg(v->assignment.expression)
                                                 .toUtf8();
            }

            qCDebug(ShaderGenerator) << "Updated Line is " << lineContent.rawContent;
        }
    }

    // Go throug all lines and insert content
    for (const LineContent &lineContent : qAsConst(lines)) {
        if (!lineContent.rawContent.isEmpty()) {
            code << lineContent.rawContent;
        }
    }

    code << QByteArrayLiteral("}");
    code << QByteArray();

    return code.join('\n');
}

}
QT_END_NAMESPACE
