// Copyright (C) 2019 Google Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

// Generated by {{GenerateArguments}}
// Do not modify this file directly.

package schema

// Opcode holds information about a specific SPIR-V opcode.
type Opcode struct {
	Opname   string
	Class    string
	Opcode   int
	Operands []Operand
}

// Operand contains information about a logical operand for an instruction.
type Operand struct {
	Kind       *OperandKind
	Name       string
	Quantifier Quantifier
}

// OperandKind contains information about a specific operand kind.
type OperandKind struct {
	Category   OperandCategory
	Kind       string
	Enumerants []Enumerant
	Bases      []*OperandKind
}

// Enumerant contains information about an enumerant in an enum.
type Enumerant struct {
	Enumerant    string
	Value        interface{}
	Capabilities []string
	Parameters   []Parameter
	Version      string
}

// Parameter contains information about a logical parameter for an enumerant.
type Parameter struct {
	Kind *OperandKind
	Name string
}

// Quantifier indicates the number of times the quantified term may appear.
type Quantifier string

const (
	// Once indicates the quantified term may appear exactly once.
	Once Quantifier = ""

	// ZeroOrOnce indicates the quantified term may appear zero or one
	// time; an optional term.
	ZeroOrOnce Quantifier = "?"

	// ZeroOrMany indicates the quantified term may appear any number of
	// times.
	ZeroOrMany Quantifier = "*"
)

// OperandCategory is an enumerator that groups operand kinds.
type OperandCategory string

const (
	// OperandCategoryBitEnum describes an operand kind where its value is a
	// mask, which is formed by combining the bits specified as enumerants in an
	// enum.
	OperandCategoryBitEnum = "BitEnum"

	// OperandCategoryValueEnum describes an operand kind where its value is an
	// enumerant from an enum.
	OperandCategoryValueEnum = "ValueEnum"

	// OperandCategoryID describes and operand kind where its value is an <id>
	// definition or reference.
	OperandCategoryID = "Id"

	// OperandCategoryLiteral describes and operand kind where its value is an
	// literal number or string.
	OperandCategoryLiteral = "Literal"

	// OperandCategoryComposite describes and operand kind where its value is
	// composed from operand values from the above categories.
	OperandCategoryComposite = "Composite"
)

// OpcodeMap is a map of opcode name to Opcode type.
type OpcodeMap map[string]*Opcode

var (
	// Opcodes is a map of opcode name to Opcode description.
	Opcodes = OpcodeMap {•{{range $i := .SPIRV.Instructions}}
		"{{$i.Opname}}": {{Title $i.Opname}},{{end}}
	}

	// ExtOpcodes is a map of extension name to Opcode description list.
	ExtOpcodes = map[string]OpcodeMap {•{{range $ext := .Extensions}}
		"{{$ext.Name}}": {•{{range $i := $ext.Instructions}}
			"{{$i.Opname}}": {{Global $ext.Name}}_{{$i.Opname}},{{end}}
		},{{end}}
	}

{{range $i := .SPIRV.Instructions}}	{{Title $i.Opname}} = &Opcode {
		Opname:   "{{$i.Opname}}",
		Class:    "{{$i.Class}}",
		Opcode:   {{$i.Opcode}},
		Operands: []Operand {•{{range $i := $i.Operands}}
			Operand {
				Kind:       OperandKind{{$i.Kind}},
				Name:       "{{Replace $i.Name "\n" " "}}",
				Quantifier: "{{$i.Quantifier}}",
			}, {{end}}
		},
	}
{{end}}
{{range $ext := .Extensions}}{{range $i := $ext.Instructions}}	{{Global $ext.Name}}_{{$i.Opname}} = &Opcode {
		Opname:   "{{$i.Opname}}",
		Operands: []Operand {•{{range $i := $i.Operands}}
			Operand {
				Kind:       OperandKind{{$i.Kind}},
				Name:       "{{Replace $i.Name "\n" " "}}",
				Quantifier: "{{$i.Quantifier}}",
			}, {{end}}
		},
	}
{{end}}{{end}}

{{range $o := .All.OperandKinds}}	OperandKind{{$o.Kind}} = &OperandKind {
		Kind:       "{{$o.Kind}}",
		Category:   "{{$o.Category}}",
		Enumerants: []Enumerant {•{{range $e := $o.Enumerants}}
			Enumerant{
				Enumerant:    "{{$e.Enumerant}}",
				Value:        {{$e.Value}},
				Capabilities: []string{•{{range $c := $e.Capabilities}}"{{$c}}",{{end}}•},
				Parameters:   []Parameter{•{{range $p := $e.Parameters}}{•OperandKind{{$p.Kind}}, "{{$p.Name}}"•},{{end}}•},
				Version:      "{{$e.Version}}",
			},{{end}}
		},
		Bases:      []*OperandKind {•{{range $b := $o.Bases}}OperandKind{{$b}},{{end}}•},
	}
{{end}}
)
