forked from gotmc/libusb
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcontext.go
More file actions
120 lines (108 loc) · 3.51 KB
/
Copy pathcontext.go
File metadata and controls
120 lines (108 loc) · 3.51 KB
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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
// Copyright (c) 2015-2017 The libusb developers. All rights reserved.
// Project site: https://github.com/gotmc/libusb
// Use of this source code is governed by a MIT-style license that
// can be found in the LICENSE.txt file for the project.
package libusb
// #cgo pkg-config: libusb-1.0
// #include <libusb.h>
import "C"
import (
"fmt"
"reflect"
"unsafe"
)
type logLevel int
// Log message levels
//
// http://bit.ly/enum_libusb_log_level
const (
LogLevelNone logLevel = C.LIBUSB_LOG_LEVEL_NONE
LogLevelError logLevel = C.LIBUSB_LOG_LEVEL_ERROR
LogLevelWarning logLevel = C.LIBUSB_LOG_LEVEL_WARNING
LogLevelInfo logLevel = C.LIBUSB_LOG_LEVEL_INFO
LogLevelDebug logLevel = C.LIBUSB_LOG_LEVEL_DEBUG
)
var logLevels = map[logLevel]string{
LogLevelNone: "No messages ever printed by the library (default)",
LogLevelError: "Error messages are printed to stderr",
LogLevelWarning: "Warning and error messages are printed to stderr",
LogLevelInfo: "Informational messages are printed to stdout, warning and error messages are printed to stderr",
LogLevelDebug: "Debug and informational messages are printed to stdout, warnings and errors to stderr",
}
func (level logLevel) String() string {
return logLevels[level]
}
// Context represents a libusb session/context.
type Context struct {
libusbContext *C.libusb_context
LogLevel logLevel
}
// Init intializes a new libusb session/context by creating a new Context and
// returning a pointer to that Context.
func Init() (*Context, error) {
newContext := &Context{
LogLevel: LogLevelNone,
}
errnum := C.libusb_init(&newContext.libusbContext)
if errnum != 0 {
return nil, fmt.Errorf(
"Failed to initialize new libusb context. Received error %d", errnum)
}
return newContext, nil
}
// Exit deinitializes the libusb session/context.
func (ctx *Context) Exit() error {
C.libusb_exit(ctx.libusbContext)
ctx.libusbContext = nil
return nil
}
// SetDebug sets the log message verbosity.
func (ctx *Context) SetDebug(level logLevel) {
C.libusb_set_debug(ctx.libusbContext, C.int(level))
ctx.LogLevel = level
return
}
// GetDeviceList returns an array of devices for the context.
func (ctx *Context) GetDeviceList() ([]*Device, error) {
var devices []*Device
var list **C.libusb_device
const unrefDevices = 1
numDevicesFound := int(C.libusb_get_device_list(ctx.libusbContext, &list))
if numDevicesFound < 0 {
return nil, ErrorCode(numDevicesFound)
}
defer C.libusb_free_device_list(list, unrefDevices)
var libusbDevices []*C.libusb_device
*(*reflect.SliceHeader)(unsafe.Pointer(&libusbDevices)) = reflect.SliceHeader{
Data: uintptr(unsafe.Pointer(list)),
Len: numDevicesFound,
Cap: numDevicesFound,
}
for _, thisLibusbDevice := range libusbDevices {
thisDevice := Device{
libusbDevice: thisLibusbDevice,
}
devices = append(devices, &thisDevice)
}
return devices, nil
}
// OpenDeviceWithVendorProduct opens a USB device using the VendorID and
// productID and then returns a device handle.
func (ctx *Context) OpenDeviceWithVendorProduct(
vendorID uint16,
productID uint16,
) (*Device, *DeviceHandle, error) {
var deviceHandle DeviceHandle
deviceHandle.libusbDeviceHandle = C.libusb_open_device_with_vid_pid(
ctx.libusbContext, C.uint16_t(vendorID), C.uint16_t(productID))
if deviceHandle.libusbDeviceHandle == nil {
return nil, nil, fmt.Errorf("Could not open USB device %v:%v",
vendorID,
productID,
)
}
device := Device{
libusbDevice: C.libusb_get_device(deviceHandle.libusbDeviceHandle),
}
return &device, &deviceHandle, nil
}