//
//Copyright (C) 2014-2015 LunarG, Inc.
//
//All rights reserved.
//
//Redistribution and use in source and binary forms, with or without
//modification, are permitted provided that the following conditions
//are met:
//
//    Redistributions of source code must retain the above copyright
//    notice, this list of conditions and the following disclaimer.
//
//    Redistributions in binary form must reproduce the above
//    copyright notice, this list of conditions and the following
//    disclaimer in the documentation and/or other materials provided
//    with the distribution.
//
//    Neither the name of 3Dlabs Inc. Ltd. nor the names of its
//    contributors may be used to endorse or promote products derived
//    from this software without specific prior written permission.
//
//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
//"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
//FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
//COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
//INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
//BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
//LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
//CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
//LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
//ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
//POSSIBILITY OF SUCH DAMAGE.

//
// Disassembler for SPIR-V.
//

#include <cstdlib>
#include <cstring>
#include <cassert>
#include <iomanip>
#include <stack>
#include <sstream>
#include <cstring>

#include "disassemble.h"
#include "doc.h"

namespace spv {
    extern "C" {
        // Include C-based headers that don't have a namespace
        #include "GLSL.std.450.h"
#ifdef AMD_EXTENSIONS
        #include "GLSL.ext.AMD.h"
#endif
    }
}
const char* GlslStd450DebugNames[spv::GLSLstd450Count];

namespace spv {

#ifdef AMD_EXTENSIONS
static const char* GLSLextAMDGetDebugNames(const char*, unsigned);
#endif

static void Kill(std::ostream& out, const char* message)
{
    out << std::endl << "Disassembly failed: " << message << std::endl;
    exit(1);
}

// used to identify the extended instruction library imported when printing
enum ExtInstSet {
    GLSL450Inst,
#ifdef AMD_EXTENSIONS
    GLSLextAMDInst,
#endif
    OpenCLExtInst,
};

// Container class for a single instance of a SPIR-V stream, with methods for disassembly.
class SpirvStream {
public:
    SpirvStream(std::ostream& out, const std::vector<unsigned int>& stream) : out(out), stream(stream), word(0), nextNestedControl(0) { }
    virtual ~SpirvStream() { }

    void validate();
    void processInstructions();

protected:
    SpirvStream(const SpirvStream&);
    SpirvStream& operator=(const SpirvStream&);
    Op getOpCode(int id) const { return idInstruction[id] ? (Op)(stream[idInstruction[id]] & OpCodeMask) : OpNop; }

    // Output methods
    void outputIndent();
    void formatId(Id id, std::stringstream&);
    void outputResultId(Id id);
    void outputTypeId(Id id);
    void outputId(Id id);
    void outputMask(OperandClass operandClass, unsigned mask);
    void disassembleImmediates(int numOperands);
    void disassembleIds(int numOperands);
    int disassembleString();
    void disassembleInstruction(Id resultId, Id typeId, Op opCode, int numOperands);

    // Data
    std::ostream& out;                       // where to write the disassembly
    const std::vector<unsigned int>& stream; // the actual word stream
    int size;                                // the size of the word stream
    int word;                                // the next word of the stream to read

    // map each <id> to the instruction that created it
    Id bound;
    std::vector<unsigned int> idInstruction;  // the word offset into the stream where the instruction for result [id] starts; 0 if not yet seen (forward reference or function parameter)

    std::vector<std::string> idDescriptor;    // the best text string known for explaining the <id>

    // schema
    unsigned int schema;

    // stack of structured-merge points
    std::stack<Id> nestedControl;
    Id nextNestedControl;         // need a slight delay for when we are nested
};

void SpirvStream::validate()
{
    size = (int)stream.size();
    if (size < 4)
        Kill(out, "stream is too short");

    // Magic number
    if (stream[word++] != MagicNumber) {
        out << "Bad magic number";
        return;
    }

    // Version
    out << "// Module Version " << std::hex << stream[word++] << std::endl;

    // Generator's magic number
    out << "// Generated by (magic number): " << std::hex << stream[word++] << std::dec << std::endl;

    // Result <id> bound
    bound = stream[word++];
    idInstruction.resize(bound);
    idDescriptor.resize(bound);
    out << "// Id's are bound by " << bound << std::endl;
    out << std::endl;

    // Reserved schema, must be 0 for now
    schema = stream[word++];
    if (schema != 0)
        Kill(out, "bad schema, must be 0");
}

// Loop over all the instructions, in order, processing each.
// Boiler plate for each is handled here directly, the rest is dispatched.
void SpirvStream::processInstructions()
{
    // Instructions
    while (word < size) {
        int instructionStart = word;

        // Instruction wordCount and opcode
        unsigned int firstWord = stream[word];
        unsigned wordCount = firstWord >> WordCountShift;
        Op opCode = (Op)(firstWord & OpCodeMask);
        int nextInst = word + wordCount;
        ++word;

        // Presence of full instruction
        if (nextInst > size)
            Kill(out, "stream instruction terminated too early");

        // Base for computing number of operands; will be updated as more is learned
        unsigned numOperands = wordCount - 1;

        // Type <id>
        Id typeId = 0;
        if (InstructionDesc[opCode].hasType()) {
            typeId = stream[word++];
            --numOperands;
        }

        // Result <id>
        Id resultId = 0;
        if (InstructionDesc[opCode].hasResult()) {
            resultId = stream[word++];
            --numOperands;

            // save instruction for future reference
            idInstruction[resultId] = instructionStart;
        }

        outputResultId(resultId);
        outputTypeId(typeId);
        outputIndent();

        // Hand off the Op and all its operands
        disassembleInstruction(resultId, typeId, opCode, numOperands);
        if (word != nextInst) {
            out << " ERROR, incorrect number of operands consumed.  At " << word << " instead of " << nextInst << " instruction start was " << instructionStart;
            word = nextInst;
        }
        out << std::endl;
    }
}

void SpirvStream::outputIndent()
{
    for (int i = 0; i < (int)nestedControl.size(); ++i)
        out << "  ";
}

void SpirvStream::formatId(Id id, std::stringstream& idStream)
{
    if (id != 0) {
        // On instructions with no IDs, this is called with "0", which does not
        // have to be within ID bounds on null shaders.
        if (id >= bound)
            Kill(out, "Bad <id>");

        idStream << id;
        if (idDescriptor[id].size() > 0)
            idStream << "(" << idDescriptor[id] << ")";
    }
}

void SpirvStream::outputResultId(Id id)
{
    const int width = 16;
    std::stringstream idStream;
    formatId(id, idStream);
    out << std::setw(width) << std::right << idStream.str();
    if (id != 0)
        out << ":";
    else
        out << " ";

    if (nestedControl.size() && id == nestedControl.top())
        nestedControl.pop();
}

void SpirvStream::outputTypeId(Id id)
{
    const int width = 12;
    std::stringstream idStream;
    formatId(id, idStream);
    out << std::setw(width) << std::right << idStream.str() << " ";
}

void SpirvStream::outputId(Id id)
{
    if (id >= bound)
        Kill(out, "Bad <id>");

    out << id;
    if (idDescriptor[id].size() > 0)
        out << "(" << idDescriptor[id] << ")";
}

void SpirvStream::outputMask(OperandClass operandClass, unsigned mask)
{
    if (mask == 0)
        out << "None";
    else {
        for (int m = 0; m < OperandClassParams[operandClass].ceiling; ++m) {
            if (mask & (1 << m))
                out << OperandClassParams[operandClass].getName(m) << " ";
        }
    }
}

void SpirvStream::disassembleImmediates(int numOperands)
{
    for (int i = 0; i < numOperands; ++i) {
        out << stream[word++];
        if (i < numOperands - 1)
            out << " ";
    }
}

void SpirvStream::disassembleIds(int numOperands)
{
    for (int i = 0; i < numOperands; ++i) {
        outputId(stream[word++]);
        if (i < numOperands - 1)
            out << " ";
    }
}

// return the number of operands consumed by the string
int SpirvStream::disassembleString()
{
    int startWord = word;

    out << " \"";

    const char* wordString;
    bool done = false;
    do {
        unsigned int content = stream[word];
        wordString = (const char*)&content;
        for (int charCount = 0; charCount < 4; ++charCount) {
            if (*wordString == 0) {
                done = true;
                break;
            }
            out << *(wordString++);
        }
        ++word;
    } while (! done);

    out << "\"";

    return word - startWord;
}

void SpirvStream::disassembleInstruction(Id resultId, Id /*typeId*/, Op opCode, int numOperands)
{
    // Process the opcode

    out << (OpcodeString(opCode) + 2);  // leave out the "Op"

    if (opCode == OpLoopMerge || opCode == OpSelectionMerge)
        nextNestedControl = stream[word];
    else if (opCode == OpBranchConditional || opCode == OpSwitch) {
        if (nextNestedControl) {
            nestedControl.push(nextNestedControl);
            nextNestedControl = 0;
        }
    } else if (opCode == OpExtInstImport) {
        idDescriptor[resultId] = (const char*)(&stream[word]);
    }
    else {
        if (resultId != 0 && idDescriptor[resultId].size() == 0) {
            switch (opCode) {
            case OpTypeInt:
                idDescriptor[resultId] = "int";
                break;
            case OpTypeFloat:
                idDescriptor[resultId] = "float";
                break;
            case OpTypeBool:
                idDescriptor[resultId] = "bool";
                break;
            case OpTypeStruct:
                idDescriptor[resultId] = "struct";
                break;
            case OpTypePointer:
                idDescriptor[resultId] = "ptr";
                break;
            case OpTypeVector:
                if (idDescriptor[stream[word]].size() > 0)
                    idDescriptor[resultId].append(idDescriptor[stream[word]].begin(), idDescriptor[stream[word]].begin() + 1);
                idDescriptor[resultId].append("vec");
                switch (stream[word + 1]) {
                case 2:   idDescriptor[resultId].append("2");   break;
                case 3:   idDescriptor[resultId].append("3");   break;
                case 4:   idDescriptor[resultId].append("4");   break;
                case 8:   idDescriptor[resultId].append("8");   break;
                case 16:  idDescriptor[resultId].append("16");  break;
                case 32:  idDescriptor[resultId].append("32");  break;
                default: break;
                }
                break;
            default:
                break;
            }
        }
    }

    // Process the operands.  Note, a new context-dependent set could be
    // swapped in mid-traversal.

    // Handle images specially, so can put out helpful strings.
    if (opCode == OpTypeImage) {
        out << " ";
        disassembleIds(1);
        out << " " << DimensionString((Dim)stream[word++]);
        out << (stream[word++] != 0 ? " depth" : "");
        out << (stream[word++] != 0 ? " array" : "");
        out << (stream[word++] != 0 ? " multi-sampled" : "");
        switch (stream[word++]) {
        case 0: out << " runtime";    break;
        case 1: out << " sampled";    break;
        case 2: out << " nonsampled"; break;
        }
        out << " format:" << ImageFormatString((ImageFormat)stream[word++]);

        if (numOperands == 8) {
            out << " " << AccessQualifierString(stream[word++]);
        }
        return;
    }

    // Handle all the parameterized operands
    for (int op = 0; op < InstructionDesc[opCode].operands.getNum() && numOperands > 0; ++op) {
        out << " ";
        OperandClass operandClass = InstructionDesc[opCode].operands.getClass(op);
        switch (operandClass) {
        case OperandId:
        case OperandScope:
        case OperandMemorySemantics:
            disassembleIds(1);
            --numOperands;
            // Get names for printing "(XXX)" for readability, *after* this id
            if (opCode == OpName)
                idDescriptor[stream[word - 1]] = (const char*)(&stream[word]);
            break;
        case OperandVariableIds:
            disassembleIds(numOperands);
            return;
        case OperandImageOperands:
            outputMask(OperandImageOperands, stream[word++]);
            --numOperands;
            disassembleIds(numOperands);
            return;
        case OperandOptionalLiteral:
        case OperandVariableLiterals:
            if ((opCode == OpDecorate && stream[word - 1] == DecorationBuiltIn) ||
                (opCode == OpMemberDecorate && stream[word - 1] == DecorationBuiltIn)) {
                out << BuiltInString(stream[word++]);
                --numOperands;
                ++op;
            }
            disassembleImmediates(numOperands);
            return;
        case OperandVariableIdLiteral:
            while (numOperands > 0) {
                out << std::endl;
                outputResultId(0);
                outputTypeId(0);
                outputIndent();
                out << "     Type ";
                disassembleIds(1);
                out << ", member ";
                disassembleImmediates(1);
                numOperands -= 2;
            }
            return;
        case OperandVariableLiteralId:
            while (numOperands > 0) {
                out << std::endl;
                outputResultId(0);
                outputTypeId(0);
                outputIndent();
                out << "     case ";
                disassembleImmediates(1);
                out << ": ";
                disassembleIds(1);
                numOperands -= 2;
            }
            return;
        case OperandLiteralNumber:
            disassembleImmediates(1);
            --numOperands;
            if (opCode == OpExtInst) {
                ExtInstSet extInstSet = GLSL450Inst;
                const char* name = idDescriptor[stream[word - 2]].c_str();
                if (0 == memcmp("OpenCL", name, 6)) {
                    extInstSet = OpenCLExtInst;
#ifdef AMD_EXTENSIONS
                } else if (strcmp(spv::E_SPV_AMD_shader_ballot, name) == 0 ||
                           strcmp(spv::E_SPV_AMD_shader_trinary_minmax, name) == 0 ||
                           strcmp(spv::E_SPV_AMD_shader_explicit_vertex_parameter, name) == 0 ||
                           strcmp(spv::E_SPV_AMD_gcn_shader, name) == 0) {
                    extInstSet = GLSLextAMDInst;
#endif
                }
                unsigned entrypoint = stream[word - 1];
                if (extInstSet == GLSL450Inst) {
                    if (entrypoint < GLSLstd450Count) {
                        out << "(" << GlslStd450DebugNames[entrypoint] << ")";
                    }
#ifdef AMD_EXTENSIONS
                } else if (extInstSet == GLSLextAMDInst) {
                    out << "(" << GLSLextAMDGetDebugNames(name, entrypoint) << ")";
#endif
                }
            }
            break;
        case OperandOptionalLiteralString:
        case OperandLiteralString:
            numOperands -= disassembleString();
            break;
        default:
            assert(operandClass >= OperandSource && operandClass < OperandOpcode);

            if (OperandClassParams[operandClass].bitmask)
                outputMask(operandClass, stream[word++]);
            else
                out << OperandClassParams[operandClass].getName(stream[word++]);
            --numOperands;

            break;
        }
    }

    return;
}

static void GLSLstd450GetDebugNames(const char** names)
{
    for (int i = 0; i < GLSLstd450Count; ++i)
        names[i] = "Unknown";

    names[GLSLstd450Round]                   = "Round";
    names[GLSLstd450RoundEven]               = "RoundEven";
    names[GLSLstd450Trunc]                   = "Trunc";
    names[GLSLstd450FAbs]                    = "FAbs";
    names[GLSLstd450SAbs]                    = "SAbs";
    names[GLSLstd450FSign]                   = "FSign";
    names[GLSLstd450SSign]                   = "SSign";
    names[GLSLstd450Floor]                   = "Floor";
    names[GLSLstd450Ceil]                    = "Ceil";
    names[GLSLstd450Fract]                   = "Fract";
    names[GLSLstd450Radians]                 = "Radians";
    names[GLSLstd450Degrees]                 = "Degrees";
    names[GLSLstd450Sin]                     = "Sin";
    names[GLSLstd450Cos]                     = "Cos";
    names[GLSLstd450Tan]                     = "Tan";
    names[GLSLstd450Asin]                    = "Asin";
    names[GLSLstd450Acos]                    = "Acos";
    names[GLSLstd450Atan]                    = "Atan";
    names[GLSLstd450Sinh]                    = "Sinh";
    names[GLSLstd450Cosh]                    = "Cosh";
    names[GLSLstd450Tanh]                    = "Tanh";
    names[GLSLstd450Asinh]                   = "Asinh";
    names[GLSLstd450Acosh]                   = "Acosh";
    names[GLSLstd450Atanh]                   = "Atanh";
    names[GLSLstd450Atan2]                   = "Atan2";
    names[GLSLstd450Pow]                     = "Pow";
    names[GLSLstd450Exp]                     = "Exp";
    names[GLSLstd450Log]                     = "Log";
    names[GLSLstd450Exp2]                    = "Exp2";
    names[GLSLstd450Log2]                    = "Log2";
    names[GLSLstd450Sqrt]                    = "Sqrt";
    names[GLSLstd450InverseSqrt]             = "InverseSqrt";
    names[GLSLstd450Determinant]             = "Determinant";
    names[GLSLstd450MatrixInverse]           = "MatrixInverse";
    names[GLSLstd450Modf]                    = "Modf";
    names[GLSLstd450ModfStruct]              = "ModfStruct";
    names[GLSLstd450FMin]                    = "FMin";
    names[GLSLstd450SMin]                    = "SMin";
    names[GLSLstd450UMin]                    = "UMin";
    names[GLSLstd450FMax]                    = "FMax";
    names[GLSLstd450SMax]                    = "SMax";
    names[GLSLstd450UMax]                    = "UMax";
    names[GLSLstd450FClamp]                  = "FClamp";
    names[GLSLstd450SClamp]                  = "SClamp";
    names[GLSLstd450UClamp]                  = "UClamp";
    names[GLSLstd450FMix]                    = "FMix";
    names[GLSLstd450Step]                    = "Step";
    names[GLSLstd450SmoothStep]              = "SmoothStep";
    names[GLSLstd450Fma]                     = "Fma";
    names[GLSLstd450Frexp]                   = "Frexp";
    names[GLSLstd450FrexpStruct]             = "FrexpStruct";
    names[GLSLstd450Ldexp]                   = "Ldexp";
    names[GLSLstd450PackSnorm4x8]            = "PackSnorm4x8";
    names[GLSLstd450PackUnorm4x8]            = "PackUnorm4x8";
    names[GLSLstd450PackSnorm2x16]           = "PackSnorm2x16";
    names[GLSLstd450PackUnorm2x16]           = "PackUnorm2x16";
    names[GLSLstd450PackHalf2x16]            = "PackHalf2x16";
    names[GLSLstd450PackDouble2x32]          = "PackDouble2x32";
    names[GLSLstd450UnpackSnorm2x16]         = "UnpackSnorm2x16";
    names[GLSLstd450UnpackUnorm2x16]         = "UnpackUnorm2x16";
    names[GLSLstd450UnpackHalf2x16]          = "UnpackHalf2x16";
    names[GLSLstd450UnpackSnorm4x8]          = "UnpackSnorm4x8";
    names[GLSLstd450UnpackUnorm4x8]          = "UnpackUnorm4x8";
    names[GLSLstd450UnpackDouble2x32]        = "UnpackDouble2x32";
    names[GLSLstd450Length]                  = "Length";
    names[GLSLstd450Distance]                = "Distance";
    names[GLSLstd450Cross]                   = "Cross";
    names[GLSLstd450Normalize]               = "Normalize";
    names[GLSLstd450FaceForward]             = "FaceForward";
    names[GLSLstd450Reflect]                 = "Reflect";
    names[GLSLstd450Refract]                 = "Refract";
    names[GLSLstd450FindILsb]                = "FindILsb";
    names[GLSLstd450FindSMsb]                = "FindSMsb";
    names[GLSLstd450FindUMsb]                = "FindUMsb";
    names[GLSLstd450InterpolateAtCentroid]   = "InterpolateAtCentroid";
    names[GLSLstd450InterpolateAtSample]     = "InterpolateAtSample";
    names[GLSLstd450InterpolateAtOffset]     = "InterpolateAtOffset";
}

#ifdef AMD_EXTENSIONS
static const char* GLSLextAMDGetDebugNames(const char* name, unsigned entrypoint)
{
    if (strcmp(name, spv::E_SPV_AMD_shader_ballot) == 0) {
        switch (entrypoint) {
        case SwizzleInvocationsAMD:         return "SwizzleInvocationsAMD";
        case SwizzleInvocationsMaskedAMD:   return "SwizzleInvocationsMaskedAMD";
        case WriteInvocationAMD:            return "WriteInvocationAMD";
        case MbcntAMD:                      return "MbcntAMD";
        default:                            return "Bad";
        }
    } else if (strcmp(name, spv::E_SPV_AMD_shader_trinary_minmax) == 0) {
        switch (entrypoint) {
        case FMin3AMD:      return "FMin3AMD";
        case UMin3AMD:      return "UMin3AMD";
        case SMin3AMD:      return "SMin3AMD";
        case FMax3AMD:      return "FMax3AMD";
        case UMax3AMD:      return "UMax3AMD";
        case SMax3AMD:      return "SMax3AMD";
        case FMid3AMD:      return "FMid3AMD";
        case UMid3AMD:      return "UMid3AMD";
        case SMid3AMD:      return "SMid3AMD";
        default:            return "Bad";
        }
    } else if (strcmp(name, spv::E_SPV_AMD_shader_explicit_vertex_parameter) == 0) {
        switch (entrypoint) {
        case InterpolateAtVertexAMD:    return "InterpolateAtVertexAMD";
        default:                        return "Bad";
        }
    }
    else if (strcmp(name, spv::E_SPV_AMD_gcn_shader) == 0) {
        switch (entrypoint) {
        case CubeFaceIndexAMD:      return "CubeFaceIndexAMD";
        case CubeFaceCoordAMD:      return "CubeFaceCoordAMD";
        case TimeAMD:               return "TimeAMD";
        default:
            break;
        }
    }

    return "Bad";
}
#endif

void Disassemble(std::ostream& out, const std::vector<unsigned int>& stream)
{
    SpirvStream SpirvStream(out, stream);
    spv::Parameterize();
    GLSLstd450GetDebugNames(GlslStd450DebugNames);
    SpirvStream.validate();
    SpirvStream.processInstructions();
}

}; // end namespace spv
