signal11/hidapi — Issue #24: Linux libusb: make sure <wchar.h> is included to stop segfaults in hid_free_enumeration()
Author: mrpippy
Created: 2011-10-10 17:53:42+00:00
State: open

Hi Alan,

While testing our app (based on the Microchip HIDBootloader) on 64-bit Linux (Ubuntu 9.04), I was consistently getting segfaults while programming a device. Here is the gdb log (note that my code still periodically polls for devices with hid_enumerate() even when device I/O is in progress):

```
Sending program data packet with address: 0x3448

Program received signal SIGSEGV, Segmentation fault.
[Switching to Thread 0x7fb605397750 (LWP 5747)]
0x00007fb602f1d225 in free () from /lib/libc.so.6
(gdb) bt
#0 0x00007fb602f1d225 in free () from /lib/libc.so.6
#1 0x000000000042a099 in hid_free_enumeration (devs=0x7fb5ec0011b0) at linux/hid-libusb.c:576
…
(gdb) up
#1 0x000000000042a099 in hid_free_enumeration (devs=0x7fb5ec0011b0) at linux/hid-libusb.c:576
576	free(d->manufacturer_string);
(gdb) print *d
$2 = {path = 0x7fb5ec000f60 "0\020", vendor_id = 8279, product_id = 1,
serial_number = 0x0, release_number = 2, manufacturer_string = 0xffffffffec000b50,
product_string = 0x0, usage_page = 0, usage = 0, interface_number = 0, next = 0x0}
```
This is very odd: manufacturer_string is set directly from wcsdup(), and hid_enumerate()/hid_free_enumeration() have run hundreds of times without crashing since the program was started. Either wcsdup() is bad (unlikely), or there's memory corruption somewhere.

I figured I would try cleaning up some compiler warnings, like this one:
```
linux/hid-libusb.c:364: warning: implicit declaration of function 'wcsdup'
linux/hid-libusb.c:364: warning: assignment makes pointer from integer without cast
```
After adding #define _GNU_SOURCE and #include \ to get rid of that warning I tested again, and **it doesn't crash**. I've never seen a missing prototype cause such a weird crash but I took a look at the assembly, and it does make a difference. Left side is without wchar.h included, right side is with:

![with/without wchar.h](http://i.imgur.com/HMJAT.png)

I found this problem when building on 64-bit Ubuntu 9.04, but newer distros like Ubuntu 10.04 (which I did development on) seem to have wchar.h included automatically. This probably explains why no one noticed the bug until now. Here's the change I made:

```

Index: hid-libusb.c
===================================================================
--- hid-libusb.c	(revision 5169)
+++ hid-libusb.c	(working copy)
@@ -22,6 +22,8 @@
http://github.com/signal11/hidapi .
********************************************************/

+#define _GNU_SOURCE
+
/* C */
#include
#include
@@ -38,6 +40,7 @@
#include
#include
#include
+#include

/* GNU / LibUSB */
#include "libusb.h"
```