ReactOS  0.4.15-dev-3719-g41b8715
joystick_osx.c
Go to the documentation of this file.
1 /* DirectInput Joystick device for Mac OS/X
2  *
3  * Copyright 1998 Marcus Meissner
4  * Copyright 1998,1999 Lionel Ulmer
5  * Copyright 2000-2001 TransGaming Technologies Inc.
6  * Copyright 2009 CodeWeavers, Aric Stewart
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21  */
22 
23 #include "config.h"
24 #include "wine/port.h"
25 
26 #if defined(HAVE_IOKIT_HID_IOHIDLIB_H)
27 #define DWORD UInt32
28 #define LPDWORD UInt32*
29 #define LONG SInt32
30 #define LPLONG SInt32*
31 #define E_PENDING __carbon_E_PENDING
32 #define ULONG __carbon_ULONG
33 #define E_INVALIDARG __carbon_E_INVALIDARG
34 #define E_OUTOFMEMORY __carbon_E_OUTOFMEMORY
35 #define E_HANDLE __carbon_E_HANDLE
36 #define E_ACCESSDENIED __carbon_E_ACCESSDENIED
37 #define E_UNEXPECTED __carbon_E_UNEXPECTED
38 #define E_FAIL __carbon_E_FAIL
39 #define E_ABORT __carbon_E_ABORT
40 #define E_POINTER __carbon_E_POINTER
41 #define E_NOINTERFACE __carbon_E_NOINTERFACE
42 #define E_NOTIMPL __carbon_E_NOTIMPL
43 #define S_FALSE __carbon_S_FALSE
44 #define S_OK __carbon_S_OK
45 #define HRESULT_FACILITY __carbon_HRESULT_FACILITY
46 #define IS_ERROR __carbon_IS_ERROR
47 #define FAILED __carbon_FAILED
48 #define SUCCEEDED __carbon_SUCCEEDED
49 #define MAKE_HRESULT __carbon_MAKE_HRESULT
50 #define HRESULT __carbon_HRESULT
51 #define STDMETHODCALLTYPE __carbon_STDMETHODCALLTYPE
52 #include <IOKit/IOKitLib.h>
53 #include <IOKit/hid/IOHIDLib.h>
54 #include <ForceFeedback/ForceFeedback.h>
55 #undef ULONG
56 #undef E_INVALIDARG
57 #undef E_OUTOFMEMORY
58 #undef E_HANDLE
59 #undef E_ACCESSDENIED
60 #undef E_UNEXPECTED
61 #undef E_FAIL
62 #undef E_ABORT
63 #undef E_POINTER
64 #undef E_NOINTERFACE
65 #undef E_NOTIMPL
66 #undef S_FALSE
67 #undef S_OK
68 #undef HRESULT_FACILITY
69 #undef IS_ERROR
70 #undef FAILED
71 #undef SUCCEEDED
72 #undef MAKE_HRESULT
73 #undef HRESULT
74 #undef STDMETHODCALLTYPE
75 #undef DWORD
76 #undef LPDWORD
77 #undef LONG
78 #undef LPLONG
79 #undef E_PENDING
80 #endif /* HAVE_IOKIT_HID_IOHIDLIB_H */
81 
82 #include "wine/debug.h"
83 #include "wine/unicode.h"
84 #include "windef.h"
85 #include "winbase.h"
86 #include "winerror.h"
87 #include "winreg.h"
88 #include "devguid.h"
89 #include "dinput.h"
90 
91 #include "dinput_private.h"
92 #include "device_private.h"
93 #include "joystick_private.h"
94 
95 #ifdef HAVE_IOHIDMANAGERCREATE
96 
98 
99 static CFMutableArrayRef device_main_elements = NULL;
100 
101 typedef struct JoystickImpl JoystickImpl;
102 static const IDirectInputDevice8AVtbl JoystickAvt;
103 static const IDirectInputDevice8WVtbl JoystickWvt;
104 
105 struct JoystickImpl
106 {
108 
109  /* osx private */
110  int id;
111  CFArrayRef elements;
112  ObjProps **propmap;
113  FFDeviceObjectReference ff;
114  struct list effects;
115 };
116 
117 static inline JoystickImpl *impl_from_IDirectInputDevice8A(IDirectInputDevice8A *iface)
118 {
119  return CONTAINING_RECORD(CONTAINING_RECORD(CONTAINING_RECORD(iface, IDirectInputDeviceImpl, IDirectInputDevice8A_iface),
120  JoystickGenericImpl, base), JoystickImpl, generic);
121 }
122 static inline JoystickImpl *impl_from_IDirectInputDevice8W(IDirectInputDevice8W *iface)
123 {
124  return CONTAINING_RECORD(CONTAINING_RECORD(CONTAINING_RECORD(iface, IDirectInputDeviceImpl, IDirectInputDevice8W_iface),
125  JoystickGenericImpl, base), JoystickImpl, generic);
126 }
127 
128 static inline IDirectInputDevice8W *IDirectInputDevice8W_from_impl(JoystickImpl *This)
129 {
130  return &This->generic.base.IDirectInputDevice8W_iface;
131 }
132 
133 typedef struct _EffectImpl {
134  IDirectInputEffect IDirectInputEffect_iface;
135  LONG ref;
136 
137  JoystickImpl *device;
138  FFEffectObjectReference effect;
139  GUID guid;
140 
141  struct list entry;
142 } EffectImpl;
143 
144 static EffectImpl *impl_from_IDirectInputEffect(IDirectInputEffect *iface)
145 {
146  return CONTAINING_RECORD(iface, EffectImpl, IDirectInputEffect_iface);
147 }
148 
149 static const IDirectInputEffectVtbl EffectVtbl;
150 
151 static const GUID DInput_Wine_OsX_Joystick_GUID = { /* 59CAD8F6-E617-41E2-8EB7-47B23EEEDC5A */
152  0x59CAD8F6, 0xE617, 0x41E2, {0x8E, 0xB7, 0x47, 0xB2, 0x3E, 0xEE, 0xDC, 0x5A}
153 };
154 
155 static HRESULT osx_to_win32_hresult(HRESULT in)
156 {
157  /* OSX returns 16-bit COM runtime errors, which we should
158  * convert to win32 */
159  switch(in){
160  case 0x80000001:
161  return E_NOTIMPL;
162  case 0x80000002:
163  return E_OUTOFMEMORY;
164  case 0x80000003:
165  return E_INVALIDARG;
166  case 0x80000004:
167  return E_NOINTERFACE;
168  case 0x80000005:
169  return E_POINTER;
170  case 0x80000006:
171  return E_HANDLE;
172  case 0x80000007:
173  return E_ABORT;
174  case 0x80000008:
175  return E_FAIL;
176  case 0x80000009:
177  return E_ACCESSDENIED;
178  case 0x8000FFFF:
179  return E_UNEXPECTED;
180  }
181  return in;
182 }
183 
184 static long get_device_property_long(IOHIDDeviceRef device, CFStringRef key)
185 {
186  CFTypeRef ref;
187  long result = 0;
188 
189  if (device)
190  {
191  assert(IOHIDDeviceGetTypeID() == CFGetTypeID(device));
192 
193  ref = IOHIDDeviceGetProperty(device, key);
194 
195  if (ref && CFNumberGetTypeID() == CFGetTypeID(ref))
196  CFNumberGetValue((CFNumberRef)ref, kCFNumberLongType, &result);
197  }
198 
199  return result;
200 }
201 
202 static CFStringRef copy_device_name(IOHIDDeviceRef device)
203 {
204  CFStringRef name;
205 
206  if (device)
207  {
208  CFTypeRef ref_name;
209 
210  assert(IOHIDDeviceGetTypeID() == CFGetTypeID(device));
211 
212  ref_name = IOHIDDeviceGetProperty(device, CFSTR(kIOHIDProductKey));
213 
214  if (ref_name && CFStringGetTypeID() == CFGetTypeID(ref_name))
215  name = CFStringCreateCopy(kCFAllocatorDefault, ref_name);
216  else
217  {
218  long vendID, prodID;
219 
220  vendID = get_device_property_long(device, CFSTR(kIOHIDVendorIDKey));
221  prodID = get_device_property_long(device, CFSTR(kIOHIDProductIDKey));
222  name = CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("0x%04lx 0x%04lx"), vendID, prodID);
223  }
224  }
225  else
226  {
227  ERR("NULL device\n");
228  name = CFStringCreateCopy(kCFAllocatorDefault, CFSTR(""));
229  }
230 
231  return name;
232 }
233 
234 static long get_device_location_ID(IOHIDDeviceRef device)
235 {
236  return get_device_property_long(device, CFSTR(kIOHIDLocationIDKey));
237 }
238 
239 static void copy_set_to_array(const void *value, void *context)
240 {
241  CFArrayAppendValue(context, value);
242 }
243 
244 static CFComparisonResult device_name_comparator(IOHIDDeviceRef device1, IOHIDDeviceRef device2)
245 {
246  CFStringRef name1 = copy_device_name(device1), name2 = copy_device_name(device2);
247  CFComparisonResult result = CFStringCompare(name1, name2, (kCFCompareForcedOrdering | kCFCompareNumerically));
248  CFRelease(name1);
249  CFRelease(name2);
250  return result;
251 }
252 
253 static CFComparisonResult device_location_name_comparator(const void *val1, const void *val2, void *context)
254 {
255  IOHIDDeviceRef device1 = (IOHIDDeviceRef)val1, device2 = (IOHIDDeviceRef)val2;
256  long loc1 = get_device_location_ID(device1), loc2 = get_device_location_ID(device2);
257 
258  if (loc1 < loc2)
259  return kCFCompareLessThan;
260  else if (loc1 > loc2)
261  return kCFCompareGreaterThan;
262  /* virtual joysticks may not have a kIOHIDLocationIDKey and will default to location ID of 0, this orders virtual joysticks by their name */
263  return device_name_comparator(device1, device2);
264 }
265 
266 static const char* debugstr_cf(CFTypeRef t)
267 {
268  CFStringRef s;
269  const char* ret;
270 
271  if (!t) return "(null)";
272 
273  if (CFGetTypeID(t) == CFStringGetTypeID())
274  s = t;
275  else
276  s = CFCopyDescription(t);
277  ret = CFStringGetCStringPtr(s, kCFStringEncodingUTF8);
278  if (ret) ret = debugstr_a(ret);
279  if (!ret)
280  {
281  const UniChar* u = CFStringGetCharactersPtr(s);
282  if (u)
283  ret = debugstr_wn((const WCHAR*)u, CFStringGetLength(s));
284  }
285  if (!ret)
286  {
287  UniChar buf[200];
288  int len = min(CFStringGetLength(s), ARRAY_SIZE(buf));
289  CFStringGetCharacters(s, CFRangeMake(0, len), buf);
290  ret = debugstr_wn(buf, len);
291  }
292  if (s != t) CFRelease(s);
293  return ret;
294 }
295 
296 static const char* debugstr_device(IOHIDDeviceRef device)
297 {
298  return wine_dbg_sprintf("<IOHIDDevice %p product %s IOHIDLocationID %lu>", device,
299  debugstr_cf(IOHIDDeviceGetProperty(device, CFSTR(kIOHIDProductKey))),
300  get_device_location_ID(device));
301 }
302 
303 static const char* debugstr_element(IOHIDElementRef element)
304 {
305  return wine_dbg_sprintf("<IOHIDElement %p type %d usage %u/%u device %p>", element,
306  IOHIDElementGetType(element), IOHIDElementGetUsagePage(element),
307  IOHIDElementGetUsage(element), IOHIDElementGetDevice(element));
308 }
309 
310 static IOHIDDeviceRef get_device_ref(int id)
311 {
312  IOHIDElementRef device_main_element;
313  IOHIDDeviceRef hid_device;
314 
315  TRACE("id %d\n", id);
316 
317  if (!device_main_elements || id >= CFArrayGetCount(device_main_elements))
318  return 0;
319 
320  device_main_element = (IOHIDElementRef)CFArrayGetValueAtIndex(device_main_elements, id);
321  if (!device_main_element)
322  {
323  ERR("Invalid Element requested %i\n",id);
324  return 0;
325  }
326 
327  hid_device = IOHIDElementGetDevice(device_main_element);
328  if (!hid_device)
329  {
330  ERR("Invalid Device requested %i\n",id);
331  return 0;
332  }
333 
334  TRACE("-> %s\n", debugstr_device(hid_device));
335  return hid_device;
336 }
337 
338 static HRESULT get_ff(IOHIDDeviceRef device, FFDeviceObjectReference *ret)
339 {
340  io_service_t service;
341  CFMutableDictionaryRef matching;
342  CFTypeRef location_id;
343  HRESULT hr;
344 
345  TRACE("device %s\n", debugstr_device(device));
346 
347  matching = IOServiceMatching(kIOHIDDeviceKey);
348  if(!matching){
349  WARN("IOServiceMatching failed, force feedback disabled\n");
350  return DIERR_DEVICENOTREG;
351  }
352 
353  location_id = IOHIDDeviceGetProperty(device, CFSTR(kIOHIDLocationIDKey));
354  if(!location_id){
355  CFRelease(matching);
356  WARN("IOHIDDeviceGetProperty failed, force feedback disabled\n");
357  return DIERR_DEVICENOTREG;
358  }
359 
360  CFDictionaryAddValue(matching, CFSTR(kIOHIDLocationIDKey), location_id);
361 
362  service = IOServiceGetMatchingService(kIOMasterPortDefault, matching);
363 
364  if (ret)
365  hr = osx_to_win32_hresult(FFCreateDevice(service, ret));
366  else
367  hr = FFIsForceFeedback(service) == FF_OK ? S_OK : S_FALSE;
368 
369  IOObjectRelease(service);
370  TRACE("-> hr 0x%08x *ret %p\n", hr, ret ? *ret : NULL);
371  return hr;
372 }
373 
374 static CFMutableDictionaryRef create_osx_device_match(int usage)
375 {
376  CFMutableDictionaryRef result;
377 
378  TRACE("usage %d\n", usage);
379 
380  result = CFDictionaryCreateMutable( kCFAllocatorDefault, 0,
381  &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks );
382 
383  if ( result )
384  {
385  int number = kHIDPage_GenericDesktop;
386  CFNumberRef page = CFNumberCreate( kCFAllocatorDefault,
387  kCFNumberIntType, &number);
388 
389  if (page)
390  {
391  CFNumberRef cf_usage;
392 
393  CFDictionarySetValue( result, CFSTR( kIOHIDDeviceUsagePageKey ), page );
394  CFRelease( page );
395 
396  cf_usage = CFNumberCreate( kCFAllocatorDefault,
397  kCFNumberIntType, &usage);
398  if (cf_usage)
399  {
400  CFDictionarySetValue( result, CFSTR( kIOHIDDeviceUsageKey ), cf_usage );
401  CFRelease( cf_usage );
402  }
403  else
404  {
405  ERR("CFNumberCreate() failed.\n");
406  CFRelease(result);
407  return NULL;
408  }
409  }
410  else
411  {
412  ERR("CFNumberCreate failed.\n");
413  CFRelease(result);
414  return NULL;
415  }
416  }
417  else
418  {
419  ERR("CFDictionaryCreateMutable failed.\n");
420  return NULL;
421  }
422 
423  return result;
424 }
425 
426 static CFIndex find_top_level(IOHIDDeviceRef hid_device, CFMutableArrayRef main_elements)
427 {
428  CFArrayRef elements;
429  CFIndex total = 0;
430 
431  TRACE("hid_device %s\n", debugstr_device(hid_device));
432 
433  if (!hid_device)
434  return 0;
435 
436  elements = IOHIDDeviceCopyMatchingElements(hid_device, NULL, 0);
437 
438  if (elements)
439  {
440  CFIndex idx, cnt = CFArrayGetCount(elements);
441  for (idx=0; idx<cnt; idx++)
442  {
443  IOHIDElementRef element = (IOHIDElementRef)CFArrayGetValueAtIndex(elements, idx);
444  int type = IOHIDElementGetType(element);
445 
446  TRACE("element %s\n", debugstr_element(element));
447 
448  /* Check for top-level gaming device collections */
449  if (type == kIOHIDElementTypeCollection && IOHIDElementGetParent(element) == 0)
450  {
451  int usage_page = IOHIDElementGetUsagePage(element);
452  int usage = IOHIDElementGetUsage(element);
453 
454  if (usage_page == kHIDPage_GenericDesktop &&
455  (usage == kHIDUsage_GD_Joystick || usage == kHIDUsage_GD_GamePad))
456  {
457  CFArrayAppendValue(main_elements, element);
458  total++;
459  }
460  }
461  }
462  CFRelease(elements);
463  }
464 
465  TRACE("-> total %d\n", (int)total);
466  return total;
467 }
468 
469 static void get_element_children(IOHIDElementRef element, CFMutableArrayRef all_children)
470 {
471  CFIndex idx, cnt;
472  CFArrayRef element_children = IOHIDElementGetChildren(element);
473 
474  TRACE("element %s\n", debugstr_element(element));
475 
476  cnt = CFArrayGetCount(element_children);
477 
478  /* Either add the element to the array or grab its children */
479  for (idx=0; idx<cnt; idx++)
480  {
481  IOHIDElementRef child;
482 
483  child = (IOHIDElementRef)CFArrayGetValueAtIndex(element_children, idx);
484  TRACE("child %s\n", debugstr_element(child));
485  if (IOHIDElementGetType(child) == kIOHIDElementTypeCollection)
486  get_element_children(child, all_children);
487  else
488  CFArrayAppendValue(all_children, child);
489  }
490 }
491 
492 static int find_osx_devices(void)
493 {
494  IOHIDManagerRef hid_manager;
495  CFMutableDictionaryRef result;
496  CFSetRef devset;
497  CFMutableArrayRef matching;
498 
499  TRACE("()\n");
500 
501  hid_manager = IOHIDManagerCreate( kCFAllocatorDefault, 0L );
502  if (IOHIDManagerOpen( hid_manager, 0 ) != kIOReturnSuccess)
503  {
504  ERR("Couldn't open IOHIDManager.\n");
505  CFRelease( hid_manager );
506  return 0;
507  }
508 
509  matching = CFArrayCreateMutable( kCFAllocatorDefault, 0,
510  &kCFTypeArrayCallBacks );
511 
512  /* build matching dictionary */
513  result = create_osx_device_match(kHIDUsage_GD_Joystick);
514  if (!result)
515  {
516  CFRelease(matching);
517  goto fail;
518  }
519  CFArrayAppendValue( matching, result );
520  CFRelease( result );
521  result = create_osx_device_match(kHIDUsage_GD_GamePad);
522  if (!result)
523  {
524  CFRelease(matching);
525  goto fail;
526  }
527  CFArrayAppendValue( matching, result );
528  CFRelease( result );
529 
530  IOHIDManagerSetDeviceMatchingMultiple( hid_manager, matching);
531  CFRelease( matching );
532  devset = IOHIDManagerCopyDevices( hid_manager );
533  if (devset)
534  {
535  CFIndex num_devices, num_main_elements, idx;
536  CFMutableArrayRef devices;
537 
538  num_devices = CFSetGetCount(devset);
539  devices = CFArrayCreateMutable(kCFAllocatorDefault, num_devices, &kCFTypeArrayCallBacks);
540  CFSetApplyFunction(devset, copy_set_to_array, devices);
541  CFRelease(devset);
542  CFArraySortValues(devices, CFRangeMake(0, num_devices), device_location_name_comparator, NULL);
543 
544  device_main_elements = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
545  if (!device_main_elements)
546  {
547  CFRelease( devices );
548  goto fail;
549  }
550 
551  num_main_elements = 0;
552  for (idx = 0; idx < num_devices; idx++)
553  {
554  CFIndex top;
555  IOHIDDeviceRef hid_device;
556 
557  hid_device = (IOHIDDeviceRef) CFArrayGetValueAtIndex(devices, idx);
558  TRACE("hid_device %s\n", debugstr_device(hid_device));
559  top = find_top_level(hid_device, device_main_elements);
560  num_main_elements += top;
561  }
562 
563  CFRelease(devices);
564 
565  TRACE("found %i device(s), %i collection(s)\n",(int)num_devices,(int)num_main_elements);
566  return (int)num_main_elements;
567  }
568 
569 fail:
570  IOHIDManagerClose( hid_manager, 0 );
571  CFRelease( hid_manager );
572  return 0;
573 }
574 
575 static int get_osx_device_name(int id, char *name, int length)
576 {
577  CFStringRef str;
578  IOHIDDeviceRef hid_device;
579 
580  hid_device = get_device_ref(id);
581 
582  TRACE("id %d hid_device %s\n", id, debugstr_device(hid_device));
583 
584  if (name)
585  name[0] = 0;
586 
587  if (!hid_device)
588  return 0;
589 
590  str = IOHIDDeviceGetProperty(hid_device, CFSTR( kIOHIDProductKey ));
591  if (str)
592  {
593  CFIndex len = CFStringGetLength(str);
594  if (length >= len)
595  {
596  CFStringGetCString(str,name,length,kCFStringEncodingASCII);
597  return len;
598  }
599  else
600  return (len+1);
601  }
602  return 0;
603 }
604 
605 static CFComparisonResult button_usage_comparator(const void *val1, const void *val2, void *context)
606 {
607  IOHIDElementRef element1 = (IOHIDElementRef)val1, element2 = (IOHIDElementRef)val2;
608  int usage1 = IOHIDElementGetUsage(element1), usage2 = IOHIDElementGetUsage(element2);
609 
610  if (usage1 < usage2)
611  return kCFCompareLessThan;
612  if (usage1 > usage2)
613  return kCFCompareGreaterThan;
614  return kCFCompareEqualTo;
615 }
616 
617 static void get_osx_device_elements(JoystickImpl *device, int axis_map[8])
618 {
619  IOHIDElementRef device_main_element;
620  CFMutableArrayRef elements;
621  DWORD sliders = 0;
622 
623  TRACE("device %p device->id %d\n", device, device->id);
624 
625  device->elements = NULL;
626 
627  if (!device_main_elements || device->id >= CFArrayGetCount(device_main_elements))
628  return;
629 
630  device_main_element = (IOHIDElementRef)CFArrayGetValueAtIndex(device_main_elements, device->id);
631  TRACE("device_main_element %s\n", debugstr_element(device_main_element));
632  if (!device_main_element)
633  return;
634 
635  elements = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
636  get_element_children(device_main_element, elements);
637 
638  if (elements)
639  {
640  CFIndex idx, cnt = CFArrayGetCount( elements );
641  CFMutableArrayRef axes = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
642  CFMutableArrayRef buttons = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
643  CFMutableArrayRef povs = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
644 
645  for ( idx = 0; idx < cnt; idx++ )
646  {
647  IOHIDElementRef element = ( IOHIDElementRef ) CFArrayGetValueAtIndex( elements, idx );
648  int type = IOHIDElementGetType( element );
649  int usage_page = IOHIDElementGetUsagePage( element );
650 
651  TRACE("element %s\n", debugstr_element(element));
652 
653  if (usage_page >= kHIDPage_VendorDefinedStart)
654  {
655  /* vendor pages can repurpose type ids, resulting in incorrect case matches below (e.g. ds4 controllers) */
656  continue;
657  }
658 
659  switch(type)
660  {
661  case kIOHIDElementTypeInput_Button:
662  {
663  TRACE("kIOHIDElementTypeInput_Button usage_page %d\n", usage_page);
664  if (usage_page != kHIDPage_Button)
665  {
666  /* avoid strange elements found on the 360 controller */
667  continue;
668  }
669 
670  if (CFArrayGetCount(buttons) < 128)
671  CFArrayAppendValue(buttons, element);
672  break;
673  }
674  case kIOHIDElementTypeInput_Axis:
675  {
676  TRACE("kIOHIDElementTypeInput_Axis\n");
677  CFArrayAppendValue(axes, element);
678  break;
679  }
680  case kIOHIDElementTypeInput_Misc:
681  {
682  uint32_t usage = IOHIDElementGetUsage( element );
683  switch(usage)
684  {
685  case kHIDUsage_GD_Hatswitch:
686  {
687  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Hatswitch\n");
688  CFArrayAppendValue(povs, element);
689  break;
690  }
691  case kHIDUsage_GD_Slider:
692  sliders ++;
693  if (sliders > 2)
694  break;
695  /* fallthrough, sliders are axis */
696  case kHIDUsage_GD_X:
697  case kHIDUsage_GD_Y:
698  case kHIDUsage_GD_Z:
699  case kHIDUsage_GD_Rx:
700  case kHIDUsage_GD_Ry:
701  case kHIDUsage_GD_Rz:
702  {
703  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_* (%d)\n", usage);
704  axis_map[CFArrayGetCount(axes)]=usage;
705  CFArrayAppendValue(axes, element);
706  break;
707  }
708  default:
709  FIXME("kIOHIDElementTypeInput_Misc / Unhandled usage %i\n", usage);
710  }
711  break;
712  }
713  default:
714  FIXME("Unhandled type %i\n",type);
715  }
716  }
717 
718  /* Sort buttons into correct order */
719  CFArraySortValues(buttons, CFRangeMake(0, CFArrayGetCount(buttons)), button_usage_comparator, NULL);
720 
721  device->generic.devcaps.dwAxes = CFArrayGetCount(axes);
722  device->generic.devcaps.dwButtons = CFArrayGetCount(buttons);
723  device->generic.devcaps.dwPOVs = CFArrayGetCount(povs);
724 
725  TRACE("axes %u povs %u buttons %u\n", device->generic.devcaps.dwAxes, device->generic.devcaps.dwPOVs,
726  device->generic.devcaps.dwButtons);
727 
728  /* build our element array in the order that dinput expects */
729  CFArrayAppendArray(axes, povs, CFRangeMake(0, device->generic.devcaps.dwPOVs));
730  CFArrayAppendArray(axes, buttons, CFRangeMake(0, device->generic.devcaps.dwButtons));
731  device->elements = axes;
732  axes = NULL;
733 
734  CFRelease(povs);
735  CFRelease(buttons);
736  CFRelease(elements);
737  }
738  else
739  {
740  device->generic.devcaps.dwAxes = 0;
741  device->generic.devcaps.dwButtons = 0;
742  device->generic.devcaps.dwPOVs = 0;
743  }
744 }
745 
746 static void get_osx_device_elements_props(JoystickImpl *device)
747 {
748  TRACE("device %p\n", device);
749 
750  if (device->elements)
751  {
752  CFIndex idx, cnt = CFArrayGetCount( device->elements );
753 
754  for ( idx = 0; idx < cnt; idx++ )
755  {
756  IOHIDElementRef element = ( IOHIDElementRef ) CFArrayGetValueAtIndex( device->elements, idx );
757 
758  TRACE("element %s\n", debugstr_element(element));
759 
760  device->generic.props[idx].lDevMin = IOHIDElementGetLogicalMin(element);
761  device->generic.props[idx].lDevMax = IOHIDElementGetLogicalMax(element);
762  device->generic.props[idx].lMin = 0;
763  device->generic.props[idx].lMax = 0xffff;
764  device->generic.props[idx].lDeadZone = 0;
765  device->generic.props[idx].lSaturation = 0;
766  }
767  }
768 }
769 
770 static void poll_osx_device_state(LPDIRECTINPUTDEVICE8A iface)
771 {
772  JoystickImpl *device = impl_from_IDirectInputDevice8A(iface);
773  IOHIDElementRef device_main_element;
774  IOHIDDeviceRef hid_device;
775 
776  TRACE("device %p device->id %i\n", device, device->id);
777 
778  if (!device_main_elements || device->id >= CFArrayGetCount(device_main_elements))
779  return;
780 
781  device_main_element = (IOHIDElementRef) CFArrayGetValueAtIndex(device_main_elements, device->id);
782  hid_device = IOHIDElementGetDevice(device_main_element);
783  TRACE("main element %s hid_device %s\n", debugstr_element(device_main_element), debugstr_device(hid_device));
784  if (!hid_device)
785  return;
786 
787  if (device->elements)
788  {
789  int button_idx = 0;
790  int pov_idx = 0;
791  int slider_idx = 0;
792  int inst_id;
793  CFIndex idx, cnt = CFArrayGetCount( device->elements );
794 
795  for ( idx = 0; idx < cnt; idx++ )
796  {
797  IOHIDValueRef valueRef;
798  int val, oldVal, newVal;
799  IOHIDElementRef element = ( IOHIDElementRef ) CFArrayGetValueAtIndex( device->elements, idx );
800  int type = IOHIDElementGetType( element );
801 
802  TRACE("element %s\n", debugstr_element(element));
803 
804  switch(type)
805  {
806  case kIOHIDElementTypeInput_Button:
807  TRACE("kIOHIDElementTypeInput_Button\n");
808  if(button_idx < 128)
809  {
810  valueRef = NULL;
811  if (IOHIDDeviceGetValue(hid_device, element, &valueRef) != kIOReturnSuccess)
812  return;
813  if (valueRef == NULL)
814  return;
815  val = IOHIDValueGetIntegerValue(valueRef);
816  newVal = val ? 0x80 : 0x0;
817  oldVal = device->generic.js.rgbButtons[button_idx];
818  device->generic.js.rgbButtons[button_idx] = newVal;
819  TRACE("valueRef %s val %d oldVal %d newVal %d\n", debugstr_cf(valueRef), val, oldVal, newVal);
820  if (oldVal != newVal)
821  {
822  button_idx = device->generic.button_map[button_idx];
823 
824  inst_id = DIDFT_MAKEINSTANCE(button_idx) | DIDFT_PSHBUTTON;
825  queue_event(iface,inst_id,newVal,GetCurrentTime(),device->generic.base.dinput->evsequence++);
826  }
827  button_idx ++;
828  }
829  break;
830  case kIOHIDElementTypeInput_Misc:
831  {
832  uint32_t usage = IOHIDElementGetUsage( element );
833  switch(usage)
834  {
835  case kHIDUsage_GD_Hatswitch:
836  {
837  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Hatswitch\n");
838  valueRef = NULL;
839  if (IOHIDDeviceGetValue(hid_device, element, &valueRef) != kIOReturnSuccess)
840  return;
841  if (valueRef == NULL)
842  return;
843  val = IOHIDValueGetIntegerValue(valueRef);
844  oldVal = device->generic.js.rgdwPOV[pov_idx];
845  if (val >= 8)
846  newVal = -1;
847  else
848  newVal = val * 4500;
849  device->generic.js.rgdwPOV[pov_idx] = newVal;
850  TRACE("valueRef %s val %d oldVal %d newVal %d\n", debugstr_cf(valueRef), val, oldVal, newVal);
851  if (oldVal != newVal)
852  {
853  inst_id = DIDFT_MAKEINSTANCE(pov_idx) | DIDFT_POV;
854  queue_event(iface,inst_id,newVal,GetCurrentTime(),device->generic.base.dinput->evsequence++);
855  }
856  pov_idx ++;
857  break;
858  }
859  case kHIDUsage_GD_X:
860  case kHIDUsage_GD_Y:
861  case kHIDUsage_GD_Z:
862  case kHIDUsage_GD_Rx:
863  case kHIDUsage_GD_Ry:
864  case kHIDUsage_GD_Rz:
865  case kHIDUsage_GD_Slider:
866  {
867  int wine_obj = -1;
868 
869  valueRef = NULL;
870  if (IOHIDDeviceGetValue(hid_device, element, &valueRef) != kIOReturnSuccess)
871  return;
872  if (valueRef == NULL)
873  return;
874  val = IOHIDValueGetIntegerValue(valueRef);
875  newVal = joystick_map_axis(&device->generic.props[idx], val);
876  switch (usage)
877  {
878  case kHIDUsage_GD_X:
879  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_X\n");
880  wine_obj = 0;
881  oldVal = device->generic.js.lX;
882  device->generic.js.lX = newVal;
883  break;
884  case kHIDUsage_GD_Y:
885  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Y\n");
886  wine_obj = 1;
887  oldVal = device->generic.js.lY;
888  device->generic.js.lY = newVal;
889  break;
890  case kHIDUsage_GD_Z:
891  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Z\n");
892  wine_obj = 2;
893  oldVal = device->generic.js.lZ;
894  device->generic.js.lZ = newVal;
895  break;
896  case kHIDUsage_GD_Rx:
897  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Rx\n");
898  wine_obj = 3;
899  oldVal = device->generic.js.lRx;
900  device->generic.js.lRx = newVal;
901  break;
902  case kHIDUsage_GD_Ry:
903  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Ry\n");
904  wine_obj = 4;
905  oldVal = device->generic.js.lRy;
906  device->generic.js.lRy = newVal;
907  break;
908  case kHIDUsage_GD_Rz:
909  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Rz\n");
910  wine_obj = 5;
911  oldVal = device->generic.js.lRz;
912  device->generic.js.lRz = newVal;
913  break;
914  case kHIDUsage_GD_Slider:
915  TRACE("kIOHIDElementTypeInput_Misc / kHIDUsage_GD_Slider\n");
916  wine_obj = 6 + slider_idx;
917  oldVal = device->generic.js.rglSlider[slider_idx];
918  device->generic.js.rglSlider[slider_idx] = newVal;
919  slider_idx ++;
920  break;
921  }
922  TRACE("valueRef %s val %d oldVal %d newVal %d\n", debugstr_cf(valueRef), val, oldVal, newVal);
923  if ((wine_obj != -1) &&
924  (oldVal != newVal))
925  {
926  inst_id = DIDFT_MAKEINSTANCE(wine_obj) | DIDFT_ABSAXIS;
927  queue_event(iface,inst_id,newVal,GetCurrentTime(),device->generic.base.dinput->evsequence++);
928  }
929 
930  break;
931  }
932  default:
933  FIXME("kIOHIDElementTypeInput_Misc / unhandled usage %i\n", usage);
934  }
935  break;
936  }
937  default:
938  FIXME("Unhandled type %i\n",type);
939  }
940  }
941  }
942 }
943 
944 static INT find_joystick_devices(void)
945 {
946  static INT joystick_devices_count = -1;
947 
948  if (joystick_devices_count != -1) return joystick_devices_count;
949 
950  joystick_devices_count = find_osx_devices();
951 
952  return joystick_devices_count;
953 }
954 
955 static DWORD make_vid_pid(IOHIDDeviceRef device)
956 {
957  long vendID, prodID;
958 
959  vendID = get_device_property_long(device, CFSTR(kIOHIDVendorIDKey));
960  prodID = get_device_property_long(device, CFSTR(kIOHIDProductIDKey));
961 
962  return MAKELONG(vendID, prodID);
963 }
964 
965 static HRESULT joydev_enum_deviceA(DWORD dwDevType, DWORD dwFlags, LPDIDEVICEINSTANCEA lpddi, DWORD version, int id)
966 {
967  IOHIDDeviceRef device;
968  BOOL is_joystick;
969 
970  TRACE("dwDevType %u dwFlags 0x%08x version 0x%04x id %d\n", dwDevType, dwFlags, version, id);
971 
972  if (id >= find_joystick_devices()) return E_FAIL;
973 
974  device = get_device_ref(id);
975 
976  if ((dwDevType == 0) ||
977  ((dwDevType == DIDEVTYPE_JOYSTICK) && (version >= 0x0300 && version < 0x0800)) ||
978  (((dwDevType == DI8DEVCLASS_GAMECTRL) || (dwDevType == DI8DEVTYPE_JOYSTICK)) && (version >= 0x0800)))
979  {
981  if(!device)
982  return S_FALSE;
983  if(get_ff(device, NULL) != S_OK)
984  return S_FALSE;
985  }
986  is_joystick = get_device_property_long(device, CFSTR(kIOHIDDeviceUsageKey)) == kHIDUsage_GD_Joystick;
987  /* Return joystick */
988  lpddi->guidInstance = DInput_Wine_OsX_Joystick_GUID;
989  lpddi->guidInstance.Data3 = id;
991  lpddi->guidProduct.Data1 = make_vid_pid(device);
992  lpddi->dwDevType = get_device_type(version, is_joystick);
993  lpddi->dwDevType |= DIDEVTYPE_HID;
994  lpddi->wUsagePage = 0x01; /* Desktop */
995  if (is_joystick)
996  lpddi->wUsage = 0x04; /* Joystick */
997  else
998  lpddi->wUsage = 0x05; /* Game Pad */
999  sprintf(lpddi->tszInstanceName, "Joystick %d", id);
1000 
1001  /* get the device name */
1002  get_osx_device_name(id, lpddi->tszProductName, MAX_PATH);
1003 
1004  lpddi->guidFFDriver = GUID_NULL;
1005  return S_OK;
1006  }
1007 
1008  return S_FALSE;
1009 }
1010 
1011 static HRESULT joydev_enum_deviceW(DWORD dwDevType, DWORD dwFlags, LPDIDEVICEINSTANCEW lpddi, DWORD version, int id)
1012 {
1013  char name[MAX_PATH];
1014  char friendly[32];
1015  IOHIDDeviceRef device;
1016  BOOL is_joystick;
1017 
1018  TRACE("dwDevType %u dwFlags 0x%08x version 0x%04x id %d\n", dwDevType, dwFlags, version, id);
1019 
1020  if (id >= find_joystick_devices()) return E_FAIL;
1021 
1022  device = get_device_ref(id);
1023 
1024  if ((dwDevType == 0) ||
1025  ((dwDevType == DIDEVTYPE_JOYSTICK) && (version >= 0x0300 && version < 0x0800)) ||
1026  (((dwDevType == DI8DEVCLASS_GAMECTRL) || (dwDevType == DI8DEVTYPE_JOYSTICK)) && (version >= 0x0800))) {
1027 
1028  if (dwFlags & DIEDFL_FORCEFEEDBACK) {
1029  if(!device)
1030  return S_FALSE;
1031  if(get_ff(device, NULL) != S_OK)
1032  return S_FALSE;
1033  }
1034  is_joystick = get_device_property_long(device, CFSTR(kIOHIDDeviceUsageKey)) == kHIDUsage_GD_Joystick;
1035  /* Return joystick */
1036  lpddi->guidInstance = DInput_Wine_OsX_Joystick_GUID;
1037  lpddi->guidInstance.Data3 = id;
1039  lpddi->guidProduct.Data1 = make_vid_pid(device);
1040  lpddi->dwDevType = get_device_type(version, is_joystick);
1041  lpddi->dwDevType |= DIDEVTYPE_HID;
1042  lpddi->wUsagePage = 0x01; /* Desktop */
1043  if (is_joystick)
1044  lpddi->wUsage = 0x04; /* Joystick */
1045  else
1046  lpddi->wUsage = 0x05; /* Game Pad */
1047  sprintf(friendly, "Joystick %d", id);
1048  MultiByteToWideChar(CP_ACP, 0, friendly, -1, lpddi->tszInstanceName, MAX_PATH);
1049 
1050  /* get the device name */
1051  get_osx_device_name(id, name, MAX_PATH);
1052 
1054  lpddi->guidFFDriver = GUID_NULL;
1055  return S_OK;
1056  }
1057 
1058  return S_FALSE;
1059 }
1060 
1061 static const char *osx_ff_axis_name(UInt8 axis)
1062 {
1063  static char ret[6];
1064  switch(axis){
1065  case FFJOFS_X:
1066  return "FFJOFS_X";
1067  case FFJOFS_Y:
1068  return "FFJOFS_Y";
1069  case FFJOFS_Z:
1070  return "FFJOFS_Z";
1071  }
1072  sprintf(ret, "%u", (unsigned int)axis);
1073  return ret;
1074 }
1075 
1076 static BOOL osx_axis_has_ff(FFCAPABILITIES *ffcaps, UInt8 axis)
1077 {
1078  int i;
1079  for(i = 0; i < ffcaps->numFfAxes; ++i)
1080  if(ffcaps->ffAxes[i] == axis)
1081  return TRUE;
1082  return FALSE;
1083 }
1084 
1085 static HRESULT alloc_device(REFGUID rguid, IDirectInputImpl *dinput,
1086  JoystickImpl **pdev, unsigned short index)
1087 {
1088  DWORD i;
1089  IOHIDDeviceRef device;
1090  JoystickImpl* newDevice;
1091  char name[MAX_PATH];
1092  HRESULT hr;
1093  LPDIDATAFORMAT df = NULL;
1094  int idx = 0;
1095  int axis_map[8]; /* max axes */
1096  int slider_count = 0;
1097  FFCAPABILITIES ffcaps;
1098 
1099  TRACE("%s %p %p %hu\n", debugstr_guid(rguid), dinput, pdev, index);
1100 
1101  newDevice = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(JoystickImpl));
1102  if (newDevice == 0) {
1103  WARN("out of memory\n");
1104  *pdev = 0;
1105  return DIERR_OUTOFMEMORY;
1106  }
1107 
1108  newDevice->id = index;
1109 
1110  device = get_device_ref(index);
1111 
1112  newDevice->generic.guidInstance = DInput_Wine_OsX_Joystick_GUID;
1113  newDevice->generic.guidInstance.Data3 = index;
1114  newDevice->generic.guidProduct = DInput_PIDVID_Product_GUID;
1115  newDevice->generic.guidProduct.Data1 = make_vid_pid(device);
1116  newDevice->generic.joy_polldev = poll_osx_device_state;
1117 
1118  /* get the device name */
1119  get_osx_device_name(index, name, MAX_PATH);
1120  TRACE("Name %s\n",name);
1121 
1122  /* copy the device name */
1123  newDevice->generic.name = HeapAlloc(GetProcessHeap(),0,strlen(name) + 1);
1124  strcpy(newDevice->generic.name, name);
1125 
1126  list_init(&newDevice->effects);
1127  if(get_ff(device, &newDevice->ff) == S_OK){
1128  newDevice->generic.devcaps.dwFlags |= DIDC_FORCEFEEDBACK;
1129 
1130  hr = FFDeviceGetForceFeedbackCapabilities(newDevice->ff, &ffcaps);
1131  if(SUCCEEDED(hr)){
1132  TRACE("FF Capabilities:\n");
1133  TRACE("\tsupportedEffects: 0x%x\n", (unsigned int)ffcaps.supportedEffects);
1134  TRACE("\temulatedEffects: 0x%x\n", (unsigned int)ffcaps.emulatedEffects);
1135  TRACE("\tsubType: 0x%x\n", (unsigned int)ffcaps.subType);
1136  TRACE("\tnumFfAxes: %u\n", (unsigned int)ffcaps.numFfAxes);
1137  TRACE("\tffAxes: [");
1138  for(i = 0; i < ffcaps.numFfAxes; ++i){
1139  TRACE("%s", osx_ff_axis_name(ffcaps.ffAxes[i]));
1140  if(i < ffcaps.numFfAxes - 1)
1141  TRACE(", ");
1142  }
1143  TRACE("]\n");
1144  TRACE("\tstorageCapacity: %u\n", (unsigned int)ffcaps.storageCapacity);
1145  TRACE("\tplaybackCapacity: %u\n", (unsigned int)ffcaps.playbackCapacity);
1146  }
1147 
1148  hr = FFDeviceSendForceFeedbackCommand(newDevice->ff, FFSFFC_RESET);
1149  if(FAILED(hr))
1150  WARN("FFDeviceSendForceFeedbackCommand(FFSFFC_RESET) failed: %08x\n", hr);
1151 
1152  hr = FFDeviceSendForceFeedbackCommand(newDevice->ff, FFSFFC_SETACTUATORSON);
1153  if(FAILED(hr))
1154  WARN("FFDeviceSendForceFeedbackCommand(FFSFFC_SETACTUATORSON) failed: %08x\n", hr);
1155  }
1156 
1157  memset(axis_map, 0, sizeof(axis_map));
1158  get_osx_device_elements(newDevice, axis_map);
1159 
1160  TRACE("%i axes %i buttons %i povs\n",newDevice->generic.devcaps.dwAxes,newDevice->generic.devcaps.dwButtons,newDevice->generic.devcaps.dwPOVs);
1161 
1162  if (newDevice->generic.devcaps.dwButtons > 128)
1163  {
1164  WARN("Can't support %d buttons. Clamping down to 128\n", newDevice->generic.devcaps.dwButtons);
1165  newDevice->generic.devcaps.dwButtons = 128;
1166  }
1167 
1168  newDevice->generic.base.IDirectInputDevice8A_iface.lpVtbl = &JoystickAvt;
1169  newDevice->generic.base.IDirectInputDevice8W_iface.lpVtbl = &JoystickWvt;
1170  newDevice->generic.base.ref = 1;
1171  newDevice->generic.base.dinput = dinput;
1172  newDevice->generic.base.guid = *rguid;
1173  InitializeCriticalSection(&newDevice->generic.base.crit);
1174  newDevice->generic.base.crit.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": JoystickImpl*->generic.base.crit");
1175 
1176  /* Create copy of default data format */
1177  if (!(df = HeapAlloc(GetProcessHeap(), 0, c_dfDIJoystick2.dwSize))) goto FAILED;
1179 
1180  df->dwNumObjs = newDevice->generic.devcaps.dwAxes + newDevice->generic.devcaps.dwPOVs + newDevice->generic.devcaps.dwButtons;
1181  if (!(df->rgodf = HeapAlloc(GetProcessHeap(), 0, df->dwNumObjs * df->dwObjSize))) goto FAILED;
1182 
1183  for (i = 0; i < newDevice->generic.devcaps.dwAxes; i++)
1184  {
1185  int wine_obj = -1;
1186  BOOL has_ff = FALSE;
1187  switch (axis_map[i])
1188  {
1189  case kHIDUsage_GD_X:
1190  wine_obj = 0;
1191  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_X);
1192  break;
1193  case kHIDUsage_GD_Y:
1194  wine_obj = 1;
1195  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_Y);
1196  break;
1197  case kHIDUsage_GD_Z:
1198  wine_obj = 2;
1199  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_Z);
1200  break;
1201  case kHIDUsage_GD_Rx:
1202  wine_obj = 3;
1203  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_RX);
1204  break;
1205  case kHIDUsage_GD_Ry:
1206  wine_obj = 4;
1207  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_RY);
1208  break;
1209  case kHIDUsage_GD_Rz:
1210  wine_obj = 5;
1211  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_RZ);
1212  break;
1213  case kHIDUsage_GD_Slider:
1214  wine_obj = 6 + slider_count;
1215  has_ff = (newDevice->ff != 0) && osx_axis_has_ff(&ffcaps, FFJOFS_SLIDER(slider_count));
1216  slider_count++;
1217  break;
1218  }
1219  if (wine_obj < 0 ) continue;
1220 
1221  memcpy(&df->rgodf[idx], &c_dfDIJoystick2.rgodf[wine_obj], df->dwObjSize);
1222  df->rgodf[idx].dwType = DIDFT_MAKEINSTANCE(wine_obj) | DIDFT_ABSAXIS;
1223  if(has_ff)
1225  ++idx;
1226  }
1227 
1228  for (i = 0; i < newDevice->generic.devcaps.dwPOVs; i++)
1229  {
1230  memcpy(&df->rgodf[idx], &c_dfDIJoystick2.rgodf[i + 8], df->dwObjSize);
1232  }
1233 
1234  for (i = 0; i < newDevice->generic.devcaps.dwButtons; i++)
1235  {
1236  memcpy(&df->rgodf[idx], &c_dfDIJoystick2.rgodf[i + 12], df->dwObjSize);
1237  df->rgodf[idx ].pguid = &GUID_Button;
1239  }
1240  newDevice->generic.base.data_format.wine_df = df;
1241 
1242  /* initialize default properties */
1243  get_osx_device_elements_props(newDevice);
1244 
1245  IDirectInput_AddRef(&newDevice->generic.base.dinput->IDirectInput7A_iface);
1246 
1247  EnterCriticalSection(&dinput->crit);
1248  list_add_tail(&dinput->devices_list, &newDevice->generic.base.entry);
1249  LeaveCriticalSection(&dinput->crit);
1250 
1251  newDevice->generic.devcaps.dwSize = sizeof(newDevice->generic.devcaps);
1252  newDevice->generic.devcaps.dwFlags |= DIDC_ATTACHED;
1253  if (newDevice->generic.base.dinput->dwVersion >= 0x0800)
1254  newDevice->generic.devcaps.dwDevType = DI8DEVTYPE_JOYSTICK | (DI8DEVTYPEJOYSTICK_STANDARD << 8);
1255  else
1256  newDevice->generic.devcaps.dwDevType = DIDEVTYPE_JOYSTICK | (DIDEVTYPEJOYSTICK_TRADITIONAL << 8);
1257  newDevice->generic.devcaps.dwFFSamplePeriod = 0;
1258  newDevice->generic.devcaps.dwFFMinTimeResolution = 0;
1259  newDevice->generic.devcaps.dwFirmwareRevision = 0;
1260  newDevice->generic.devcaps.dwHardwareRevision = 0;
1261  newDevice->generic.devcaps.dwFFDriverVersion = 0;
1262 
1263  if (TRACE_ON(dinput)) {
1264  TRACE("allocated device %p\n", newDevice);
1265  _dump_DIDATAFORMAT(newDevice->generic.base.data_format.wine_df);
1266  _dump_DIDEVCAPS(&newDevice->generic.devcaps);
1267  }
1268 
1269  *pdev = newDevice;
1270 
1271  return DI_OK;
1272 
1273 FAILED:
1275  if (newDevice->ff) FFReleaseDevice(newDevice->ff);
1276  if (newDevice->elements) CFRelease(newDevice->elements);
1277  if (df) HeapFree(GetProcessHeap(), 0, df->rgodf);
1278  HeapFree(GetProcessHeap(), 0, df);
1279  release_DataFormat(&newDevice->generic.base.data_format);
1280  HeapFree(GetProcessHeap(),0,newDevice->generic.name);
1281  HeapFree(GetProcessHeap(),0,newDevice);
1282  *pdev = 0;
1283 
1284  return hr;
1285 }
1286 
1287 /******************************************************************************
1288  * get_joystick_index : Get the joystick index from a given GUID
1289  */
1290 static unsigned short get_joystick_index(REFGUID guid)
1291 {
1292  GUID wine_joystick = DInput_Wine_OsX_Joystick_GUID;
1293  GUID dev_guid = *guid;
1294 
1295  wine_joystick.Data3 = 0;
1296  dev_guid.Data3 = 0;
1297 
1298  /* for the standard joystick GUID use index 0 */
1299  if(IsEqualGUID(&GUID_Joystick,guid)) return 0;
1300 
1301  /* for the wine joystick GUIDs use the index stored in Data3 */
1302  if(IsEqualGUID(&wine_joystick, &dev_guid)) return guid->Data3;
1303 
1304  return 0xffff;
1305 }
1306 
1307 static HRESULT joydev_create_device(IDirectInputImpl *dinput, REFGUID rguid, REFIID riid, LPVOID *pdev, int unicode)
1308 {
1309  unsigned short index;
1310  int joystick_devices_count;
1311 
1312  TRACE("%p %s %s %p %i\n", dinput, debugstr_guid(rguid), debugstr_guid(riid), pdev, unicode);
1313  *pdev = NULL;
1314 
1315  if ((joystick_devices_count = find_joystick_devices()) == 0)
1316  return DIERR_DEVICENOTREG;
1317 
1318  if ((index = get_joystick_index(rguid)) < 0xffff &&
1319  joystick_devices_count && index < joystick_devices_count)
1320  {
1321  JoystickImpl *This;
1322  HRESULT hr;
1323 
1324  if (riid == NULL)
1325  ;/* nothing */
1326  else if (IsEqualGUID(&IID_IDirectInputDeviceA, riid) ||
1327  IsEqualGUID(&IID_IDirectInputDevice2A, riid) ||
1328  IsEqualGUID(&IID_IDirectInputDevice7A, riid) ||
1329  IsEqualGUID(&IID_IDirectInputDevice8A, riid))
1330  {
1331  unicode = 0;
1332  }
1333  else if (IsEqualGUID(&IID_IDirectInputDeviceW, riid) ||
1334  IsEqualGUID(&IID_IDirectInputDevice2W, riid) ||
1335  IsEqualGUID(&IID_IDirectInputDevice7W, riid) ||
1336  IsEqualGUID(&IID_IDirectInputDevice8W, riid))
1337  {
1338  unicode = 1;
1339  }
1340  else
1341  {
1342  WARN("no interface\n");
1343  return DIERR_NOINTERFACE;
1344  }
1345 
1346  hr = alloc_device(rguid, dinput, &This, index);
1347  if (!This) return hr;
1348 
1349  if (unicode)
1350  *pdev = &This->generic.base.IDirectInputDevice8W_iface;
1351  else
1352  *pdev = &This->generic.base.IDirectInputDevice8A_iface;
1353  return hr;
1354  }
1355 
1356  return DIERR_DEVICENOTREG;
1357 }
1358 
1359 static HRESULT WINAPI JoystickWImpl_GetProperty(LPDIRECTINPUTDEVICE8W iface, REFGUID rguid, LPDIPROPHEADER pdiph)
1360 {
1361  JoystickImpl *This = impl_from_IDirectInputDevice8W(iface);
1362 
1363  TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(rguid), pdiph);
1364  _dump_DIPROPHEADER(pdiph);
1365 
1366  if (!IS_DIPROP(rguid)) return DI_OK;
1367 
1368  switch (LOWORD(rguid)) {
1370  {
1371  static const WCHAR formatW[] = {'\\','\\','?','\\','h','i','d','#','v','i','d','_','%','0','4','x','&',
1372  'p','i','d','_','%','0','4','x','&','%','s','_','%','i',0};
1373  static const WCHAR miW[] = {'m','i',0};
1374  static const WCHAR igW[] = {'i','g',0};
1375 
1376  BOOL is_gamepad;
1377  IOHIDDeviceRef device = get_device_ref(This->id);
1379  WORD vid = get_device_property_long(device, CFSTR(kIOHIDVendorIDKey));
1380  WORD pid = get_device_property_long(device, CFSTR(kIOHIDProductIDKey));
1381 
1382  if (!pid || !vid)
1383  return DIERR_UNSUPPORTED;
1384 
1385  is_gamepad = is_xinput_device(&This->generic.devcaps, vid, pid);
1386  pd->guidClass = GUID_DEVCLASS_HIDCLASS;
1387  sprintfW(pd->wszPath, formatW, vid, pid, is_gamepad ? igW : miW, This->id);
1388 
1389  TRACE("DIPROP_GUIDANDPATH(%s, %s): returning fake path\n", debugstr_guid(&pd->guidClass), debugstr_w(pd->wszPath));
1390  break;
1391  }
1392 
1393  default:
1394  return JoystickWGenericImpl_GetProperty(iface, rguid, pdiph);
1395  }
1396 
1397  return DI_OK;
1398 }
1399 
1400 static HRESULT WINAPI JoystickAImpl_GetProperty(LPDIRECTINPUTDEVICE8A iface, REFGUID rguid, LPDIPROPHEADER pdiph)
1401 {
1402  JoystickImpl *This = impl_from_IDirectInputDevice8A(iface);
1403  return JoystickWImpl_GetProperty(IDirectInputDevice8W_from_impl(This), rguid, pdiph);
1404 }
1405 
1406 static HRESULT osx_set_autocenter(JoystickImpl *This,
1407  const DIPROPDWORD *header)
1408 {
1409  UInt32 v;
1410  HRESULT hr;
1411  if(!This->ff)
1412  return DIERR_UNSUPPORTED;
1413  v = header->dwData;
1414  hr = osx_to_win32_hresult(FFDeviceSetForceFeedbackProperty(This->ff, FFPROP_AUTOCENTER, &v));
1415  TRACE("returning: %08x\n", hr);
1416  return hr;
1417 }
1418 
1419 static HRESULT osx_set_ffgain(JoystickImpl *This, const DIPROPDWORD *header)
1420 {
1421  UInt32 v;
1422  HRESULT hr;
1423  if(!This->ff)
1424  return DIERR_UNSUPPORTED;
1425  v = header->dwData;
1426  hr = osx_to_win32_hresult(FFDeviceSetForceFeedbackProperty(This->ff, FFPROP_FFGAIN, &v));
1427  TRACE("returning: %08x\n", hr);
1428  return hr;
1429 }
1430 
1431 static HRESULT WINAPI JoystickWImpl_SetProperty(IDirectInputDevice8W *iface,
1432  const GUID *prop, const DIPROPHEADER *header)
1433 {
1434  JoystickImpl *This = impl_from_IDirectInputDevice8W(iface);
1435 
1436  TRACE("%p %s %p\n", This, debugstr_guid(prop), header);
1437 
1438  switch(LOWORD(prop))
1439  {
1441  return osx_set_autocenter(This, (const DIPROPDWORD *)header);
1442  case (DWORD_PTR)DIPROP_FFGAIN:
1443  return osx_set_ffgain(This, (const DIPROPDWORD *)header);
1444  }
1445 
1446  return JoystickWGenericImpl_SetProperty(iface, prop, header);
1447 }
1448 
1449 static HRESULT WINAPI JoystickAImpl_SetProperty(IDirectInputDevice8A *iface,
1450  const GUID *prop, const DIPROPHEADER *header)
1451 {
1452  JoystickImpl *This = impl_from_IDirectInputDevice8A(iface);
1453 
1454  TRACE("%p %s %p\n", This, debugstr_guid(prop), header);
1455 
1456  switch(LOWORD(prop))
1457  {
1459  return osx_set_autocenter(This, (const DIPROPDWORD *)header);
1460  case (DWORD_PTR)DIPROP_FFGAIN:
1461  return osx_set_ffgain(This, (const DIPROPDWORD *)header);
1462  }
1463 
1464  return JoystickAGenericImpl_SetProperty(iface, prop, header);
1465 }
1466 
1467 static CFUUIDRef effect_win_to_mac(const GUID *effect)
1468 {
1469 #define DO_MAP(X) \
1470  if(IsEqualGUID(&GUID_##X, effect)) \
1471  return kFFEffectType_##X##_ID;
1472  DO_MAP(ConstantForce)
1473  DO_MAP(RampForce)
1474  DO_MAP(Square)
1475  DO_MAP(Sine)
1476  DO_MAP(Triangle)
1477  DO_MAP(SawtoothUp)
1478  DO_MAP(SawtoothDown)
1479  DO_MAP(Spring)
1480  DO_MAP(Damper)
1481  DO_MAP(Inertia)
1482  DO_MAP(Friction)
1483  DO_MAP(CustomForce)
1484 #undef DO_MAP
1485  WARN("Unknown effect GUID! %s\n", debugstr_guid(effect));
1486  return 0;
1487 }
1488 
1489 static HRESULT WINAPI JoystickWImpl_CreateEffect(IDirectInputDevice8W *iface,
1490  const GUID *type, const DIEFFECT *params, IDirectInputEffect **out,
1491  IUnknown *outer)
1492 {
1493  JoystickImpl *This = impl_from_IDirectInputDevice8W(iface);
1494  EffectImpl *effect;
1495  HRESULT hr;
1496 
1497  TRACE("(%p)->(%s %p %p %p)\n", This, debugstr_guid(type), params, out, outer);
1498  dump_DIEFFECT(params, type, 0);
1499 
1500  if(!This->ff){
1501  TRACE("No force feedback support\n");
1502  *out = NULL;
1503  return DIERR_UNSUPPORTED;
1504  }
1505 
1506  if(outer)
1507  WARN("aggregation not implemented\n");
1508 
1509  effect = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*This));
1510  effect->IDirectInputEffect_iface.lpVtbl = &EffectVtbl;
1511  effect->ref = 1;
1512  effect->guid = *type;
1513  effect->device = This;
1514 
1515  /* Mac's FFEFFECT and Win's DIEFFECT are binary identical. */
1516  hr = osx_to_win32_hresult(FFDeviceCreateEffect(This->ff,
1517  effect_win_to_mac(type), (FFEFFECT*)params, &effect->effect));
1518  if(FAILED(hr)){
1519  WARN("FFDeviceCreateEffect failed: %08x\n", hr);
1520  HeapFree(GetProcessHeap(), 0, effect);
1521  return hr;
1522  }
1523 
1524  list_add_tail(&This->effects, &effect->entry);
1525  *out = &effect->IDirectInputEffect_iface;
1526 
1527  TRACE("allocated effect: %p\n", effect);
1528 
1529  return S_OK;
1530 }
1531 
1532 static HRESULT WINAPI JoystickAImpl_CreateEffect(IDirectInputDevice8A *iface,
1533  const GUID *type, const DIEFFECT *params, IDirectInputEffect **out,
1534  IUnknown *outer)
1535 {
1536  JoystickImpl *This = impl_from_IDirectInputDevice8A(iface);
1537 
1538  TRACE("(%p)->(%s %p %p %p)\n", This, debugstr_guid(type), params, out, outer);
1539 
1540  return JoystickWImpl_CreateEffect(&This->generic.base.IDirectInputDevice8W_iface,
1541  type, params, out, outer);
1542 }
1543 
1544 static HRESULT WINAPI JoystickWImpl_SendForceFeedbackCommand(IDirectInputDevice8W *iface,
1545  DWORD flags)
1546 {
1547  JoystickImpl *This = impl_from_IDirectInputDevice8W(iface);
1548  HRESULT hr;
1549 
1550  TRACE("%p 0x%x\n", This, flags);
1551 
1552  if(!This->ff)
1553  return DI_NOEFFECT;
1554 
1555  hr = osx_to_win32_hresult(FFDeviceSendForceFeedbackCommand(This->ff, flags));
1556  if(FAILED(hr)){
1557  WARN("FFDeviceSendForceFeedbackCommand failed: %08x\n", hr);
1558  return hr;
1559  }
1560 
1561  return S_OK;
1562 }
1563 
1564 static HRESULT WINAPI JoystickAImpl_SendForceFeedbackCommand(IDirectInputDevice8A *iface,
1565  DWORD flags)
1566 {
1567  JoystickImpl *This = impl_from_IDirectInputDevice8A(iface);
1568 
1569  TRACE("%p 0x%x\n", This, flags);
1570 
1571  return JoystickWImpl_SendForceFeedbackCommand(&This->generic.base.IDirectInputDevice8W_iface, flags);
1572 }
1573 
1574 const struct dinput_device joystick_osx_device = {
1575  "Wine OS X joystick driver",
1576  joydev_enum_deviceA,
1577  joydev_enum_deviceW,
1578  joydev_create_device
1579 };
1580 
1581 static const IDirectInputDevice8AVtbl JoystickAvt =
1582 {
1588  JoystickAImpl_GetProperty,
1589  JoystickAImpl_SetProperty,
1601  JoystickAImpl_CreateEffect,
1605  JoystickAImpl_SendForceFeedbackCommand,
1615 };
1616 
1617 static const IDirectInputDevice8WVtbl JoystickWvt =
1618 {
1624  JoystickWImpl_GetProperty,
1625  JoystickWImpl_SetProperty,
1637  JoystickWImpl_CreateEffect,
1641  JoystickWImpl_SendForceFeedbackCommand,
1651 };
1652 
1653 static HRESULT WINAPI effect_QueryInterface(IDirectInputEffect *iface,
1654  const GUID *guid, void **out)
1655 {
1656  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1657 
1658  TRACE("%p %s %p\n", This, debugstr_guid(guid), out);
1659 
1660  if(IsEqualIID(guid, &IID_IUnknown) || IsEqualIID(guid, &IID_IDirectInputEffect)){
1661  *out = iface;
1663  return S_OK;
1664  }
1665 
1666  return E_NOINTERFACE;
1667 }
1668 
1669 static ULONG WINAPI effect_AddRef(IDirectInputEffect *iface)
1670 {
1671  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1673  TRACE("%p, ref is now: %u\n", This, ref);
1674  return ref;
1675 }
1676 
1677 static ULONG WINAPI effect_Release(IDirectInputEffect *iface)
1678 {
1679  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1681  TRACE("%p, ref is now: %u\n", This, ref);
1682 
1683  if(!ref){
1684  list_remove(&This->entry);
1685  FFDeviceReleaseEffect(This->device->ff, This->effect);
1686  HeapFree(GetProcessHeap(), 0, This);
1687  }
1688 
1689  return ref;
1690 }
1691 
1692 static HRESULT WINAPI effect_Initialize(IDirectInputEffect *iface, HINSTANCE hinst,
1693  DWORD version, const GUID *guid)
1694 {
1695  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1696  TRACE("%p %p 0x%x, %s\n", This, hinst, version, debugstr_guid(guid));
1697  return S_OK;
1698 }
1699 
1700 static HRESULT WINAPI effect_GetEffectGuid(IDirectInputEffect *iface, GUID *out)
1701 {
1702  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1703  TRACE("%p %p\n", This, out);
1704  *out = This->guid;
1705  return S_OK;
1706 }
1707 
1708 static HRESULT WINAPI effect_GetParameters(IDirectInputEffect *iface,
1709  DIEFFECT *effect, DWORD flags)
1710 {
1711  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1712  TRACE("%p %p 0x%x\n", This, effect, flags);
1713  return osx_to_win32_hresult(FFEffectGetParameters(This->effect, (FFEFFECT*)effect, flags));
1714 }
1715 
1716 static HRESULT WINAPI effect_SetParameters(IDirectInputEffect *iface,
1717  const DIEFFECT *effect, DWORD flags)
1718 {
1719  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1720  TRACE("%p %p 0x%x\n", This, effect, flags);
1721  dump_DIEFFECT(effect, &This->guid, flags);
1722  return osx_to_win32_hresult(FFEffectSetParameters(This->effect, (FFEFFECT*)effect, flags));
1723 }
1724 
1725 static HRESULT WINAPI effect_Start(IDirectInputEffect *iface, DWORD iterations,
1726  DWORD flags)
1727 {
1728  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1729  TRACE("%p 0x%x 0x%x\n", This, iterations, flags);
1730  return osx_to_win32_hresult(FFEffectStart(This->effect, iterations, flags));
1731 }
1732 
1733 static HRESULT WINAPI effect_Stop(IDirectInputEffect *iface)
1734 {
1735  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1736  TRACE("%p\n", This);
1737  return osx_to_win32_hresult(FFEffectStop(This->effect));
1738 }
1739 
1740 static HRESULT WINAPI effect_GetEffectStatus(IDirectInputEffect *iface, DWORD *flags)
1741 {
1742  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1743  TRACE("%p %p\n", This, flags);
1744  return osx_to_win32_hresult(FFEffectGetEffectStatus(This->effect, (UInt32*)flags));
1745 }
1746 
1747 static HRESULT WINAPI effect_Download(IDirectInputEffect *iface)
1748 {
1749  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1750  TRACE("%p\n", This);
1751  return osx_to_win32_hresult(FFEffectDownload(This->effect));
1752 }
1753 
1754 static HRESULT WINAPI effect_Unload(IDirectInputEffect *iface)
1755 {
1756  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1757  TRACE("%p\n", This);
1758  return osx_to_win32_hresult(FFEffectUnload(This->effect));
1759 }
1760 
1761 static HRESULT WINAPI effect_Escape(IDirectInputEffect *iface, DIEFFESCAPE *escape)
1762 {
1763  EffectImpl *This = impl_from_IDirectInputEffect(iface);
1764  TRACE("%p %p\n", This, escape);
1765  return osx_to_win32_hresult(FFEffectEscape(This->effect, (FFEFFESCAPE*)escape));
1766 }
1767 
1768 static const IDirectInputEffectVtbl EffectVtbl = {
1769  effect_QueryInterface,
1770  effect_AddRef,
1771  effect_Release,
1772  effect_Initialize,
1773  effect_GetEffectGuid,
1774  effect_GetParameters,
1775  effect_SetParameters,
1776  effect_Start,
1777  effect_Stop,
1778  effect_GetEffectStatus,
1779  effect_Download,
1780  effect_Unload,
1781  effect_Escape
1782 };
1783 
1784 #else /* HAVE_IOHIDMANAGERCREATE */
1785 
1787  "Wine OS X joystick driver",
1788  NULL,
1789  NULL,
1790  NULL
1791 };
1792 
1793 #endif /* HAVE_IOHIDMANAGERCREATE */
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble * u
Definition: glfuncs.h:240
HRESULT WINAPI IDirectInputDevice8WImpl_GetImageInfo(LPDIRECTINPUTDEVICE8W iface, LPDIDEVICEIMAGEINFOHEADERW lpdiDevImageInfoHeader)
Definition: device.c:1950
HRESULT WINAPI IDirectInputDevice2WImpl_EnumObjects(LPDIRECTINPUTDEVICE8W iface, LPDIENUMDEVICEOBJECTSCALLBACKW lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1352
GUID guidInstance
Definition: dinput.h:413
#define IDirectInput_AddRef(p)
Definition: dinput.h:2293
_In_ ULONG_PTR _In_ ULONG _Out_ ULONG_PTR * pid
Definition: winddi.h:3835
HRESULT WINAPI JoystickAGenericImpl_GetCapabilities(LPDIRECTINPUTDEVICE8A iface, LPDIDEVCAPS lpDIDevCaps)
Definition: joystick.c:554
HRESULT WINAPI IDirectInputDevice2AImpl_GetDeviceData(LPDIRECTINPUTDEVICE8A iface, DWORD dodsize, LPDIDEVICEOBJECTDATA dod, LPDWORD entries, DWORD flags)
Definition: device.c:1685
#define E_ACCESSDENIED
Definition: winerror.h:2849
Definition: pdh_main.c:93
#define REFIID
Definition: guiddef.h:118
HRESULT WINAPI IDirectInputDevice2AImpl_SendDeviceData(LPDIRECTINPUTDEVICE8A iface, DWORD cbObjectData, LPCDIDEVICEOBJECTDATA rgdod, LPDWORD pdwInOut, DWORD dwFlags)
Definition: device.c:1867
DWORD dwDevType
Definition: dinput.h:428
#define E_NOINTERFACE
Definition: winerror.h:2364
HRESULT WINAPI JoystickAGenericImpl_SetProperty(LPDIRECTINPUTDEVICE8A iface, REFGUID rguid, LPCDIPROPHEADER ph)
Definition: joystick.c:473
#define E_HANDLE
Definition: winerror.h:2850
DWORD dwSize
Definition: dinput.h:808
static IDirectInputDevice8W * IDirectInputDevice8W_from_impl(IDirectInputDeviceImpl *This)
Definition: device.c:60
#define DWORD_PTR
Definition: treelist.c:76
HRESULT hr
Definition: shlfolder.c:183
GLuint64EXT * result
Definition: glext.h:11304
Definition: scsiwmi.h:51
HRESULT WINAPI JoystickWGenericImpl_GetProperty(LPDIRECTINPUTDEVICE8W iface, REFGUID rguid, LPDIPROPHEADER pdiph)
Definition: joystick.c:610
HRESULT WINAPI IDirectInputDevice2AImpl_EnumObjects(LPDIRECTINPUTDEVICE8A iface, LPDIENUMDEVICEOBJECTSCALLBACKA lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1322
Definition: http.c:7251
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
#define DIDFT_PSHBUTTON
Definition: dinput.h:754
#define TRUE
Definition: types.h:120
REFIID riid
Definition: precomp.h:44
DWORD UInt32
Definition: chm_lib.c:104
#define CP_ACP
Definition: compat.h:109
DWORD dwNumObjs
Definition: dinput.h:812
HRESULT WINAPI IDirectInputDevice2WImpl_Acquire(LPDIRECTINPUTDEVICE8W iface)
Definition: device.c:1076
const char * devices
Definition: diskspace.c:793
#define WARN(fmt,...)
Definition: debug.h:112
HRESULT WINAPI JoystickAGenericImpl_GetDeviceInfo(LPDIRECTINPUTDEVICE8A iface, LPDIDEVICEINSTANCEA pdidi)
Definition: joystick.c:689
#define DIDFT_MAKEINSTANCE(n)
Definition: dinput.h:762
GLdouble GLdouble t
Definition: gl.h:2047
#define DIDC_ATTACHED
Definition: dinput.h:945
#define UInt8
Definition: interfaces.hpp:75
DWORD dwObjSize
Definition: dinput.h:809
#define assert(x)
Definition: debug.h:53
HRESULT WINAPI IDirectInputDevice2AImpl_RunControlPanel(LPDIRECTINPUTDEVICE8A iface, HWND hwndOwner, DWORD dwFlags)
Definition: device.c:1700
struct list devices_list
#define DIEDFL_FORCEFEEDBACK
Definition: dinput.h:192
GUID guidFFDriver
Definition: dinput.h:431
#define IDirectInputEffect_AddRef(p)
Definition: dinput.h:1508
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
HRESULT WINAPI JoystickWGenericImpl_Poll(LPDIRECTINPUTDEVICE8W iface)
Definition: joystick.c:779
HRESULT WINAPI IDirectInputDevice7WImpl_WriteEffectToFile(LPDIRECTINPUTDEVICE8W iface, LPCWSTR lpszFileName, DWORD dwEntries, LPDIFILEEFFECT rgDiFileEft, DWORD dwFlags)
Definition: device.c:1912
HRESULT WINAPI JoystickWGenericImpl_GetObjectInfo(LPDIRECTINPUTDEVICE8W iface, LPDIDEVICEOBJECTINSTANCEW pdidoi, DWORD dwObj, DWORD dwHow)
Definition: joystick.c:563
static WCHAR name1[]
Definition: record.c:34
#define E_FAIL
Definition: ddrawi.h:102
ULONG WINAPI IDirectInputDevice2WImpl_AddRef(LPDIRECTINPUTDEVICE8W iface)
Definition: device.c:1308
BOOL is_xinput_device(const DIDEVCAPS *devcaps, WORD vid, WORD pid)
Definition: joystick.c:312
int32_t INT
Definition: typedefs.h:58
Definition: send.c:48
static HWND child
Definition: cursoricon.c:298
static IDirectInputDeviceImpl * impl_from_IDirectInputDevice8A(IDirectInputDevice8A *iface)
Definition: device.c:47
#define DIDFT_ABSAXIS
Definition: dinput.h:752
#define DIERR_UNSUPPORTED
Definition: dinput.h:156
const char * wine_dbg_sprintf(const char *format,...)
Definition: compat.c:296
FxDevice * device
#define sprintf(buf, format,...)
Definition: sprintf.c:55
__WINE_SERVER_LIST_INLINE void list_add_tail(struct list *list, struct list *elem)
Definition: list.h:102
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
const GUID * guid
#define L(x)
Definition: ntvdm.h:50
WCHAR wszPath[MAX_PATH]
Definition: dinput.h:869
#define GetCurrentTime
Definition: winbase.h:2080
DWORD get_device_type(DWORD version, BOOL is_joystick) DECLSPEC_HIDDEN
Definition: joystick.c:107
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define FALSE
Definition: types.h:117
GLenum const GLfloat * params
Definition: glext.h:5645
unsigned int BOOL
Definition: ntddk_ex.h:94
long LONG
Definition: pedump.c:60
Definition: devices.h:37
HRESULT WINAPI IDirectInputDevice2WImpl_SendDeviceData(LPDIRECTINPUTDEVICE8W iface, DWORD cbObjectData, LPCDIDEVICEOBJECTDATA rgdod, LPDWORD pdwInOut, DWORD dwFlags)
Definition: device.c:1857
static size_t double number
Definition: printf.c:69
HRESULT WINAPI JoystickAGenericImpl_SetActionMap(LPDIRECTINPUTDEVICE8A iface, LPDIACTIONFORMATA lpdiaf, LPCSTR lpszUserName, DWORD dwFlags)
Definition: joystick.c:948
if SUCCEEDED(hr)
HRESULT WINAPI JoystickWGenericImpl_SetProperty(LPDIRECTINPUTDEVICE8W iface, REFGUID rguid, LPCDIPROPHEADER ph)
Definition: joystick.c:398
#define debugstr_w
Definition: kernel32.h:32
GLenum GLint ref
Definition: glext.h:6028
#define FIXME(fmt,...)
Definition: debug.h:111
GLenum GLuint GLenum GLsizei length
Definition: glext.h:5579
DWORD dwDevType
Definition: dinput.h:415
unsigned int idx
Definition: utils.c:41
void _dump_DIDEVCAPS(const DIDEVCAPS *lpDIDevCaps)
Definition: joystick.c:480
#define S_FALSE
Definition: winerror.h:2357
#define DIDOI_FFACTUATOR
Definition: dinput.h:817
HRESULT WINAPI JoystickAGenericImpl_GetDeviceState(LPDIRECTINPUTDEVICE8A iface, DWORD len, LPVOID ptr)
Definition: joystick.c:824
struct DIPROPGUIDANDPATH * LPDIPROPGUIDANDPATH
#define E_INVALIDARG
Definition: ddrawi.h:101
GUID guidProduct
Definition: dinput.h:414
const WCHAR * str
#define MAKELONG(a, b)
Definition: typedefs.h:249
VOID WINAPI InitializeCriticalSection(OUT LPCRITICAL_SECTION lpCriticalSection)
Definition: synch.c:751
static const WCHAR version[]
Definition: asmname.c:66
HRESULT WINAPI IDirectInputDevice2AImpl_Escape(LPDIRECTINPUTDEVICE8A iface, LPDIEFFESCAPE lpDIEEsc)
Definition: device.c:1835
Definition: module.h:566
GLuint index
Definition: glext.h:6031
#define debugstr_guid
Definition: kernel32.h:35
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
HRESULT WINAPI IDirectInputDevice2AImpl_EnumCreatedEffectObjects(LPDIRECTINPUTDEVICE8A iface, LPDIENUMCREATEDEFFECTOBJECTSCALLBACK lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1821
GLuint GLfloat * val
Definition: glext.h:7180
const GUID DInput_PIDVID_Product_GUID
Definition: joystick.c:61
HRESULT WINAPI JoystickAGenericImpl_GetObjectInfo(LPDIRECTINPUTDEVICE8A iface, LPDIDEVICEOBJECTINSTANCEA pdidoi, DWORD dwObj, DWORD dwHow)
Definition: joystick.c:586
__WINE_SERVER_LIST_INLINE void list_remove(struct list *elem)
Definition: list.h:108
HRESULT WINAPI IDirectInputDevice7AImpl_EnumEffectsInFile(LPDIRECTINPUTDEVICE8A iface, LPCSTR lpszFileName, LPDIENUMEFFECTSINFILECALLBACK pec, LPVOID pvRef, DWORD dwFlags)
Definition: device.c:1876
HRESULT WINAPI IDirectInputDevice8AImpl_GetImageInfo(LPDIRECTINPUTDEVICE8A iface, LPDIDEVICEIMAGEINFOHEADERA lpdiDevImageInfoHeader)
Definition: device.c:1941
static SysKeyboardImpl * alloc_device(REFGUID rguid, IDirectInputImpl *dinput)
Definition: keyboard.c:255
void _dump_DIDATAFORMAT(const DIDATAFORMAT *df)
Definition: device.c:242
#define TRACE(s)
Definition: solgame.cpp:4
HRESULT WINAPI IDirectInputDevice2WImpl_SetEventNotification(LPDIRECTINPUTDEVICE8W iface, HANDLE event)
Definition: device.c:1212
HRESULT WINAPI IDirectInputDevice2WImpl_RunControlPanel(LPDIRECTINPUTDEVICE8W iface, HWND hwndOwner, DWORD dwFlags)
Definition: device.c:1692
static IDirectInputDeviceImpl * impl_from_IDirectInputDevice8W(IDirectInputDevice8W *iface)
Definition: device.c:51
void _dump_DIPROPHEADER(LPCDIPROPHEADER diph)
Definition: device.c:176
#define GetProcessHeap()
Definition: compat.h:595
HRESULT WINAPI IDirectInputDevice7AImpl_WriteEffectToFile(LPDIRECTINPUTDEVICE8A iface, LPCSTR lpszFileName, DWORD dwEntries, LPDIFILEEFFECT rgDiFileEft, DWORD dwFlags)
Definition: device.c:1900
PVOID WINAPI HeapAlloc(HANDLE, DWORD, SIZE_T)
HRESULT WINAPI IDirectInputDevice2WImpl_SetDataFormat(LPDIRECTINPUTDEVICE8W iface, LPCDIDATAFORMAT df)
Definition: device.c:1135
#define DIERR_OUTOFMEMORY
Definition: dinput.h:155
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define debugstr_a
Definition: kernel32.h:31
LONG HRESULT
Definition: typedefs.h:79
const GUID IID_IUnknown
HRESULT WINAPI IDirectInputDevice2AImpl_EnumEffects(LPDIRECTINPUTDEVICE8A iface, LPDIENUMEFFECTSCALLBACKA lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1743
#define MAX_PATH
Definition: compat.h:34
#define WINAPI
Definition: msvc.h:6
HRESULT WINAPI IDirectInputDevice2WImpl_EnumEffects(LPDIRECTINPUTDEVICE8W iface, LPDIENUMEFFECTSCALLBACKW lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1755
unsigned short WORD
Definition: ntddk_ex.h:93
static FILE * out
Definition: regtests2xml.c:44
#define DIERR_DEVICENOTREG
Definition: dinput.h:147
unsigned long DWORD
Definition: ntddk_ex.h:95
#define DIPROP_FFGAIN
Definition: dinput.h:895
#define DIDEVTYPE_JOYSTICK
Definition: dinput.h:200
HRESULT WINAPI IDirectInputDevice2WImpl_Initialize(LPDIRECTINPUTDEVICE8W iface, HINSTANCE hinst, DWORD dwVersion, REFGUID rguid)
Definition: device.c:1706
#define DI8DEVTYPEJOYSTICK_STANDARD
Definition: dinput.h:274
HRESULT WINAPI IDirectInputDevice2WImpl_GetDeviceData(LPDIRECTINPUTDEVICE8W iface, DWORD dodsize, LPDIDEVICEOBJECTDATA dod, LPDWORD entries, DWORD flags)
Definition: device.c:1629
GLbitfield flags
Definition: glext.h:7161
HRESULT WINAPI IDirectInputDevice2WImpl_Escape(LPDIRECTINPUTDEVICE8W iface, LPDIEFFESCAPE lpDIEEsc)
Definition: device.c:1828
HRESULT WINAPI IDirectInputDevice2AImpl_GetEffectInfo(LPDIRECTINPUTDEVICE8A iface, LPDIEFFECTINFOA lpdei, REFGUID rguid)
Definition: device.c:1767
WCHAR tszProductName[MAX_PATH]
Definition: dinput.h:430
int ret
#define index(s, c)
Definition: various.h:29
#define InterlockedDecrement
Definition: armddk.h:52
HRESULT WINAPI IDirectInputDevice2WImpl_QueryInterface(LPDIRECTINPUTDEVICE8W iface, REFIID riid, LPVOID *ppobj)
Definition: device.c:1273
HRESULT WINAPI IDirectInputDevice2AImpl_Unacquire(LPDIRECTINPUTDEVICE8A iface)
Definition: device.c:1125
ULONG WINAPI IDirectInputDevice2AImpl_Release(LPDIRECTINPUTDEVICE8A iface)
Definition: device.c:1267
_In_ PCCERT_CONTEXT _In_ DWORD dwFlags
Definition: wincrypt.h:1175
GLsizeiptr const GLvoid GLenum usage
Definition: glext.h:5919
uint32_t entry
Definition: isohybrid.c:63
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
void dump_DIEFFECT(LPCDIEFFECT eff, REFGUID guid, DWORD dwFlags)
Definition: joystick.c:190
CHAR tszInstanceName[MAX_PATH]
Definition: dinput.h:416
#define GUID_NULL
Definition: ks.h:106
GLdouble s
Definition: gl.h:2039
Definition: _list.h:228
#define DI_NOEFFECT
Definition: dinput.h:132
LPDIOBJECTDATAFORMAT rgodf
Definition: dinput.h:813
#define DIDEVTYPEJOYSTICK_TRADITIONAL
Definition: dinput.h:243
HRESULT WINAPI IDirectInputDevice2AImpl_QueryInterface(LPDIRECTINPUTDEVICE8A iface, REFIID riid, LPVOID *ppobj)
Definition: device.c:1302
#define DIPROP_GUIDANDPATH
Definition: dinput.h:908
#define E_ABORT
Definition: winerror.h:2366
uint32_t DWORD_PTR
Definition: typedefs.h:65
WCHAR tszInstanceName[MAX_PATH]
Definition: dinput.h:429
#define debugstr_wn
Definition: kernel32.h:33
const DIDATAFORMAT c_dfDIJoystick2
Definition: data_formats.c:251
#define DI8DEVTYPE_JOYSTICK
Definition: dinput.h:212
HRESULT WINAPI IDirectInputDevice2WImpl_GetEffectInfo(LPDIRECTINPUTDEVICE8W iface, LPDIEFFECTINFOW lpdei, REFGUID rguid)
Definition: device.c:1777
HRESULT WINAPI JoystickAGenericImpl_BuildActionMap(LPDIRECTINPUTDEVICE8A iface, LPDIACTIONFORMATA lpdiaf, LPCSTR lpszUserName, DWORD dwFlags)
Definition: joystick.c:906
#define ERR(fmt,...)
Definition: debug.h:110
#define DIPROP_AUTOCENTER
Definition: dinput.h:897
void release_DataFormat(DataFormat *format)
Definition: device.c:391
#define S_OK
Definition: intsafe.h:52
HRESULT WINAPI IDirectInputDevice2AImpl_SetCooperativeLevel(LPDIRECTINPUTDEVICE8A iface, HWND hwnd, DWORD dwflags)
Definition: device.c:1203
CRITICAL_SECTION crit
struct IDirectInputDevice8W * LPDIRECTINPUTDEVICE8W
Definition: dinput.h:106
#define InterlockedIncrement
Definition: armddk.h:53
HRESULT WINAPI IDirectInputDevice2AImpl_GetForceFeedbackState(LPDIRECTINPUTDEVICE8A iface, LPDWORD pdwOut)
Definition: device.c:1794
const GLdouble * v
Definition: gl.h:2040
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLuint in
Definition: glext.h:9616
const GUID * pguid
Definition: dinput.h:800
HWND buttons[5]
Definition: sndrec32.cpp:40
#define DIERR_NOINTERFACE
Definition: dinput.h:153
HRESULT WINAPI IDirectInputDevice2WImpl_SetCooperativeLevel(LPDIRECTINPUTDEVICE8W iface, HWND hwnd, DWORD dwflags)
Definition: device.c:1167
HRESULT WINAPI JoystickWGenericImpl_BuildActionMap(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, LPCWSTR lpszUserName, DWORD dwFlags)
Definition: joystick.c:831
const struct dinput_device joystick_osx_device
HRESULT WINAPI IDirectInputDevice7WImpl_EnumEffectsInFile(LPDIRECTINPUTDEVICE8W iface, LPCWSTR lpszFileName, LPDIENUMEFFECTSINFILECALLBACK pec, LPVOID pvRef, DWORD dwFlags)
Definition: device.c:1888
HRESULT WINAPI JoystickAGenericImpl_Poll(LPDIRECTINPUTDEVICE8A iface)
Definition: joystick.c:794
#define ARRAY_SIZE(a)
Definition: main.h:24
#define DIDEVTYPE_HID
Definition: dinput.h:201
#define DIDFT_POV
Definition: dinput.h:757
ULONG WINAPI IDirectInputDevice2AImpl_AddRef(LPDIRECTINPUTDEVICE8A iface)
Definition: device.c:1316
#define E_NOTIMPL
Definition: ddrawi.h:99
#define sprintfW
Definition: unicode.h:58
GUID guidFFDriver
Definition: dinput.h:418
LONG joystick_map_axis(ObjProps *props, int val) DECLSPEC_HIDDEN
Definition: joystick.c:985
HRESULT WINAPI JoystickWGenericImpl_GetCapabilities(LPDIRECTINPUTDEVICE8W iface, LPDIDEVCAPS lpDIDevCaps)
Definition: joystick.c:526
#define min(a, b)
Definition: monoChain.cc:55
HRESULT WINAPI IDirectInputDevice2AImpl_Acquire(LPDIRECTINPUTDEVICE8A iface)
Definition: device.c:1097
#define NULL
Definition: types.h:112
BOOL WINAPI IsEqualGUID(REFGUID rguid1, REFGUID rguid2)
Definition: compobj.c:4112
HRESULT WINAPI JoystickWGenericImpl_GetDeviceState(LPDIRECTINPUTDEVICE8W iface, DWORD len, LPVOID ptr)
Definition: joystick.c:804
#define HEAP_ZERO_MEMORY
Definition: compat.h:134
UINT32 uint32_t
Definition: types.h:75
size_t total
GUID guidInstance
Definition: dinput.h:426
HRESULT WINAPI IDirectInputDevice2AImpl_SetDataFormat(LPDIRECTINPUTDEVICE8A iface, LPCDIDATAFORMAT df)
Definition: device.c:1156
#define MultiByteToWideChar
Definition: compat.h:110
#define E_UNEXPECTED
Definition: winerror.h:2456
CHAR tszProductName[MAX_PATH]
Definition: dinput.h:417
static WCHAR escape[]
Definition: url.c:36
void queue_event(LPDIRECTINPUTDEVICE8A iface, int inst_id, DWORD data, DWORD time, DWORD seq)
Definition: device.c:1025
struct IDirectInputDevice8A * LPDIRECTINPUTDEVICE8A
Definition: dinput.h:105
HRESULT WINAPI IDirectInputDevice2WImpl_EnumCreatedEffectObjects(LPDIRECTINPUTDEVICE8W iface, LPDIENUMCREATEDEFFECTOBJECTSCALLBACK lpCallback, LPVOID lpvRef, DWORD dwFlags)
Definition: device.c:1813
Definition: name.c:38
HRESULT WINAPI JoystickWGenericImpl_GetDeviceInfo(LPDIRECTINPUTDEVICE8W iface, LPDIDEVICEINSTANCEW pdidi)
Definition: joystick.c:737
#define DI_OK
Definition: dinput.h:128
__WINE_SERVER_LIST_INLINE void list_init(struct list *list)
Definition: list.h:149
char * strcpy(char *DstString, const char *SrcString)
Definition: utclib.c:388
HRESULT WINAPI IDirectInputDevice2WImpl_Unacquire(LPDIRECTINPUTDEVICE8W iface)
Definition: device.c:1108
unsigned int ULONG
Definition: retypes.h:1
GLenum GLuint id
Definition: glext.h:5579
static HINSTANCE hinst
Definition: edit.c:551
static WCHAR name2[]
Definition: record.c:35
#define IS_DIPROP(x)
GLdouble GLdouble GLdouble GLdouble top
Definition: glext.h:10859
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
#define DI8DEVCLASS_GAMECTRL
Definition: dinput.h:207
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
#define E_POINTER
Definition: winerror.h:2365
#define memset(x, y, z)
Definition: compat.h:39
#define TRACE_ON(x)
Definition: compat.h:75
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define DIDC_FORCEFEEDBACK
Definition: dinput.h:949
HRESULT WINAPI JoystickWGenericImpl_SetActionMap(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, LPCWSTR lpszUserName, DWORD dwFlags)
Definition: joystick.c:936
#define LOWORD(l)
Definition: pedump.c:82
#define HeapFree(x, y, z)
Definition: compat.h:594
HRESULT WINAPI IDirectInputDevice2AImpl_SetEventNotification(LPDIRECTINPUTDEVICE8A iface, HANDLE event)
Definition: device.c:1224
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
HRESULT WINAPI IDirectInputDevice2WImpl_GetForceFeedbackState(LPDIRECTINPUTDEVICE8W iface, LPDWORD pdwOut)
Definition: device.c:1787
Definition: path.c:41
ULONG WINAPI IDirectInputDevice2WImpl_Release(LPDIRECTINPUTDEVICE8W iface)
Definition: device.c:1231
GUID guidProduct
Definition: dinput.h:427
HRESULT WINAPI IDirectInputDevice2AImpl_Initialize(LPDIRECTINPUTDEVICE8A iface, HINSTANCE hinst, DWORD dwVersion, REFGUID rguid)
Definition: device.c:1714
GLuint const GLchar * name
Definition: glext.h:6031