Skip to content

Commit 3ef8258

Browse files
wizgravYannis Grv
authored andcommitted
Kinect for Windows and Xbox 360 Model 1473 support
This patch does auto detection of all three models and disables motor subdevice for the 2 newer ones. It also adds a function to test for the presence of the motor and audio devices on newer models. Signed-off-by: Yannis Gravezas <[email protected]> (wizgrav)
1 parent ec04a63 commit 3ef8258

File tree

8 files changed

+75
-9
lines changed

8 files changed

+75
-9
lines changed

include/libfreenect.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -302,6 +302,15 @@ FREENECTAPI int freenect_supported_subdevices(void);
302302
*/
303303
FREENECTAPI void freenect_select_subdevices(freenect_context *ctx, freenect_device_flags subdevs);
304304

305+
/**
306+
* Returns the devices that are enabled after calls to freenect_open_device()
307+
* On newer kinects the motor and audio are automatically disabled for now
308+
*
309+
* @param ctx Context to set future subdevice selection for
310+
* @return Flags representing the subdevices that were actually opened (see freenect_device_flags)
311+
*/
312+
FREENECTAPI freenect_device_flags freenect_enabled_subdevices(freenect_context *ctx);
313+
305314
/**
306315
* Opens a kinect device via a context. Index specifies the index of
307316
* the device on the current state of the bus. Bus resets may cause

platform/windows/libusb10emu/libusb-1.0/libusb.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ int libusb_get_string_descriptor(libusb_device_handle *dev_handle, uint8_t desc_
7777
int libusb_get_string_descriptor_ascii(libusb_device_handle *dev_handle, uint8_t desc_index, unsigned char *data, int length);
7878

7979
int libusb_set_configuration(libusb_device_handle *dev, int configuration);
80+
int libusb_set_interface_alt_setting(libusb_device_handle *dev,int interface_number,int alternate_setting);
8081
int libusb_claim_interface(libusb_device_handle* dev, int interface_number);
8182
int libusb_release_interface(libusb_device_handle* dev, int interface_number);
8283

platform/windows/libusb10emu/libusb-1.0/libusbemu.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -302,6 +302,17 @@ int libusb_set_configuration(libusb_device_handle *dev, int configuration)
302302
return 0;
303303
}
304304

305+
int libusb_set_interface_alt_setting(libusb_device_handle *dev, int interface_number,int alternate_setting){
306+
RAIIMutex lock (dev->dev->ctx->mutex);
307+
if (0 != usb_set_altinterface(dev->handle, alternate_setting))
308+
{
309+
LIBUSBEMU_ERROR_LIBUSBWIN32();
310+
return(LIBUSB_ERROR_OTHER);
311+
}
312+
313+
return(0);
314+
}
315+
305316
int libusb_claim_interface(libusb_device_handle* dev, int interface_number)
306317
{
307318
RAIIMutex lock (dev->dev->ctx->mutex);

src/cameras.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -904,9 +904,9 @@ static int freenect_fetch_zero_plane_info(freenect_device *dev)
904904
uint16_t cmd[5] = {0}; // Offset is the only field in this command, and it's 0
905905

906906
int res;
907-
res = send_cmd(dev, 0x04, cmd, 10, reply, 322); //OPCODE_GET_FIXED_PARAMS = 4,
908-
if (res != 322) {
909-
FN_ERROR("freenect_fetch_zero_plane_info: send_cmd read %d bytes (expected 322)\n", res);
907+
res = send_cmd(dev, 0x04, cmd, 10, reply, ctx->zero_plane_res); //OPCODE_GET_FIXED_PARAMS = 4,
908+
if (res != ctx->zero_plane_res) {
909+
FN_ERROR("freenect_fetch_zero_plane_info: send_cmd read %d bytes (expected %d)\n", res,ctx->zero_plane_res);
910910
return -1;
911911
}
912912

src/core.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -148,6 +148,10 @@ FREENECTAPI void freenect_select_subdevices(freenect_context *ctx, freenect_devi
148148
));
149149
}
150150

151+
FREENECTAPI freenect_device_flags freenect_enabled_subdevices(freenect_context *ctx) {
152+
return ctx->enabled_subdevices;
153+
}
154+
151155
FREENECTAPI int freenect_open_device(freenect_context *ctx, freenect_device **dev, int index)
152156
{
153157
int res;

src/freenect_internal.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ struct _freenect_context {
5252
fnusb_ctx usb;
5353
freenect_device_flags enabled_subdevices;
5454
freenect_device *first;
55+
int zero_plane_res;
5556
};
5657

5758
#define LL_FATAL FREENECT_LOG_FATAL
@@ -131,6 +132,8 @@ static inline int32_t fn_le32s(int32_t s)
131132
#define PID_NUI_AUDIO 0x02ad
132133
#define PID_NUI_CAMERA 0x02ae
133134
#define PID_NUI_MOTOR 0x02b0
135+
#define PID_K4W_CAMERA 0x02bf
136+
#define PID_K4W_AUDIO 0x02be
134137

135138
typedef struct {
136139
int running;

src/tilt.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@ freenect_raw_tilt_state* freenect_get_tilt_state(freenect_device *dev)
4747
int freenect_update_tilt_state(freenect_device *dev)
4848
{
4949
freenect_context *ctx = dev->parent;
50+
if(!(ctx->enabled_subdevices & FREENECT_DEVICE_MOTOR))
51+
return 0;
5052
uint8_t buf[10];
5153
uint16_t ux, uy, uz;
5254
int ret = fnusb_control(&dev->usb_motor, 0xC0, 0x32, 0x0, 0x0, buf, 10);
@@ -70,6 +72,9 @@ int freenect_update_tilt_state(freenect_device *dev)
7072

7173
int freenect_set_tilt_degs(freenect_device *dev, double angle)
7274
{
75+
freenect_context *ctx = dev->parent;
76+
if(!(ctx->enabled_subdevices & FREENECT_DEVICE_MOTOR))
77+
return 0;
7378
int ret;
7479
uint8_t empty[0x1];
7580

@@ -82,6 +87,9 @@ int freenect_set_tilt_degs(freenect_device *dev, double angle)
8287

8388
int freenect_set_led(freenect_device *dev, freenect_led_options option)
8489
{
90+
freenect_context *ctx = dev->parent;
91+
if(!(ctx->enabled_subdevices & FREENECT_DEVICE_MOTOR))
92+
return 0;
8593
int ret;
8694
uint8_t empty[0x1];
8795
ret = fnusb_control(&dev->usb_motor, 0x40, 0x06, (uint16_t)option, 0x0, empty, 0x0);

src/usb_libusb10.c

Lines changed: 36 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ FN_INTERNAL int fnusb_num_devices(fnusb_ctx *ctx)
4747
int r = libusb_get_device_descriptor (devs[i], &desc);
4848
if (r < 0)
4949
continue;
50-
if (desc.idVendor == VID_MICROSOFT && desc.idProduct == PID_NUI_CAMERA)
50+
if (desc.idVendor == VID_MICROSOFT && (desc.idProduct == PID_NUI_CAMERA || desc.idProduct == PID_K4W_CAMERA))
5151
nr++;
5252
}
5353
libusb_free_device_list (devs, 1);
@@ -76,7 +76,7 @@ FN_INTERNAL int fnusb_list_device_attributes(fnusb_ctx *ctx, struct freenect_dev
7676
int r = libusb_get_device_descriptor (devs[i], &desc);
7777
if (r < 0)
7878
continue;
79-
if (desc.idVendor == VID_MICROSOFT && desc.idProduct == PID_NUI_CAMERA) {
79+
if (desc.idVendor == VID_MICROSOFT && (desc.idProduct == PID_NUI_CAMERA || desc.idProduct == PID_K4W_CAMERA)) {
8080
// Verify that a serial number exists to query. If not, don't touch the device.
8181
if (desc.iSerialNumber == 0) {
8282
continue;
@@ -188,9 +188,9 @@ FN_INTERNAL int fnusb_open_subdevices(freenect_device *dev, int index)
188188

189189
if (desc.idVendor != VID_MICROSOFT)
190190
continue;
191-
191+
res = 0;
192192
// Search for the camera
193-
if ((ctx->enabled_subdevices & FREENECT_DEVICE_CAMERA) && !dev->usb_cam.dev && desc.idProduct == PID_NUI_CAMERA) {
193+
if ((ctx->enabled_subdevices & FREENECT_DEVICE_CAMERA) && !dev->usb_cam.dev && (desc.idProduct == PID_NUI_CAMERA || desc.idProduct == PID_K4W_CAMERA)) {
194194
// If the index given by the user matches our camera index
195195
if (nr_cam == index) {
196196
res = libusb_open (devs[i], &dev->usb_cam.dev);
@@ -199,6 +199,15 @@ FN_INTERNAL int fnusb_open_subdevices(freenect_device *dev, int index)
199199
dev->usb_cam.dev = NULL;
200200
break;
201201
}
202+
if(desc.idProduct == PID_K4W_CAMERA || desc.bcdDevice != fn_le32(267)){
203+
/* Not the old kinect so we only set up the camera*/
204+
ctx->enabled_subdevices = FREENECT_DEVICE_CAMERA;
205+
ctx->zero_plane_res = 334;
206+
}else{
207+
/* The good old kinect that tilts and tweets */
208+
ctx->zero_plane_res = 322;
209+
}
210+
202211
#ifndef _WIN32
203212
// Detach an existing kernel driver for the device
204213
res = libusb_kernel_driver_active(dev->usb_cam.dev, 0);
@@ -219,12 +228,33 @@ FN_INTERNAL int fnusb_open_subdevices(freenect_device *dev, int index)
219228
dev->usb_cam.dev = NULL;
220229
break;
221230
}
231+
if(desc.idProduct == PID_K4W_CAMERA){
232+
res = libusb_set_interface_alt_setting(dev->usb_cam.dev, 0, 1);
233+
if (res != 0) {
234+
FN_ERROR("Failed to set alternate interface #1 for K4W: %d\n", res);
235+
libusb_close(dev->usb_cam.dev);
236+
dev->usb_cam.dev = NULL;
237+
break;
238+
}
239+
240+
}
222241
} else {
223242
nr_cam++;
224243
}
225244
}
226-
245+
}
246+
247+
if(ctx->enabled_subdevices == FREENECT_DEVICE_CAMERA || res < 0) cnt = 0;
248+
227249
// Search for the motor
250+
251+
for (i = 0; i < cnt; i++) {
252+
int r = libusb_get_device_descriptor (devs[i], &desc);
253+
if (r < 0)
254+
continue;
255+
256+
if (desc.idVendor != VID_MICROSOFT)
257+
continue;
228258
if ((ctx->enabled_subdevices & FREENECT_DEVICE_MOTOR) && !dev->usb_motor.dev && desc.idProduct == PID_NUI_MOTOR) {
229259
// If the index given by the user matches our camera index
230260
if (nr_mot == index) {
@@ -249,7 +279,7 @@ FN_INTERNAL int fnusb_open_subdevices(freenect_device *dev, int index)
249279
#ifdef BUILD_AUDIO
250280
// TODO: check that the firmware has already been loaded; if not, upload firmware.
251281
// Search for the audio
252-
if ((ctx->enabled_subdevices & FREENECT_DEVICE_AUDIO) && !dev->usb_audio.dev && desc.idProduct == PID_NUI_AUDIO) {
282+
if ((ctx->enabled_subdevices & FREENECT_DEVICE_AUDIO) && !dev->usb_audio.dev && (desc.idProduct == PID_NUI_AUDIO || desc.idProduct == PID_K4W_AUDIO)) {
253283
// If the index given by the user matches our audio index
254284
if (nr_audio == index) {
255285
res = libusb_open (devs[i], &dev->usb_audio.dev);

0 commit comments

Comments
 (0)