aboutsummaryrefslogtreecommitdiff
path: root/nexgb/xgbgen/protocol.go
blob: 433f4e22c56af3f274aca371a1566d4e4fda0f96 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
package main

import (
	"log"
	"strings"
)

// Protocol is a type that encapsulates all information about one
// particular XML file. It also contains links to other protocol types
// if this protocol imports other other extensions. The import relationship
// is recursive.
type Protocol struct {
	Parent       *Protocol
	Name         string
	ExtXName     string
	ExtName      string
	MajorVersion string
	MinorVersion string

	Imports  []*Protocol
	Types    []Type
	Requests []*Request
}

type Protocols []*Protocol

func (ps Protocols) Len() int           { return len(ps) }
func (ps Protocols) Swap(i, j int)      { ps[i], ps[j] = ps[j], ps[i] }
func (ps Protocols) Less(i, j int) bool { return ps[i].ExtName < ps[j].ExtName }

// Initialize traverses all structures, looks for 'Translation' type,
// and looks up the real type in the namespace. It also sets the source
// name for all relevant fields/structures.
// This is necessary because we don't traverse the XML in order initially.
func (p *Protocol) Initialize() {
	for _, typ := range p.Types {
		typ.Initialize(p)
	}
	for _, req := range p.Requests {
		req.Initialize(p)
	}
}

// PkgName returns the name of this package.
// i.e., 'xproto' for the core X protocol, 'randr' for the RandR extension, etc.
func (p *Protocol) PkgName() string {
	return strings.Replace(p.Name, "_", "", -1)
}

// ProtocolGet searches the current context for the protocol with the given
// name. (i.e., the current protocol and its imports.)
// It is an error if one is not found.
func (p *Protocol) ProtocolFind(name string) *Protocol {
	if p.Name == name {
		return p // that was easy
	}
	for _, imp := range p.Imports {
		if imp.Name == name {
			return imp
		}
	}
	log.Panicf("Could not find protocol with name '%s'.", name)
	panic("unreachable")
}

// isExt returns true if this protocol is an extension.
// i.e., it's name isn't "xproto".
func (p *Protocol) isExt() bool {
	return strings.ToLower(p.Name) != "xproto"
}