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
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
|
--- daemons/hw_hiddev.c.orig 2011-03-25 22:28:18 UTC
+++ daemons/hw_hiddev.c
@@ -22,9 +22,17 @@
#include <stdio.h>
#include <sys/fcntl.h>
#include <sys/ioctl.h>
+#include <errno.h>
+#ifdef HAVE_USBHID_H
+#include <usbhid.h>
+#endif
+#ifdef HAVE_LINUX_TYPES_H
#include <linux/types.h>
+#endif
+#ifdef HAVE_LINUX_HIDDEV_H
#include <linux/hiddev.h>
+#endif
#include "hardware.h"
#include "ir_remote.h"
@@ -135,6 +143,7 @@ struct hardware hw_sb0540 = {
};
#endif
+#ifdef HAVE_LINUX_HIDDEV_H
/* Apple Mac mini USB IR Receiver */
struct hardware hw_macmini = {
"/dev/usb/hiddev0", /* "device" */
@@ -152,6 +161,7 @@ struct hardware hw_macmini = {
NULL, /* readdata */
"macmini" /* name */
};
+#endif
#ifdef HAVE_LINUX_HIDDEV_FLAG_UREF
/* Samsung USB IR Receiver */
@@ -191,7 +201,11 @@ int hiddev_init()
logprintf(LOG_INFO, "initializing '%s'", hw.device);
if ((hw.fd = open(hw.device, O_RDONLY)) < 0) {
- logprintf(LOG_ERR, "unable to open '%s'", hw.device);
+ logprintf(LOG_ERR,
+ "unable to open '%s': %s (%d)",
+ hw.device,
+ strerror (errno),
+ errno );
return 0;
}
@@ -235,8 +249,40 @@ int hiddev_decode(struct ir_remote *remote, ir_code *
return 1;
}
+/*
+ * Read a record from the remote control, decode it and return a
+ * string of the form
+ *
+ * 00010046000042fe 00 start DVICO_MCE
+ *
+ * The first field is the complete event. The second appears to tbe
+ * the repeat flag, the third the name of the the key, and the fourth
+ * some kind of identification. I have no idea how much of this is
+ * used.
+ *
+ * The code below works around the extremely fast repeat holdoff on
+ * the DVICO control. It's difficult to press a key without it
+ * repeating. We work around this by ignoring the first 3 repeats.
+ *
+ * For FreeBSD, we have the problem of a different HID interface.
+ * Linux returns a struct hiddev_event, while FreeBSD returns data
+ * with no specific structure. Part of the Linux structure is the
+ * hid, which FreeBSD doesn't seem to supply. Work around these
+ * issues by reading the FreeBSD data and packing it into a Linux
+ * struct hiddev_event. This requires lying about the hid.
+ */
+
char *hiddev_rec(struct ir_remote *remotes)
{
+#ifdef __FreeBSD__
+#define HIDRECLEN 3 /* get this from hid_init() */
+ char inbuf [HIDRECLEN];
+ struct hiddev_event
+ {
+ unsigned hid;
+ int32_t value;
+ };
+#endif
struct hiddev_event event;
struct hiddev_event asus_events[8];
int rd;
@@ -253,9 +299,41 @@ char *hiddev_rec(struct ir_remote *remotes)
last = end;
gettimeofday(&start, NULL);
+#ifdef __FreeBSD__
+ if (!strcmp(hw.name, "dvico")) {
+ rd = read(hw.fd, inbuf, sizeof inbuf);
+ if (rd != sizeof inbuf) {
+ logprintf(LOG_ERR,
+ "Really read %d bytes from '%s', expected %d",
+ rd,
+ hw.device,
+ sizeof inbuf );
+ return 0;
+ }
+ event.hid = 0x10046; /* XXX not in FreeBSD */
+ event.value = * (int16_t *) (&inbuf [1]);
+ } else {
+ rd = read(hw.fd, &event.value, sizeof event.value);
+ if (rd != sizeof event.value) {
+ logprintf(LOG_ERR,
+ "Really read %d bytes from '%s', expected %d",
+ rd,
+ hw.device,
+ sizeof event.value );
+ return 0;
+ }
+ event.hid = 0x10046; /* XXX not in FreeBSD */
+ }
+ rd = sizeof event; /* to make code happy */
+#else
rd = read(hw.fd, &event, sizeof event);
+#endif
if (rd != sizeof event) {
- logprintf(LOG_ERR, "error reading '%s'", hw.device);
+ logprintf(LOG_ERR,
+ "Read %d bytes from '%s', expected %d",
+ rd,
+ hw.device,
+ sizeof event );
logperror(LOG_ERR, NULL);
hiddev_deinit();
return 0;
@@ -515,6 +593,7 @@ char *sb0540_rec(struct ir_remote *remotes)
}
#endif
+#ifdef HAVE_LINUX_HIDDEV_H
/*
* Apple Mac mini USB IR Receiver specific code.
*
@@ -566,6 +645,7 @@ char *macmini_rec(struct ir_remote *remotes)
return decode_all(remotes);
}
+#endif
/*
* Samsung/Cypress USB IR Receiver specific code
|