Migrate all libvirt calls to the generated code.
- Update libvirt.go so that all libvirt calls now go through the generated routines. - Remove some libvirt routines that had the same name as generated ones, leave the rest as convenience routines. - Fix the handling of Optional-values (the declarations of which in the .x file look like pointers)
This commit is contained in:
parent
a3bd42a5b1
commit
b59e9d42f4
@ -25,6 +25,10 @@ import (
|
||||
"unicode/utf8"
|
||||
)
|
||||
|
||||
// If you're making changes to the generator, or troubleshooting the generated
|
||||
// code, the docs for sunrpc and xdr (the line encoding) are helpful:
|
||||
// https://docs.oracle.com/cd/E26502_01/html/E35597/
|
||||
|
||||
// ConstItem stores an const's symbol and value from the parser. This struct is
|
||||
// also used for enums.
|
||||
type ConstItem struct {
|
||||
@ -81,7 +85,6 @@ var goEquivTypes = map[string]string{
|
||||
// TODO: Get rid of these. They're only needed because we lose information
|
||||
// that the parser has (the parser knows it has emitted a go type), and then
|
||||
// we capitalize types to make them public.
|
||||
"String": "string",
|
||||
"Int": "int",
|
||||
"Uint": "uint",
|
||||
"Int8": "int8",
|
||||
@ -580,7 +583,7 @@ func checkIdentifier(i string) string {
|
||||
}
|
||||
|
||||
// GetUnion returns the type information for a union. If the provided type name
|
||||
// isn't a union, the second return value will be false.
|
||||
// isn't a union, this will return a zero-value Union type.
|
||||
func (decl *Decl) GetUnion() Union {
|
||||
ix, ok := Gen.UnionMap[decl.Type]
|
||||
if ok {
|
||||
|
@ -42,8 +42,10 @@ type {{$casetype}} struct {
|
||||
DVal uint32
|
||||
{{.Name}} {{.Type}}
|
||||
}
|
||||
func New{{$casetype}}(v {{.Type}}) *{{$casetype}} { return &{{$casetype}}{DVal: {{.DiscriminantVal}}, {{.Name}}: v} }
|
||||
func Decode{{$casetype}}(dec *xdr.Decoder) (*{{$casetype}}, error) {
|
||||
func New{{$casetype}}(v {{.Type}}) *{{$casetype}} {
|
||||
return &{{$casetype}}{DVal: {{.DiscriminantVal}}, {{.Name}}: v}
|
||||
}
|
||||
func decode{{$casetype}}(dec *xdr.Decoder) (*{{$casetype}}, error) {
|
||||
var v {{.Type}}
|
||||
_, err := dec.Decode(&v)
|
||||
if err != nil {
|
||||
@ -53,49 +55,46 @@ func Decode{{$casetype}}(dec *xdr.Decoder) (*{{$casetype}}, error) {
|
||||
}
|
||||
func (c *{{$casetype}}) Get() interface{} { return c.{{.Name}} }
|
||||
{{end}}
|
||||
{{- end}}
|
||||
|
||||
// TODO: Generate this.
|
||||
func decodeTypedParams(dec *xdr.Decoder) ([]TypedParam, error) {
|
||||
count, _, err := dec.DecodeInt()
|
||||
params := make([]TypedParam, count)
|
||||
func decode{{.Name}}(dec *xdr.Decoder) ({{.Name}}, error) {
|
||||
discriminant, _, err := dec.DecodeInt()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
for ix := int32(0); ix < count; ix++ {
|
||||
var caseval {{.Name}}
|
||||
switch discriminant {
|
||||
{{range .Cases}}{{$casetype := printf "%v%v" $uname .CaseName}} case {{.DiscriminantVal}}:
|
||||
caseval, err = decode{{$casetype}}(dec)
|
||||
{{end}}
|
||||
default:
|
||||
err = fmt.Errorf("invalid parameter type %v", discriminant)
|
||||
}
|
||||
|
||||
return caseval, err
|
||||
}
|
||||
{{- end}}
|
||||
|
||||
// TODO: Generate these.
|
||||
func decodeTypedParam(dec *xdr.Decoder) (*TypedParam, error) {
|
||||
name, _, err := dec.DecodeString()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
ptype, _, err := dec.DecodeInt()
|
||||
val, err := decodeTypedParamValue(dec)
|
||||
return &TypedParam{name, val}, nil
|
||||
}
|
||||
|
||||
func decodeTypedParams(dec *xdr.Decoder) ([]TypedParam, error) {
|
||||
count, _, err := dec.DecodeInt()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var tpv TypedParamValue
|
||||
switch ptype {
|
||||
case 1: // TypedParamValueInt
|
||||
tpv, err = DecodeTypedParamValueInt(dec)
|
||||
case 2: // TypedParamValueUint
|
||||
tpv, err = DecodeTypedParamValueUint(dec)
|
||||
case 3: // TypedParamValueLlong
|
||||
tpv, err = DecodeTypedParamValueLlong(dec)
|
||||
case 4: // TypedParamValueUllong
|
||||
tpv, err = DecodeTypedParamValueUllong(dec)
|
||||
case 5: // TypedParamValueDouble
|
||||
tpv, err = DecodeTypedParamValueDouble(dec)
|
||||
case 6: // TypedParamValueBoolean
|
||||
tpv, err = DecodeTypedParamValueBoolean(dec)
|
||||
case 7: // TypedParamValueString
|
||||
tpv, err = DecodeTypedParamValueString(dec)
|
||||
default:
|
||||
err = fmt.Errorf("invalid parameter type %v", ptype)
|
||||
}
|
||||
|
||||
params := make([]TypedParam, count)
|
||||
for ix := int32(0); ix < count; ix++ {
|
||||
p, err := decodeTypedParam(dec)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
params[ix] = TypedParam{name, tpv}
|
||||
params[ix] = *p
|
||||
}
|
||||
|
||||
return params, nil
|
||||
@ -131,17 +130,16 @@ func (l *Libvirt) {{.Name}}({{range $ix, $arg := .Args}}{{if $ix}}, {{end}}{{.Na
|
||||
rdr := bytes.NewReader(r.Payload)
|
||||
dec := xdr.NewDecoder(rdr)
|
||||
{{range .Ret}} // {{.Name}}: {{.Type}}
|
||||
{{if eq .Type "[]TypedParam"}} // {{.Name}}
|
||||
r{{.Name}}, err = decodeTypedParams(dec)
|
||||
{{if eq .Type "[]TypedParam"}} r{{.Name}}, err = decodeTypedParams(dec)
|
||||
if err != nil {
|
||||
fmt.Println("error decoding typedparams")
|
||||
return
|
||||
}
|
||||
{{else}} _, err = dec.Decode(&r{{.Name}})
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
{{end}}{{end}}
|
||||
{{end}}
|
||||
{{end}}{{end}}{{end}}
|
||||
return
|
||||
}
|
||||
{{end}}
|
||||
|
@ -146,8 +146,12 @@ variable_array_declaration
|
||||
| type_specifier variable_ident '<' '>' { AddVariableArray($2.val, $1.val, "") }
|
||||
;
|
||||
|
||||
// while pointer_declarations may look like their familiar c-equivalents, in the
|
||||
// XDR language they actually declare "Optional-data". The simplest
|
||||
// representation to use for these is a variable-length array with a size of 1.
|
||||
// See the XDR spec for a more complete explanation of this.
|
||||
pointer_declaration
|
||||
: type_specifier '*' variable_ident { AddDeclaration($3.val, "*"+$1.val) }
|
||||
: type_specifier '*' variable_ident { AddVariableArray($3.val, $1.val, "1") }
|
||||
;
|
||||
|
||||
struct_definition
|
||||
|
574
libvirt.gen.go
574
libvirt.gen.go
File diff suppressed because it is too large
Load Diff
703
libvirt.go
703
libvirt.go
@ -52,17 +52,10 @@ type Libvirt struct {
|
||||
s uint32
|
||||
}
|
||||
|
||||
// Domain represents a domain as seen by libvirt.
|
||||
// type Domain struct {
|
||||
// Name string
|
||||
// UUID [constants.UUIDSize]byte
|
||||
// ID int
|
||||
// }
|
||||
|
||||
// DomainEvent represents a libvirt domain event.
|
||||
type DomainEvent struct {
|
||||
CallbackID uint32
|
||||
Domain Domain
|
||||
Domain NonnullDomain
|
||||
Event string
|
||||
Seconds uint64
|
||||
Microseconds uint32
|
||||
@ -70,19 +63,6 @@ type DomainEvent struct {
|
||||
Details []byte
|
||||
}
|
||||
|
||||
// Secret represents a secret managed by the libvirt daemon.
|
||||
// type Secret struct {
|
||||
// UUID [constants.UUIDSize]byte
|
||||
// UsageType SecretUsageType
|
||||
// UsageID string
|
||||
// }
|
||||
|
||||
// StoragePool represents a storage pool as seen by libvirt.
|
||||
// type StoragePool struct {
|
||||
// Name string
|
||||
// UUID [constants.UUIDSize]byte
|
||||
// }
|
||||
|
||||
// qemuError represents a QEMU process error.
|
||||
type qemuError struct {
|
||||
Error struct {
|
||||
@ -137,46 +117,6 @@ const (
|
||||
TypeParamLast
|
||||
)
|
||||
|
||||
// TypedParam represents libvirt's virTypedParameter, which is used to pass
|
||||
// typed parameters to libvirt functions. This is defined as an interface, and
|
||||
// implemented by TypedParam... concrete types.
|
||||
// type TypedParam interface {
|
||||
// Field() string
|
||||
// Value() interface{}
|
||||
// }
|
||||
|
||||
// TypedParamInt contains a 32-bit signed integer.
|
||||
// type TypedParamInt struct {
|
||||
// Fld string
|
||||
// PType int32
|
||||
// Padding [4]byte
|
||||
// Val int32
|
||||
// }
|
||||
|
||||
// Field returns the field name, a string name for the parameter.
|
||||
// func (tp *TypedParamInt) Field() string {
|
||||
// return tp.Fld
|
||||
// }
|
||||
|
||||
// Value returns the value for the typed parameter, as an empty interface.
|
||||
// func (tp *TypedParamInt) Value() interface{} {
|
||||
// return tp.Val
|
||||
// }
|
||||
|
||||
// NewTypedParamInt returns a TypedParam encoding for an int.
|
||||
// func NewTypedParamInt(name string, v int32) *TypedParamInt {
|
||||
// // Truncate the field name if it's longer than the limit.
|
||||
// if len(name) > constants.TypedParamFieldLength {
|
||||
// name = name[:constants.TypedParamFieldLength]
|
||||
// }
|
||||
// tp := TypedParamInt{
|
||||
// Fld: name,
|
||||
// PType: TypeParamInt,
|
||||
// Val: v,
|
||||
// }
|
||||
// return &tp
|
||||
// }
|
||||
|
||||
// TypedParamULongLong contains a 64-bit unsigned integer.
|
||||
type TypedParamULongLong struct {
|
||||
Fld string
|
||||
@ -506,27 +446,9 @@ const (
|
||||
DomainMemoryStatTagNr
|
||||
)
|
||||
|
||||
// DomainMemoryStat specifies memory stats of the domain
|
||||
// type DomainMemoryStat struct {
|
||||
// Tag DomainMemoryStatTag
|
||||
// Val uint64
|
||||
// }
|
||||
|
||||
// Capabilities returns an XML document describing the host's capabilties.
|
||||
func (l *Libvirt) Capabilities() ([]byte, error) {
|
||||
resp, err := l.request(constants.ProcConnectGetCapabilities, constants.Program, nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
caps, _, err := dec.DecodeString()
|
||||
|
||||
caps, err := l.ConnectGetCapabilities()
|
||||
return []byte(caps), err
|
||||
}
|
||||
|
||||
@ -555,118 +477,13 @@ func (l *Libvirt) Disconnect() error {
|
||||
}
|
||||
|
||||
// Domains returns a list of all domains managed by libvirt.
|
||||
func (l *Libvirt) Domains() ([]Domain, error) {
|
||||
func (l *Libvirt) Domains() ([]NonnullDomain, error) {
|
||||
// these are the flags as passed by `virsh`, defined in:
|
||||
// src/remote/remote_protocol.x # remote_connect_list_all_domains_args
|
||||
req := struct {
|
||||
NeedResults uint32
|
||||
Flags uint32
|
||||
}{
|
||||
NeedResults: 1,
|
||||
Flags: 3,
|
||||
}
|
||||
|
||||
buf, err := encode(&req)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcConnectListAllDomains, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
result := struct {
|
||||
Domains []Domain
|
||||
Count uint32
|
||||
}{}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
_, err = dec.Decode(&result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return result.Domains, nil
|
||||
domains, _, err := l.ConnectListAllDomains(1, 3)
|
||||
return domains, err
|
||||
}
|
||||
|
||||
// DomainCreateWithFlags starts specified domain with flags
|
||||
// func (l *Libvirt) DomainCreateWithFlags(dom string, flags DomainCreateFlags) error {
|
||||
// d, err := l.lookup(dom)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
// req := struct {
|
||||
// Domain Domain
|
||||
// Flags DomainCreateFlags
|
||||
// }{
|
||||
// Domain: *d,
|
||||
// Flags: flags,
|
||||
// }
|
||||
//
|
||||
// buf, err := encode(&req)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
// resp, err := l.request(constants.ProcDomainCreateWithFlags, constants.Program, &buf)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
// r := <-resp
|
||||
// if r.Status != StatusOK {
|
||||
// return decodeError(r.Payload)
|
||||
// }
|
||||
// return nil
|
||||
// }
|
||||
|
||||
// DomainMemoryStats returns memory stats of the domain managed by libvirt.
|
||||
// func (l *Libvirt) DomainMemoryStats(dom string) ([]DomainMemoryStat, error) {
|
||||
//
|
||||
// d, err := l.lookup(dom)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// req := struct {
|
||||
// Domain Domain
|
||||
// MaxStats uint32
|
||||
// Flags uint32
|
||||
// }{
|
||||
// Domain: *d,
|
||||
// MaxStats: 8,
|
||||
// Flags: 0,
|
||||
// }
|
||||
//
|
||||
// buf, err := encode(&req)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// resp, err := l.request(constants.ProcDomainMemoryStats, constants.Program, &buf)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// r := <-resp
|
||||
//
|
||||
// result := struct {
|
||||
// DomainMemoryStats []DomainMemoryStat
|
||||
// }{}
|
||||
//
|
||||
// dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
// _, err = dec.Decode(&result)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// return result.DomainMemoryStats, nil
|
||||
// }
|
||||
|
||||
// DomainState returns state of the domain managed by libvirt.
|
||||
func (l *Libvirt) DomainState(dom string) (DomainState, error) {
|
||||
d, err := l.lookup(dom)
|
||||
@ -674,41 +491,8 @@ func (l *Libvirt) DomainState(dom string) (DomainState, error) {
|
||||
return DomainStateNoState, err
|
||||
}
|
||||
|
||||
req := struct {
|
||||
Domain Domain
|
||||
Flags uint32
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: 0,
|
||||
}
|
||||
|
||||
buf, err := encode(&req)
|
||||
if err != nil {
|
||||
return DomainStateNoState, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainGetState, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return DomainStateNoState, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return DomainStateNoState, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
result := struct {
|
||||
State uint32
|
||||
Reason uint32
|
||||
}{}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
_, err = dec.Decode(&result)
|
||||
if err != nil {
|
||||
return DomainStateNoState, err
|
||||
}
|
||||
|
||||
return DomainState(result.State), nil
|
||||
state, _, err := l.DomainGetState(d, 0)
|
||||
return DomainState(state), err
|
||||
}
|
||||
|
||||
// Events streams domain events.
|
||||
@ -723,7 +507,7 @@ func (l *Libvirt) Events(dom string) (<-chan DomainEvent, error) {
|
||||
|
||||
payload := struct {
|
||||
Padding [4]byte
|
||||
Domain Domain
|
||||
Domain NonnullDomain
|
||||
Event [2]byte
|
||||
Flags [2]byte
|
||||
}{
|
||||
@ -793,39 +577,11 @@ func (l *Libvirt) Migrate(dom string, dest string, flags MigrateFlags) error {
|
||||
// and CookieIn. In testing both values are always set to 0 by virsh
|
||||
// and the source does not provide clear definitions of their purpose.
|
||||
// For now, using the same zero'd values as done by virsh will be Good Enough.
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Padding [4]byte
|
||||
DestinationURI string
|
||||
RemoteParameters uint32
|
||||
CookieIn uint32
|
||||
Flags MigrateFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Padding: [4]byte{0x0, 0x0, 0x0, 0x1},
|
||||
DestinationURI: dest,
|
||||
RemoteParameters: 0,
|
||||
CookieIn: 0,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
destURI := []string{dest}
|
||||
remoteParams := []TypedParam{}
|
||||
cookieIn := []byte{}
|
||||
_, err = l.DomainMigratePerform3Params(d, destURI, remoteParams, cookieIn, uint32(flags))
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainMigratePerform3Params,
|
||||
constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// MigrateSetMaxSpeed set the maximum migration bandwidth (in MiB/s) for a
|
||||
@ -837,33 +593,7 @@ func (l *Libvirt) MigrateSetMaxSpeed(dom string, speed int64) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Padding [4]byte
|
||||
Domain Domain
|
||||
Bandwidth int64
|
||||
Flags uint32
|
||||
}{
|
||||
Padding: [4]byte{0x0, 0x0, 0x1, 0x0},
|
||||
Domain: d,
|
||||
Bandwidth: speed,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainMigrateSetMaxSpeed, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainMigrateSetMaxSpeed(d, uint64(speed), 0)
|
||||
}
|
||||
|
||||
// Run executes the given QAPI command against a domain's QEMU instance.
|
||||
@ -876,7 +606,7 @@ func (l *Libvirt) Run(dom string, cmd []byte) ([]byte, error) {
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Domain NonnullDomain
|
||||
Command []byte
|
||||
Flags uint32
|
||||
}{
|
||||
@ -919,7 +649,7 @@ func (l *Libvirt) Run(dom string, cmd []byte) ([]byte, error) {
|
||||
}
|
||||
|
||||
// Secrets returns all secrets managed by the libvirt daemon.
|
||||
func (l *Libvirt) Secrets() ([]Secret, error) {
|
||||
func (l *Libvirt) Secrets() ([]NonnullSecret, error) {
|
||||
req := struct {
|
||||
NeedResults uint32
|
||||
Flags uint32
|
||||
@ -944,7 +674,7 @@ func (l *Libvirt) Secrets() ([]Secret, error) {
|
||||
}
|
||||
|
||||
result := struct {
|
||||
Secrets []Secret
|
||||
Secrets []NonnullSecret
|
||||
Count uint32
|
||||
}{}
|
||||
|
||||
@ -959,112 +689,15 @@ func (l *Libvirt) Secrets() ([]Secret, error) {
|
||||
|
||||
// StoragePool returns the storage pool associated with the provided name.
|
||||
// An error is returned if the requested storage pool is not found.
|
||||
func (l *Libvirt) StoragePool(name string) (StoragePool, error) {
|
||||
req := struct {
|
||||
Name string
|
||||
}{
|
||||
Name: name,
|
||||
}
|
||||
|
||||
buf, err := encode(&req)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcStoragePoolLookupByName, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
result := struct {
|
||||
Pool StoragePool
|
||||
}{}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
_, err = dec.Decode(&result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return result.Pool, nil
|
||||
func (l *Libvirt) StoragePool(name string) (NonnullStoragePool, error) {
|
||||
return l.StoragePoolLookupByName(name)
|
||||
}
|
||||
|
||||
// StoragePoolRefresh refreshes the storage pool specified by name.
|
||||
// func (l *Libvirt) StoragePoolRefresh(name string) error {
|
||||
// pool, err := l.StoragePool(name)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
//
|
||||
// req := struct {
|
||||
// Pool StoragePool
|
||||
// Flags uint32
|
||||
// }{
|
||||
// Pool: *pool,
|
||||
// Flags: 0, // unused per libvirt source, callers should pass 0
|
||||
// }
|
||||
//
|
||||
// buf, err := encode(&req)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
//
|
||||
// resp, err := l.request(constants.ProcStoragePoolRefresh, constants.Program, &buf)
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
//
|
||||
// r := <-resp
|
||||
// if r.Status != StatusOK {
|
||||
// return decodeError(r.Payload)
|
||||
// }
|
||||
//
|
||||
// return nil
|
||||
// }
|
||||
|
||||
// StoragePools returns a list of defined storage pools. Pools are filtered by
|
||||
// the provided flags. See StoragePools*.
|
||||
func (l *Libvirt) StoragePools(flags StoragePoolsFlags) ([]StoragePool, error) {
|
||||
req := struct {
|
||||
NeedResults uint32
|
||||
Flags StoragePoolsFlags
|
||||
}{
|
||||
NeedResults: 1,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&req)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcConnectListAllStoragePools, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
result := struct {
|
||||
Pools []StoragePool
|
||||
Count uint32
|
||||
}{}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
_, err = dec.Decode(&result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return result.Pools, nil
|
||||
func (l *Libvirt) StoragePools(flags StoragePoolsFlags) ([]NonnullStoragePool, error) {
|
||||
pools, _, err := l.ConnectListAllStoragePools(1, uint32(flags))
|
||||
return pools, err
|
||||
}
|
||||
|
||||
// Undefine undefines the domain specified by dom, e.g., 'prod-lb-01'.
|
||||
@ -1077,30 +710,7 @@ func (l *Libvirt) Undefine(dom string, flags UndefineFlags) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags UndefineFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainUndefineFlags, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainUndefineFlags(d, uint32(flags))
|
||||
}
|
||||
|
||||
// Destroy destroys the domain specified by dom, e.g., 'prod-lb-01'.
|
||||
@ -1113,30 +723,7 @@ func (l *Libvirt) Destroy(dom string, flags DestroyFlags) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags DestroyFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainDestroyFlags, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainDestroyFlags(d, uint32(flags))
|
||||
}
|
||||
|
||||
// XML returns a domain's raw XML definition, akin to `virsh dumpxml <domain>`.
|
||||
@ -1147,85 +734,19 @@ func (l *Libvirt) XML(dom string, flags DomainXMLFlags) ([]byte, error) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags DomainXMLFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainGetXMLDesc, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
pl := bytes.NewReader(r.Payload)
|
||||
dec := xdr.NewDecoder(pl)
|
||||
s, _, err := dec.DecodeString()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return []byte(s), nil
|
||||
xml, err := l.DomainGetXMLDesc(d, uint32(flags))
|
||||
return []byte(xml), err
|
||||
}
|
||||
|
||||
// DefineXML defines a domain, but does not start it.
|
||||
func (l *Libvirt) DefineXML(x []byte, flags DomainDefineXMLFlags) error {
|
||||
payload := struct {
|
||||
Domain []byte
|
||||
Flags DomainDefineXMLFlags
|
||||
}{
|
||||
Domain: x,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
_, err := l.DomainDefineXMLFlags(string(x), uint32(flags))
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainDefineXMLFlags, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Version returns the version of the libvirt daemon.
|
||||
func (l *Libvirt) Version() (string, error) {
|
||||
resp, err := l.request(constants.ProcConnectGetLibVersion, constants.Program, nil)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return "", decodeError(r.Payload)
|
||||
}
|
||||
|
||||
result := struct {
|
||||
Version uint64
|
||||
}{}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
_, err = dec.Decode(&result)
|
||||
ver, err := l.ConnectGetLibVersion()
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
@ -1233,11 +754,11 @@ func (l *Libvirt) Version() (string, error) {
|
||||
// The version is provided as an int following this formula:
|
||||
// version * 1,000,000 + minor * 1000 + micro
|
||||
// See src/libvirt-host.c # virConnectGetLibVersion
|
||||
major := result.Version / 1000000
|
||||
result.Version %= 1000000
|
||||
minor := result.Version / 1000
|
||||
result.Version %= 1000
|
||||
micro := result.Version
|
||||
major := ver / 1000000
|
||||
ver %= 1000000
|
||||
minor := ver / 1000
|
||||
ver %= 1000
|
||||
micro := ver
|
||||
|
||||
versionString := fmt.Sprintf("%d.%d.%d", major, minor, micro)
|
||||
return versionString, nil
|
||||
@ -1251,30 +772,7 @@ func (l *Libvirt) Shutdown(dom string, flags ShutdownFlags) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags ShutdownFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainShutdownFlags, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainShutdownFlags(d, uint32(flags))
|
||||
}
|
||||
|
||||
// Reboot reboots the domain. Note that the guest OS may ignore the request.
|
||||
@ -1285,30 +783,7 @@ func (l *Libvirt) Reboot(dom string, flags RebootFlags) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags RebootFlags
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: flags,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainReboot, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainReboot(d, uint32(flags))
|
||||
}
|
||||
|
||||
// Reset resets domain immediately without any guest OS shutdown
|
||||
@ -1318,30 +793,7 @@ func (l *Libvirt) Reset(dom string) error {
|
||||
return err
|
||||
}
|
||||
|
||||
payload := struct {
|
||||
Domain Domain
|
||||
Flags uint32
|
||||
}{
|
||||
Domain: d,
|
||||
Flags: 0,
|
||||
}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainReset, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return decodeError(r.Payload)
|
||||
}
|
||||
|
||||
return nil
|
||||
return l.DomainReset(d, 0)
|
||||
}
|
||||
|
||||
// BlockLimit contains a name and value pair for a Get/SetBlockIOTune limit. The
|
||||
@ -1404,7 +856,7 @@ func (l *Libvirt) SetBlockIOTune(dom string, disk string, limits ...BlockLimit)
|
||||
params[ix] = TypedParam{Field: limit.Name, Value: tpval}
|
||||
}
|
||||
|
||||
return l.DomainSetBlockIOTune(*d, disk, params, FlagDomainAffectLive)
|
||||
return l.DomainSetBlockIOTune(d, disk, params, FlagDomainAffectLive)
|
||||
}
|
||||
|
||||
// GetBlockIOTune returns a slice containing the current block I/O tunables for
|
||||
@ -1415,46 +867,12 @@ func (l *Libvirt) GetBlockIOTune(dom string, disk string) ([]BlockLimit, error)
|
||||
return nil, err
|
||||
}
|
||||
|
||||
lims, _, err := l.DomainGetBlockIOTune(*d, disk, 32, FlagTypedParamStringOkay)
|
||||
lims, _, err := l.DomainGetBlockIOTune(d, []string{disk}, 32, FlagTypedParamStringOkay)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
// payload := struct {
|
||||
// Domain Domain
|
||||
// Disk []string
|
||||
// ParamCount uint32
|
||||
// Flags DomainAffectFlags
|
||||
// }{
|
||||
// Domain: d,
|
||||
// Disk: []string{disk},
|
||||
// ParamCount: 32,
|
||||
// Flags: FlagTypedParamStringOkay,
|
||||
// }
|
||||
//
|
||||
// buf, err := encode(&payload)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// resp, err := l.request(constants.ProcDomainGetBlockIOTune, constants.Program, &buf)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// r := <-resp
|
||||
// if r.Status != StatusOK {
|
||||
// return nil, decodeError(r.Payload)
|
||||
// }
|
||||
|
||||
var limits []BlockLimit
|
||||
// rdr := bytes.NewReader(r.Payload)
|
||||
// dec := xdr.NewDecoder(rdr)
|
||||
|
||||
// find out how many params were returned
|
||||
// paramCount, _, err := dec.DecodeInt()
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
|
||||
// now decode each of the returned TypedParams. To do this we read the field
|
||||
// name and type, then use the type information to decode the value.
|
||||
@ -1468,73 +886,40 @@ func (l *Libvirt) GetBlockIOTune(dom string, disk string) ([]BlockLimit, error)
|
||||
limits = append(limits, l)
|
||||
}
|
||||
|
||||
// for param := int32(0); param < paramCount; param++ {
|
||||
// // Get the field name
|
||||
// name, _, err := dec.DecodeString()
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
// // ...and the type
|
||||
// ptype, _, err := dec.DecodeInt()
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
//
|
||||
// // Now we can read the actual value.
|
||||
// switch ptype {
|
||||
// case TypeParamULLong:
|
||||
// var val uint64
|
||||
// _, err = dec.Decode(&val)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
// lim := BlockLimit{name, val}
|
||||
// limits = append(limits, lim)
|
||||
// case TypeParamString:
|
||||
// var val string
|
||||
// _, err = dec.Decode(&val)
|
||||
// if err != nil {
|
||||
// return nil, err
|
||||
// }
|
||||
// // This routine doesn't currently return strings. As of libvirt 3+,
|
||||
// // there's one string here, `group_name`.
|
||||
// }
|
||||
// }
|
||||
|
||||
return limits, nil
|
||||
}
|
||||
|
||||
// lookup returns a domain as seen by libvirt.
|
||||
func (l *Libvirt) lookup(name string) (Domain, error) {
|
||||
func (l *Libvirt) lookup(name string) (NonnullDomain, error) {
|
||||
var d NonnullDomain
|
||||
payload := struct {
|
||||
Name string
|
||||
}{name}
|
||||
|
||||
buf, err := encode(&payload)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return d, err
|
||||
}
|
||||
|
||||
resp, err := l.request(constants.ProcDomainLookupByName, constants.Program, &buf)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return d, err
|
||||
}
|
||||
|
||||
r := <-resp
|
||||
if r.Status != StatusOK {
|
||||
return nil, decodeError(r.Payload)
|
||||
return d, decodeError(r.Payload)
|
||||
}
|
||||
|
||||
dec := xdr.NewDecoder(bytes.NewReader(r.Payload))
|
||||
|
||||
// var d Domain
|
||||
var d NonnullDomain
|
||||
_, err = dec.Decode(&d)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return d, err
|
||||
}
|
||||
|
||||
return &d, nil
|
||||
return d, nil
|
||||
}
|
||||
|
||||
// getQEMUError checks the provided response for QEMU process errors.
|
||||
|
@ -153,7 +153,7 @@ func TestDomainMemoryStats(t *testing.T) {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
gotDomainMemoryStats, err := l.DomainMemoryStats(*d, 8, 0)
|
||||
gotDomainMemoryStats, err := l.DomainMemoryStats(d, 8, 0)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
@ -361,7 +361,7 @@ func TestStoragePoolRefresh(t *testing.T) {
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
err = l.StoragePoolRefresh(*pool, 0)
|
||||
err = l.StoragePoolRefresh(pool, 0)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
@ -422,7 +422,7 @@ func TestDomainCreateWithFlags(t *testing.T) {
|
||||
t.Fatalf("failed to lookup domain: %v", err)
|
||||
}
|
||||
var flags uint32
|
||||
if _, err := l.DomainCreateWithFlags(*d, flags); err != nil {
|
||||
if _, err := l.DomainCreateWithFlags(d, flags); err != nil {
|
||||
t.Fatalf("unexpected create error: %v", err)
|
||||
}
|
||||
}
|
||||
|
@ -340,10 +340,6 @@ func TestLookup(t *testing.T) {
|
||||
t.Error(err)
|
||||
}
|
||||
|
||||
if d == nil {
|
||||
t.Error("nil domain returned")
|
||||
}
|
||||
|
||||
if d.Name != name {
|
||||
t.Errorf("expected domain %s, got %s", name, d.Name)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user