wine  6.0.1
About: Wine is an Open Source implementation of the MS Windows API on top of X, OpenGL, and Unix. Think of Wine as a compatibility layer for running Windows programs.
  Fossies Dox: wine-6.0.1.tar.xz  ("unofficial" and yet experimental doxygen-generated source code documentation)  

pnp.c
Go to the documentation of this file.
1 /*
2  * Plug and Play
3  *
4  * Copyright 2016 Sebastian Lackner
5  * Copyright 2016 Aric Stewart for CodeWeavers
6  * Copyright 2019 Zebediah Figura
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 <stdarg.h>
24 
25 #define NONAMELESSUNION
26 
27 #include "ntstatus.h"
28 #define WIN32_NO_STATUS
29 #include "windef.h"
30 #include "winbase.h"
31 #include "winioctl.h"
32 #include "winreg.h"
33 #include "winuser.h"
34 #include "winsvc.h"
35 #include "winternl.h"
36 #include "setupapi.h"
37 #include "cfgmgr32.h"
38 #include "dbt.h"
39 #include "ddk/wdm.h"
40 #include "ddk/ntifs.h"
41 #include "wine/debug.h"
42 #include "wine/exception.h"
43 #include "wine/heap.h"
44 #include "wine/rbtree.h"
45 
46 #include "ntoskrnl_private.h"
47 #include "plugplay.h"
48 
49 #include "initguid.h"
50 DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
51 
53 
54 #define MAX_SERVICE_NAME 260
55 
57 {
58  struct wine_rb_entry entry;
59 
64 };
65 
66 static int interface_rb_compare( const void *key, const struct wine_rb_entry *entry)
67 {
68  const struct device_interface *iface = WINE_RB_ENTRY_VALUE( entry, const struct device_interface, entry );
69  const UNICODE_STRING *k = key;
70 
71  return RtlCompareUnicodeString( k, &iface->symbolic_link, FALSE );
72 }
73 
75 
77 {
78  HANDLE event = context;
79  SetEvent( event );
81 }
82 
84 {
85  HANDLE event = CreateEventA( NULL, FALSE, FALSE, NULL );
86  DEVICE_OBJECT *toplevel_device;
88 
91 
92  toplevel_device = IoGetAttachedDeviceReference( device );
93  status = IoCallDriver( toplevel_device, irp );
94 
95  if (status == STATUS_PENDING)
97 
98  status = irp->IoStatus.u.Status;
99  if (info)
100  *info = irp->IoStatus.Information;
102  ObDereferenceObject( toplevel_device );
103  CloseHandle( event );
104  return status;
105 }
106 
108 {
109  IO_STACK_LOCATION *irpsp;
110  IO_STATUS_BLOCK irp_status;
111  IRP *irp;
112 
114 
115  if (!(irp = IoBuildSynchronousFsdRequest( IRP_MJ_PNP, device, NULL, 0, NULL, NULL, &irp_status )))
116  return STATUS_NO_MEMORY;
117 
118  irpsp = IoGetNextIrpStackLocation( irp );
120  irpsp->Parameters.QueryId.IdType = type;
121 
122  return send_device_irp( device, irp, (ULONG_PTR *)id );
123 }
124 
126 {
127  IO_STACK_LOCATION *irpsp;
128  IO_STATUS_BLOCK irp_status;
129  IRP *irp;
130 
132 
133  if (!(irp = IoBuildSynchronousFsdRequest( IRP_MJ_PNP, device, NULL, 0, NULL, NULL, &irp_status )))
134  return STATUS_NO_MEMORY;
135 
136  irpsp = IoGetNextIrpStackLocation( irp );
137  irpsp->MinorFunction = minor;
138 
139  irpsp->Parameters.StartDevice.AllocatedResources = NULL;
140  irpsp->Parameters.StartDevice.AllocatedResourcesTranslated = NULL;
141 
142  return send_device_irp( device, irp, NULL );
143 }
144 
146 {
147  static const WCHAR backslashW[] = {'\\',0};
149  WCHAR *id;
150 
151  if ((status = get_device_id( device, BusQueryDeviceID, &id )))
152  {
153  ERR("Failed to get device ID, status %#x.\n", status);
154  return status;
155  }
156 
157  lstrcpyW( buffer, id );
158  ExFreePool( id );
159 
161  {
162  ERR("Failed to get instance ID, status %#x.\n", status);
163  return status;
164  }
165 
167  lstrcatW( buffer, id );
168  ExFreePool( id );
169 
170  TRACE("Returning ID %s.\n", debugstr_w(buffer));
171 
172  return STATUS_SUCCESS;
173 }
174 
176 {
177  IO_STATUS_BLOCK irp_status;
178  IO_STACK_LOCATION *irpsp;
179  IRP *irp;
180 
182 
183  if (!(irp = IoBuildSynchronousFsdRequest( IRP_MJ_POWER, device, NULL, 0, NULL, NULL, &irp_status )))
184  return STATUS_NO_MEMORY;
185 
186  irpsp = IoGetNextIrpStackLocation( irp );
188 
189  irpsp->Parameters.Power.Type = DevicePowerState;
190  irpsp->Parameters.Power.State.DeviceState = power;
191 
192  return send_device_irp( device, irp, NULL );
193 }
194 
196 {
197  static const WCHAR driverW[] = {'\\','D','r','i','v','e','r','\\',0};
203 
205  NULL, (BYTE *)driver, sizeof(driver), NULL ))
206  {
207  WARN("No driver registered for device %p.\n", device);
208  return;
209  }
210 
212  lstrcatW( buffer, driver );
213  RtlInitUnicodeString( &string, buffer );
214  status = ZwLoadDriver( &string );
216  {
217  ERR("Failed to load driver %s, status %#x.\n", debugstr_w(driver), status);
218  return;
219  }
220 
221  lstrcpyW( buffer, driverW );
222  lstrcatW( buffer, driver );
223  RtlInitUnicodeString( &string, buffer );
225  0, NULL, KernelMode, NULL, (void **)&driver_obj ) != STATUS_SUCCESS)
226  {
227  ERR("Failed to locate loaded driver %s.\n", debugstr_w(driver));
228  return;
229  }
230 
231  TRACE("Calling AddDevice routine %p.\n", driver_obj->DriverExtension->AddDevice);
234  else
236  TRACE("AddDevice routine %p returned %#x.\n", driver_obj->DriverExtension->AddDevice, status);
237 
239 
240  if (status != STATUS_SUCCESS)
241  ERR("AddDevice failed for driver %s, status %#x.\n", debugstr_w(driver), status);
242 }
243 
244 /* Return the total number of characters in a REG_MULTI_SZ string, including
245  * the final terminating null. */
246 static size_t sizeof_multiszW( const WCHAR *str )
247 {
248  const WCHAR *p;
249  for (p = str; *p; p += lstrlenW(p) + 1);
250  return p + 1 - str;
251 }
252 
253 /* This does almost the same thing as UpdateDriverForPlugAndPlayDevices(),
254  * except that we don't know the INF path beforehand. */
256 {
257  static const DWORD dif_list[] =
258  {
267  };
268 
270  unsigned int i;
271  WCHAR *ids;
272 
274  {
275  ERR("Failed to get hardware IDs, status %#x.\n", status);
276  return FALSE;
277  }
278 
280  sizeof_multiszW( ids ) * sizeof(WCHAR) );
281  ExFreePool( ids );
282 
284  {
285  ERR("Failed to get compatible IDs, status %#x.\n", status);
286  return FALSE;
287  }
288 
290  sizeof_multiszW( ids ) * sizeof(WCHAR) );
291  ExFreePool( ids );
292 
294  {
295  ERR("Failed to build compatible driver list, error %#x.\n", GetLastError());
296  return FALSE;
297  }
298 
299  for (i = 0; i < ARRAY_SIZE(dif_list); ++i)
300  {
301  if (!SetupDiCallClassInstaller(dif_list[i], set, sp_device) && GetLastError() != ERROR_DI_DO_DEFAULT)
302  {
303  WARN("Install function %#x failed, error %#x.\n", dif_list[i], GetLastError());
304  return FALSE;
305  }
306  }
307 
308  return TRUE;
309 }
310 
311 /* Load the function driver for a newly created PDO, if one is present, and
312  * send IRPs to start the device. */
314 {
315  load_function_driver( device, set, sp_device );
316  if (device->DriverObject)
317  {
320  }
321 }
322 
324 {
325  static const WCHAR infpathW[] = {'I','n','f','P','a','t','h',0};
326 
327  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
328  WCHAR device_instance_id[MAX_DEVICE_ID_LEN];
329  BOOL need_driver = TRUE;
330  HKEY key;
331 
332  if (get_device_instance_id( device, device_instance_id ))
333  return;
334 
335  if (!SetupDiCreateDeviceInfoW( set, device_instance_id, &GUID_NULL, NULL, NULL, 0, &sp_device )
336  && !SetupDiOpenDeviceInfoW( set, device_instance_id, NULL, 0, &sp_device ))
337  {
338  ERR("Failed to create or open device %s, error %#x.\n", debugstr_w(device_instance_id), GetLastError());
340  return;
341  }
342 
343  TRACE("Creating new device %s.\n", debugstr_w(device_instance_id));
344 
345  /* Check if the device already has a driver registered; if not, find one
346  * and install it. */
348  if (key != INVALID_HANDLE_VALUE)
349  {
350  if (!RegQueryValueExW( key, infpathW, NULL, NULL, NULL, NULL ))
351  need_driver = FALSE;
352  RegCloseKey( key );
353  }
354 
355  if (need_driver && !install_device_driver( device, set, &sp_device ))
356  {
358  return;
359  }
360 
361  start_device( device, set, &sp_device );
362 }
363 
365 {
367 
368  TRACE("Removing device %p.\n", device);
369 
370  if (wine_device->children)
371  {
372  ULONG i;
373  for (i = 0; i < wine_device->children->Count; ++i)
375  }
376 
380 }
381 
383 {
384  ULONG i;
385  for (i = 0; i < list->Count; ++i)
386  {
387  if (list->Objects[i] == device)
388  return TRUE;
389  }
390  return FALSE;
391 }
392 
393 static void handle_bus_relations( DEVICE_OBJECT *parent )
394 {
395  struct wine_device *wine_parent = CONTAINING_RECORD(parent, struct wine_device, device_obj);
396  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
397  DEVICE_RELATIONS *relations;
398  IO_STATUS_BLOCK irp_status;
399  IO_STACK_LOCATION *irpsp;
401  HDEVINFO set;
402  IRP *irp;
403  ULONG i;
404 
405  TRACE( "(%p)\n", parent );
406 
408 
409  parent = IoGetAttachedDevice( parent );
410 
411  if (!(irp = IoBuildSynchronousFsdRequest( IRP_MJ_PNP, parent, NULL, 0, NULL, NULL, &irp_status )))
412  {
414  return;
415  }
416 
417  irpsp = IoGetNextIrpStackLocation( irp );
420  if ((status = send_device_irp( parent, irp, (ULONG_PTR *)&relations )))
421  {
422  ERR("Failed to enumerate child devices, status %#x.\n", status);
424  return;
425  }
426 
427  TRACE("Got %u devices.\n", relations->Count);
428 
429  for (i = 0; i < relations->Count; ++i)
430  {
431  DEVICE_OBJECT *child = relations->Objects[i];
432 
433  if (!wine_parent->children || !device_in_list( wine_parent->children, child ))
434  {
435  TRACE("Adding new device %p.\n", child);
436  enumerate_new_device( child, set );
437  }
438  }
439 
440  if (wine_parent->children)
441  {
442  for (i = 0; i < wine_parent->children->Count; ++i)
443  {
444  DEVICE_OBJECT *child = wine_parent->children->Objects[i];
445 
446  if (!device_in_list( relations, child ))
447  {
448  TRACE("Removing device %p.\n", child);
449  remove_device( child );
450  }
451  ObDereferenceObject( child );
452  }
453  }
454 
455  ExFreePool( wine_parent->children );
456  wine_parent->children = relations;
457 
459 }
460 
461 /***********************************************************************
462  * IoInvalidateDeviceRelations (NTOSKRNL.EXE.@)
463  */
465 {
466  TRACE("device %p, type %#x.\n", device_object, type);
467 
468  switch (type)
469  {
470  case BusRelations:
471  handle_bus_relations( device_object );
472  break;
473  default:
474  FIXME("Unhandled relation %#x.\n", type);
475  break;
476  }
477 }
478 
479 /***********************************************************************
480  * IoGetDeviceProperty (NTOSKRNL.EXE.@)
481  */
483  ULONG length, void *buffer, ULONG *needed )
484 {
485  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
486  WCHAR device_instance_id[MAX_DEVICE_ID_LEN];
487  DWORD sp_property = -1;
489  HDEVINFO set;
490 
491  TRACE("device %p, property %u, length %u, buffer %p, needed %p.\n",
492  device, property, length, buffer, needed);
493 
494  switch (property)
495  {
497  {
498  WCHAR *id, *ptr;
499 
501  if (status != STATUS_SUCCESS)
502  {
503  ERR("Failed to get instance ID, status %#x.\n", status);
504  break;
505  }
506 
507  wcsupr( id );
508  ptr = wcschr( id, '\\' );
509  if (ptr) *ptr = 0;
510 
511  *needed = sizeof(WCHAR) * (lstrlenW(id) + 1);
512  if (length >= *needed)
513  memcpy( buffer, id, *needed );
514  else
516 
517  ExFreePool( id );
518  return status;
519  }
521  {
522  ULONG used_len, len = length + sizeof(OBJECT_NAME_INFORMATION);
524  HANDLE handle;
525 
527  if (!status)
528  {
529  status = NtQueryObject( handle, ObjectNameInformation, name, len, &used_len );
530  NtClose( handle );
531  }
532  if (status == STATUS_SUCCESS)
533  {
534  /* Ensure room for NULL termination */
535  if (length >= name->Name.MaximumLength)
536  memcpy(buffer, name->Name.Buffer, name->Name.MaximumLength);
537  else
539  *needed = name->Name.MaximumLength;
540  }
541  else
542  {
545  {
547  *needed = used_len - sizeof(OBJECT_NAME_INFORMATION);
548  }
549  else
550  *needed = 0;
551  }
553  return status;
554  }
556  sp_property = SPDRP_DEVICEDESC;
557  break;
559  sp_property = SPDRP_HARDWAREID;
560  break;
562  sp_property = SPDRP_COMPATIBLEIDS;
563  break;
565  sp_property = SPDRP_CLASS;
566  break;
568  sp_property = SPDRP_CLASSGUID;
569  break;
571  sp_property = SPDRP_MFG;
572  break;
574  sp_property = SPDRP_FRIENDLYNAME;
575  break;
577  sp_property = SPDRP_LOCATION_INFORMATION;
578  break;
580  sp_property = SPDRP_BUSTYPEGUID;
581  break;
583  sp_property = SPDRP_LEGACYBUSTYPE;
584  break;
586  sp_property = SPDRP_BUSNUMBER;
587  break;
589  sp_property = SPDRP_ADDRESS;
590  break;
592  sp_property = SPDRP_UI_NUMBER;
593  break;
595  sp_property = SPDRP_INSTALL_STATE;
596  break;
598  sp_property = SPDRP_REMOVAL_POLICY;
599  break;
600  default:
601  FIXME("Unhandled property %u.\n", property);
602  return STATUS_NOT_IMPLEMENTED;
603  }
604 
605  if ((status = get_device_instance_id( device, device_instance_id )))
606  return status;
607 
609  {
610  ERR("Failed to create device list, error %#x.\n", GetLastError());
611  return GetLastError();
612  }
613 
614  if (!SetupDiOpenDeviceInfoW( set, device_instance_id, NULL, 0, &sp_device))
615  {
616  ERR("Failed to open device, error %#x.\n", GetLastError());
618  return GetLastError();
619  }
620 
621  if (SetupDiGetDeviceRegistryPropertyW( set, &sp_device, sp_property, NULL, buffer, length, needed ))
623  else
624  status = GetLastError();
625 
627 
628  return status;
629 }
630 
632 {
633  UNICODE_STRING device_nameU;
634  WCHAR *device_name;
635  ULONG len = 0;
636  NTSTATUS ret;
637 
639  if (ret != STATUS_BUFFER_TOO_SMALL)
640  return ret;
641 
642  device_name = heap_alloc( len );
644  if (ret)
645  {
646  heap_free( device_name );
647  return ret;
648  }
649 
650  RtlInitUnicodeString( &device_nameU, device_name );
651  ret = IoCreateSymbolicLink( symlink_name, &device_nameU );
652  heap_free( device_name );
653  return ret;
654 }
655 
656 void __RPC_FAR * __RPC_USER MIDL_user_allocate( SIZE_T len )
657 {
658  return heap_alloc( len );
659 }
660 
661 void __RPC_USER MIDL_user_free( void __RPC_FAR *ptr )
662 {
663  heap_free( ptr );
664 }
665 
667 {
669 }
670 
671 static void send_devicechange( DWORD code, void *data, unsigned int size )
672 {
673  __TRY
674  {
676  }
678  {
679  WARN("Failed to send event, exception %#x.\n", GetExceptionCode());
680  }
681  __ENDTRY
682 }
683 
684 /***********************************************************************
685  * IoSetDeviceInterfaceState (NTOSKRNL.EXE.@)
686  */
688 {
689  static const WCHAR DeviceClassesW[] = {'\\','R','E','G','I','S','T','R','Y','\\',
690  'M','a','c','h','i','n','e','\\','S','y','s','t','e','m','\\',
691  'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\',
692  'C','o','n','t','r','o','l','\\',
693  'D','e','v','i','c','e','C','l','a','s','s','e','s','\\',0};
694  static const WCHAR controlW[] = {'C','o','n','t','r','o','l',0};
695  static const WCHAR linkedW[] = {'L','i','n','k','e','d',0};
696  static const WCHAR slashW[] = {'\\',0};
697  static const WCHAR hashW[] = {'#',0};
698 
699  size_t namelen = name->Length / sizeof(WCHAR);
701  struct device_interface *iface;
702  HANDLE iface_key, control_key;
703  OBJECT_ATTRIBUTES attr = {0};
704  struct wine_rb_entry *entry;
705  WCHAR *path, *refstr, *p;
707  DWORD data = enable;
708  NTSTATUS ret;
709  ULONG len;
710 
711  TRACE("device %s, enable %u.\n", debugstr_us(name), enable);
712 
713  entry = wine_rb_get( &device_interfaces, name );
714  if (!entry)
716 
717  iface = WINE_RB_ENTRY_VALUE( entry, struct device_interface, entry );
718 
719  if (!enable && !iface->enabled)
721 
722  if (enable && iface->enabled)
724 
725  for (p = name->Buffer + 4, refstr = NULL; p < name->Buffer + namelen; p++)
726  if (*p == '\\') refstr = p;
727  if (!refstr) refstr = p;
728 
729  len = lstrlenW(DeviceClassesW) + 38 + 1 + namelen + 2 + 1;
730 
731  if (!(path = heap_alloc( len * sizeof(WCHAR) )))
732  return STATUS_NO_MEMORY;
733 
734  lstrcpyW( path, DeviceClassesW );
735  lstrcpynW( path + lstrlenW( path ), refstr - 38, 39 );
736  lstrcatW( path, slashW );
737  p = path + lstrlenW( path );
738  lstrcpynW( path + lstrlenW( path ), name->Buffer, (refstr - name->Buffer) + 1 );
739  p[0] = p[1] = p[3] = '#';
740  lstrcatW( path, slashW );
741  lstrcatW( path, hashW );
742  if (refstr < name->Buffer + namelen)
743  lstrcpynW( path + lstrlenW( path ), refstr, name->Buffer + namelen - refstr + 1 );
744 
745  attr.Length = sizeof(attr);
746  attr.ObjectName = &string;
747  RtlInitUnicodeString( &string, path );
748  ret = NtOpenKey( &iface_key, KEY_CREATE_SUB_KEY, &attr );
749  heap_free(path);
750  if (ret)
751  return ret;
752 
753  attr.RootDirectory = iface_key;
754  RtlInitUnicodeString( &string, controlW );
755  ret = NtCreateKey( &control_key, KEY_SET_VALUE, &attr, 0, NULL, REG_OPTION_VOLATILE, NULL );
756  NtClose( iface_key );
757  if (ret)
758  return ret;
759 
760  RtlInitUnicodeString( &string, linkedW );
761  ret = NtSetValueKey( control_key, &string, 0, REG_DWORD, &data, sizeof(data) );
762  if (ret)
763  {
764  NtClose( control_key );
765  return ret;
766  }
767 
768  if (enable)
769  ret = create_device_symlink( iface->device, name );
770  else
771  ret = IoDeleteSymbolicLink( name );
772  if (ret)
773  {
774  NtDeleteValueKey( control_key, &string );
775  NtClose( control_key );
776  return ret;
777  }
778 
779  iface->enabled = enable;
780 
781  len = offsetof(DEV_BROADCAST_DEVICEINTERFACE_W, dbcc_name[namelen + 1]);
782 
783  if ((broadcast = heap_alloc( len )))
784  {
785  broadcast->dbcc_size = len;
787  broadcast->dbcc_reserved = 0;
788  broadcast->dbcc_classguid = iface->interface_class;
789  lstrcpynW( broadcast->dbcc_name, name->Buffer, namelen + 1 );
791  heap_free( broadcast );
792  }
793  return ret;
794 }
795 
796 /***********************************************************************
797  * IoRegisterDeviceInterface (NTOSKRNL.EXE.@)
798  */
800  UNICODE_STRING *refstr, UNICODE_STRING *symbolic_link)
801 {
802  SP_DEVICE_INTERFACE_DATA sp_iface = {sizeof(sp_iface)};
803  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
804  WCHAR device_instance_id[MAX_DEVICE_ID_LEN];
807  UNICODE_STRING device_path;
808  struct device_interface *iface;
809  struct wine_rb_entry *entry;
810  DWORD required;
811  HDEVINFO set;
812 
813  TRACE("device %p, class_guid %s, refstr %s, symbolic_link %p.\n",
814  device, debugstr_guid(class_guid), debugstr_us(refstr), symbolic_link);
815 
816  if ((status = get_device_instance_id( device, device_instance_id )))
817  return status;
818 
821 
822  if (!SetupDiCreateDeviceInfoW( set, device_instance_id, class_guid, NULL, NULL, 0, &sp_device )
823  && !SetupDiOpenDeviceInfoW( set, device_instance_id, NULL, 0, &sp_device ))
824  {
825  ERR("Failed to create device %s, error %#x.\n", debugstr_w(device_instance_id), GetLastError());
826  return GetLastError();
827  }
828 
829  if (!SetupDiCreateDeviceInterfaceW( set, &sp_device, class_guid, refstr ? refstr->Buffer : NULL, 0, &sp_iface ))
830  return STATUS_UNSUCCESSFUL;
831 
832  required = 0;
834  if (required == 0) return STATUS_UNSUCCESSFUL;
835 
837  data->cbSize = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA_W);
838 
840  {
841  HeapFree( GetProcessHeap(), 0, data );
842  return STATUS_UNSUCCESSFUL;
843  }
844 
845  data->DevicePath[1] = '?';
846  TRACE("Returning path %s.\n", debugstr_w(data->DevicePath));
847  RtlCreateUnicodeString( &device_path, data->DevicePath);
848 
849  entry = wine_rb_get( &device_interfaces, &device_path );
850  if (entry)
851  {
852  iface = WINE_RB_ENTRY_VALUE( entry, struct device_interface, entry );
853  if (iface->enabled)
854  ERR("Device interface %s is still enabled.\n", debugstr_us(&iface->symbolic_link));
855  }
856  else
857  {
858  iface = heap_alloc_zero( sizeof(struct device_interface) );
859  RtlCreateUnicodeString(&iface->symbolic_link, data->DevicePath);
860  if (wine_rb_put( &device_interfaces, &iface->symbolic_link, &iface->entry ))
861  ERR("Failed to insert interface %s into tree.\n", debugstr_us(&iface->symbolic_link));
862  }
863 
864  iface->device = device;
865  iface->interface_class = *class_guid;
866  if (symbolic_link)
867  RtlCreateUnicodeString( symbolic_link, data->DevicePath);
868 
869  HeapFree( GetProcessHeap(), 0, data );
870 
871  RtlFreeUnicodeString( &device_path );
872 
873  return status;
874 }
875 
876 /***********************************************************************
877  * IoOpenDeviceRegistryKey (NTOSKRNL.EXE.@)
878  */
880 {
881  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
882  WCHAR device_instance_id[MAX_DEVICE_ID_LEN];
884  HDEVINFO set;
885 
886  TRACE("device %p, type %#x, access %#x, key %p.\n", device, type, access, key);
887 
888  if ((status = get_device_instance_id( device, device_instance_id )))
889  {
890  ERR("Failed to get device instance ID, error %#x.\n", status);
891  return status;
892  }
893 
895 
896  SetupDiOpenDeviceInfoW( set, device_instance_id, NULL, 0, &sp_device );
897 
898  *key = SetupDiOpenDevRegKey( set, &sp_device, DICS_FLAG_GLOBAL, 0, type, access );
900  if (*key == INVALID_HANDLE_VALUE)
901  return GetLastError();
902  return STATUS_SUCCESS;
903 }
904 
905 /***********************************************************************
906  * PoSetPowerState (NTOSKRNL.EXE.@)
907  */
909 {
910  FIXME("device %p, type %u, state %u, stub!\n", device, type, state.DeviceState);
911  return state;
912 }
913 
914 /*****************************************************
915  * PoStartNextPowerIrp (NTOSKRNL.EXE.@)
916  */
918 {
919  FIXME("irp %p, stub!\n", irp);
920 }
921 
922 /*****************************************************
923  * PoCallDriver (NTOSKRNL.EXE.@)
924  */
926 {
927  TRACE("device %p, irp %p.\n", device, irp);
928  return IoCallDriver( device, irp );
929 }
930 
932 
934 {
936  struct wine_rb_entry entry;
938 };
939 
940 static int root_pnp_devices_rb_compare( const void *key, const struct wine_rb_entry *entry )
941 {
942  const struct root_pnp_device *device = WINE_RB_ENTRY_VALUE( entry, const struct root_pnp_device, entry );
943  const WCHAR *k = key;
944 
945  return wcsicmp( k, device->id );
946 }
947 
949 
951 {
953  struct root_pnp_device *root_device = device->DeviceExtension;
955 
956  TRACE("device %p, irp %p, minor function %#x.\n", device, irp, stack->MinorFunction);
957 
958  switch (stack->MinorFunction)
959  {
961  /* The FDO above already handled this, so return the same status. */
962  break;
963  case IRP_MN_START_DEVICE:
966  /* Nothing to do. */
967  irp->IoStatus.u.Status = STATUS_SUCCESS;
968  break;
970  irp->IoStatus.u.Status = STATUS_SUCCESS;
971  break;
972  case IRP_MN_QUERY_ID:
973  {
974  BUS_QUERY_ID_TYPE type = stack->Parameters.QueryId.IdType;
975  WCHAR *id, *p;
976 
977  TRACE("Received IRP_MN_QUERY_ID, type %#x.\n", type);
978 
979  switch (type)
980  {
981  case BusQueryDeviceID:
982  p = wcsrchr( root_device->id, '\\' );
983  if ((id = ExAllocatePool( NonPagedPool, (p - root_device->id + 1) * sizeof(WCHAR) )))
984  {
985  memcpy( id, root_device->id, (p - root_device->id) * sizeof(WCHAR) );
986  id[p - root_device->id] = 0;
987  irp->IoStatus.Information = (ULONG_PTR)id;
988  irp->IoStatus.u.Status = STATUS_SUCCESS;
989  }
990  else
991  {
992  irp->IoStatus.Information = 0;
994  }
995  break;
996  case BusQueryInstanceID:
997  p = wcsrchr( root_device->id, '\\' );
998  if ((id = ExAllocatePool( NonPagedPool, (wcslen( p + 1 ) + 1) * sizeof(WCHAR) )))
999  {
1000  wcscpy( id, p + 1 );
1001  irp->IoStatus.Information = (ULONG_PTR)id;
1002  irp->IoStatus.u.Status = STATUS_SUCCESS;
1003  }
1004  else
1005  {
1006  irp->IoStatus.Information = 0;
1007  irp->IoStatus.u.Status = STATUS_NO_MEMORY;
1008  }
1009  break;
1010  default:
1011  FIXME("Unhandled IRP_MN_QUERY_ID type %#x.\n", type);
1012  }
1013  break;
1014  }
1015  default:
1016  FIXME("Unhandled PnP request %#x.\n", stack->MinorFunction);
1017  }
1018 
1019  status = irp->IoStatus.u.Status;
1021  return status;
1022 }
1023 
1025 {
1026  pnp_manager = driver;
1027  driver->MajorFunction[IRP_MJ_PNP] = pnp_manager_device_pnp;
1028  return STATUS_SUCCESS;
1029 }
1030 
1032 {
1033  static const WCHAR driver_nameW[] = {'\\','D','r','i','v','e','r','\\','P','n','p','M','a','n','a','g','e','r',0};
1034  WCHAR endpoint[] = L"\\pipe\\wine_plugplay";
1035  WCHAR protseq[] = L"ncalrpc";
1036  UNICODE_STRING driver_nameU;
1037  RPC_WSTR binding_str;
1038  NTSTATUS status;
1039  RPC_STATUS err;
1040 
1041  RtlInitUnicodeString( &driver_nameU, driver_nameW );
1042  if ((status = IoCreateDriver( &driver_nameU, pnp_manager_driver_entry )))
1043  ERR("Failed to create PnP manager driver, status %#x.\n", status);
1044 
1045  if ((err = RpcStringBindingComposeW( NULL, protseq, NULL, endpoint, NULL, &binding_str )))
1046  {
1047  ERR("RpcStringBindingCompose() failed, error %#x\n", err);
1048  return;
1049  }
1050  err = RpcBindingFromStringBindingW( binding_str, &plugplay_binding_handle );
1051  RpcStringFreeW( &binding_str );
1052  if (err)
1053  ERR("RpcBindingFromStringBinding() failed, error %#x\n", err);
1054 }
1055 
1057 {
1059  remove_device( device->device );
1060 }
1061 
1063 {
1066  RpcBindingFree( &plugplay_binding_handle );
1067 }
1068 
1069 void pnp_manager_enumerate_root_devices( const WCHAR *driver_name )
1070 {
1071  static const WCHAR driverW[] = {'\\','D','r','i','v','e','r','\\',0};
1072  static const WCHAR rootW[] = {'R','O','O','T',0};
1074  SP_DEVINFO_DATA sp_device = {sizeof(sp_device)};
1075  struct root_pnp_device *pnp_device;
1077  NTSTATUS status;
1078  unsigned int i;
1079  HDEVINFO set;
1080 
1081  TRACE("Searching for new root-enumerated devices for driver %s.\n", debugstr_w(driver_name));
1082 
1084  if (set == INVALID_HANDLE_VALUE)
1085  {
1086  ERR("Failed to build device set, error %#x.\n", GetLastError());
1087  return;
1088  }
1089 
1090  for (i = 0; SetupDiEnumDeviceInfo( set, i, &sp_device ); ++i)
1091  {
1093  NULL, (BYTE *)buffer, sizeof(buffer), NULL )
1094  || lstrcmpiW( buffer, driver_name ))
1095  {
1096  continue;
1097  }
1098 
1099  SetupDiGetDeviceInstanceIdW( set, &sp_device, id, ARRAY_SIZE(id), NULL );
1100 
1101  if (wine_rb_get( &root_pnp_devices, id ))
1102  continue;
1103 
1104  TRACE("Adding new root-enumerated device %s.\n", debugstr_w(id));
1105 
1106  if ((status = IoCreateDevice( pnp_manager, sizeof(struct root_pnp_device), NULL,
1108  {
1109  ERR("Failed to create root-enumerated PnP device %s, status %#x.\n", debugstr_w(id), status);
1110  continue;
1111  }
1112 
1113  pnp_device = device->DeviceExtension;
1114  wcscpy( pnp_device->id, id );
1117  {
1118  ERR("Failed to insert device %s into tree.\n", debugstr_w(id));
1120  continue;
1121  }
1122 
1123  start_device( device, set, &sp_device );
1124  }
1125 
1127 }
BOOL required
Definition: adapter_vk.c:1810
static LPCSTR debugstr_us(const UNICODE_STRING *us)
Definition: lsa.c:47
unsigned long ULONG_PTR
Definition: basetsd.h:130
ULONG_PTR SIZE_T
Definition: basetsd.h:264
LONG NTSTATUS
Definition: bcrypt.h:40
#define WINAPI
Definition: bcrypt.h:23
enum shader_type type
unsigned char minor
#define MAX_DEVICE_ID_LEN
Definition: cfgmgr32.h:106
Definition: type.pm:7
#define ERR(...)
Definition: cocoa_app.h:61
static UINT set(struct ID3DXConstantTableImpl *table, IDirect3DDevice9 *device, struct ctab_constant *constant, const void **indata, D3DXPARAMETER_TYPE intype, UINT *size, UINT incol, D3DXPARAMETER_CLASS inclass, UINT index, BOOL is_pointer)
Definition: shader.c:1062
#define DBT_DEVICEARRIVAL
Definition: dbt.h:40
#define DBT_DEVTYP_DEVICEINTERFACE
Definition: dbt.h:60
#define DBT_DEVICEREMOVECOMPLETE
Definition: dbt.h:44
BOOL SetupDiEnumDeviceInfo(HDEVINFO devinfo, DWORD index, SP_DEVINFO_DATA *device_data)
Definition: devinst.c:1759
HKEY SetupDiOpenDevRegKey(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, DWORD Scope, DWORD HwProfile, DWORD KeyType, REGSAM samDesired)
Definition: devinst.c:3961
BOOL SetupDiCreateDeviceInterfaceW(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, const GUID *class, const WCHAR *refstr, DWORD flags, SP_DEVICE_INTERFACE_DATA *iface_data)
Definition: devinst.c:2610
BOOL SetupDiDestroyDeviceInfoList(HDEVINFO devinfo)
Definition: devinst.c:2841
BOOL SetupDiGetDeviceRegistryPropertyW(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, DWORD Property, DWORD *PropertyRegDataType, BYTE *PropertyBuffer, DWORD PropertyBufferSize, DWORD *RequiredSize)
Definition: devinst.c:3021
BOOL SetupDiOpenDeviceInfoW(HDEVINFO devinfo, PCWSTR instance_id, HWND hwnd_parent, DWORD flags, PSP_DEVINFO_DATA device_data)
Definition: devinst.c:3451
HDEVINFO SetupDiGetClassDevsW(const GUID *class, LPCWSTR enumstr, HWND parent, DWORD flags)
Definition: devinst.c:2480
BOOL SetupDiSetDeviceRegistryPropertyW(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, DWORD prop, const BYTE *buffer, DWORD size)
Definition: devinst.c:3091
BOOL SetupDiCreateDeviceInfoW(HDEVINFO devinfo, const WCHAR *name, const GUID *class, const WCHAR *description, HWND parent, DWORD flags, SP_DEVINFO_DATA *device_data)
Definition: devinst.c:1557
static const WCHAR backslashW[]
Definition: devinst.c:104
BOOL SetupDiGetDeviceInstanceIdW(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, WCHAR *DeviceInstanceId, DWORD DeviceInstanceIdSize, DWORD *RequiredSize)
Definition: devinst.c:1822
BOOL SetupDiBuildDriverInfoList(HDEVINFO devinfo, SP_DEVINFO_DATA *device_data, DWORD type)
Definition: devinst.c:4607
BOOL SetupDiGetDeviceInterfaceDetailW(HDEVINFO devinfo, SP_DEVICE_INTERFACE_DATA *iface_data, SP_DEVICE_INTERFACE_DETAIL_DATA_W *DeviceInterfaceDetailData, DWORD DeviceInterfaceDetailDataSize, DWORD *RequiredSize, SP_DEVINFO_DATA *device_data)
Definition: devinst.c:2923
HDEVINFO SetupDiCreateDeviceInfoList(const GUID *ClassGuid, HWND hwndParent)
Definition: devinst.c:1336
BOOL SetupDiCallClassInstaller(DI_FUNCTION function, HDEVINFO devinfo, SP_DEVINFO_DATA *device_data)
Definition: devinst.c:3656
int id
Definition: main.c:4907
BOOL CloseHandle(HANDLE handle)
Definition: process.c:390
LSTATUS RegQueryValueExW(HKEY hkey, LPCWSTR name, LPDWORD reserved, LPDWORD type, LPBYTE data, LPDWORD count)
Definition: registry.c:1424
LSTATUS RegCloseKey(HKEY hkey)
Definition: registry.c:964
int lstrcmpiW(LPCWSTR str1, LPCWSTR str2)
Definition: string.c:86
void * memcpy(void *dst, const void *src, size_t n)
Definition: string.c:2580
NTSTATUS NtQueryObject(HANDLE handle, OBJECT_INFORMATION_CLASS info_class, void *ptr, ULONG len, ULONG *used_len)
Definition: file.c:6497
NTSTATUS NtSetValueKey(HANDLE key, const UNICODE_STRING *name, ULONG index, ULONG type, const void *data, ULONG count)
Definition: registry.c:508
NTSTATUS NtOpenKey(HANDLE *key, ACCESS_MASK access, const OBJECT_ATTRIBUTES *attr)
Definition: registry.c:124
NTSTATUS NtCreateKey(HANDLE *key, ACCESS_MASK access, const OBJECT_ATTRIBUTES *attr, ULONG index, const UNICODE_STRING *class, ULONG options, ULONG *dispos)
Definition: registry.c:45
NTSTATUS NtDeleteValueKey(HANDLE key, const UNICODE_STRING *name)
Definition: registry.c:534
NTSTATUS NtClose(HANDLE handle)
Definition: server.c:1666
static DRIVER_OBJECT * driver_obj
Definition: main.c:97
@ L
Definition: bidi.c:78
long BOOL
Definition: dxgitype.idl:24
NTSTATUS status
Definition: except.c:81
#define __TRY
Definition: exception.h:136
#define __ENDTRY
Definition: exception.h:179
#define __EXCEPT(func)
Definition: exception.h:143
#define GetExceptionCode()
Definition: exception.h:222
GLuint err
Definition: glu.c:32
const char * str
Definition: glu.c:32
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8)
Definition: guiddef.h:102
static void heap_free(void *mem)
Definition: heap.h:44
static DEVICE_OBJECT * device_obj
Definition: http.c:32
#define WINE_DEFAULT_DEBUG_CHANNEL(ch)
Definition: debug.h:499
static int access(const char *path, int mode)
Definition: io.h:110
LPWSTR lstrcatW(LPWSTR dst, LPCWSTR src)
Definition: virtual.c:277
LPWSTR lstrcpyW(LPWSTR dst, LPCWSTR src)
Definition: virtual.c:317
HANDLE CreateEventA(SECURITY_ATTRIBUTES *sa, BOOL manual_reset, BOOL initial_state, LPCSTR name)
Definition: sync.c:377
DWORD WaitForSingleObject(HANDLE handle, DWORD timeout)
Definition: sync.c:299
BOOL SetEvent(HANDLE handle)
Definition: sync.c:504
struct version_info info
Definition: version.c:140
int k
Definition: mpi.c:3366
static void size_t len
USHORT * data
Definition: env.c:81
void IoCompleteRequest(IRP *irp, UCHAR priority_boost)
Definition: ntoskrnl.c:1901
void ExFreePool(void *ptr)
Definition: ntoskrnl.c:2103
DEVICE_OBJECT * IoGetAttachedDevice(DEVICE_OBJECT *device)
Definition: ntoskrnl.c:1193
NTSTATUS IoCreateDevice(DRIVER_OBJECT *driver, ULONG ext_size, UNICODE_STRING *name, DWORD type, ULONG characteristics, BOOLEAN exclusive, DEVICE_OBJECT **ret_device)
Definition: ntoskrnl.c:1490
void ObDereferenceObject(void *obj)
Definition: ntoskrnl.c:185
void IoDeleteDevice(DEVICE_OBJECT *device)
Definition: ntoskrnl.c:1561
NTSTATUS IoCallDriver(DEVICE_OBJECT *device, IRP *irp)
Definition: ntoskrnl.c:1692
PVOID ExAllocatePool(POOL_TYPE type, SIZE_T size)
Definition: ntoskrnl.c:2039
NTSTATUS IoCreateDriver(UNICODE_STRING *name, PDRIVER_INITIALIZE init)
Definition: ntoskrnl.c:1415
void IoDeleteDriver(DRIVER_OBJECT *driver_object)
Definition: ntoskrnl.c:1465
PIRP IoBuildSynchronousFsdRequest(ULONG majorfunc, PDEVICE_OBJECT device, PVOID buffer, ULONG length, PLARGE_INTEGER startoffset, PKEVENT event, PIO_STATUS_BLOCK iosb)
Definition: ntoskrnl.c:1344
DEVICE_OBJECT * IoGetAttachedDeviceReference(DEVICE_OBJECT *device)
Definition: ntoskrnl.c:2907
NTSTATUS ObOpenObjectByPointer(void *obj, ULONG attr, ACCESS_STATE *access_state, ACCESS_MASK access, POBJECT_TYPE type, KPROCESSOR_MODE mode, HANDLE *handle)
Definition: ntoskrnl.c:372
NTSTATUS ObReferenceObjectByName(UNICODE_STRING *ObjectName, ULONG Attributes, ACCESS_STATE *AccessState, ACCESS_MASK DesiredAccess, POBJECT_TYPE ObjectType, KPROCESSOR_MODE AccessMode, void *ParseContext, void **Object)
Definition: ntoskrnl.c:2767
NTSTATUS IoDeleteSymbolicLink(UNICODE_STRING *name)
Definition: ntoskrnl.c:1636
NTSTATUS ZwLoadDriver(const UNICODE_STRING *service_name)
Definition: ntoskrnl.c:3733
NTSTATUS IoCreateSymbolicLink(UNICODE_STRING *name, UNICODE_STRING *target)
Definition: ntoskrnl.c:1590
static void destroy_root_pnp_device(struct wine_rb_entry *entry, void *context)
Definition: pnp.c:1056
static LONG rpc_filter(EXCEPTION_POINTERS *eptr)
Definition: pnp.c:666
const GUID GUID_NULL
static NTSTATUS get_device_id(DEVICE_OBJECT *device, BUS_QUERY_ID_TYPE type, WCHAR **id)
Definition: pnp.c:107
static size_t sizeof_multiszW(const WCHAR *str)
Definition: pnp.c:246
static NTSTATUS internal_complete(DEVICE_OBJECT *device, IRP *irp, void *context)
Definition: pnp.c:76
NTSTATUS IoGetDeviceProperty(DEVICE_OBJECT *device, DEVICE_REGISTRY_PROPERTY property, ULONG length, void *buffer, ULONG *needed)
Definition: pnp.c:482
static void send_devicechange(DWORD code, void *data, unsigned int size)
Definition: pnp.c:671
#define MAX_SERVICE_NAME
Definition: pnp.c:54
static void handle_bus_relations(DEVICE_OBJECT *parent)
Definition: pnp.c:393
static NTSTATUS create_device_symlink(DEVICE_OBJECT *device, UNICODE_STRING *symlink_name)
Definition: pnp.c:631
NTSTATUS IoOpenDeviceRegistryKey(DEVICE_OBJECT *device, ULONG type, ACCESS_MASK access, HANDLE *key)
Definition: pnp.c:879
static NTSTATUS send_pnp_irp(DEVICE_OBJECT *device, UCHAR minor)
Definition: pnp.c:125
static void start_device(DEVICE_OBJECT *device, HDEVINFO set, SP_DEVINFO_DATA *sp_device)
Definition: pnp.c:313
void PoStartNextPowerIrp(IRP *irp)
Definition: pnp.c:917
NTSTATUS IoRegisterDeviceInterface(DEVICE_OBJECT *device, const GUID *class_guid, UNICODE_STRING *refstr, UNICODE_STRING *symbolic_link)
Definition: pnp.c:799
NTSTATUS PoCallDriver(DEVICE_OBJECT *device, IRP *irp)
Definition: pnp.c:925
void __RPC_USER MIDL_user_free(void __RPC_FAR *ptr)
Definition: pnp.c:661
static BOOL device_in_list(const DEVICE_RELATIONS *list, const DEVICE_OBJECT *device)
Definition: pnp.c:382
static NTSTATUS get_device_instance_id(DEVICE_OBJECT *device, WCHAR *buffer)
Definition: pnp.c:145
static int interface_rb_compare(const void *key, const struct wine_rb_entry *entry)
Definition: pnp.c:66
void pnp_manager_stop(void)
Definition: pnp.c:1062
static struct wine_rb_tree device_interfaces
Definition: pnp.c:74
void IoInvalidateDeviceRelations(DEVICE_OBJECT *device_object, DEVICE_RELATION_TYPE type)
Definition: pnp.c:464
POWER_STATE PoSetPowerState(DEVICE_OBJECT *device, POWER_STATE_TYPE type, POWER_STATE state)
Definition: pnp.c:908
static void enumerate_new_device(DEVICE_OBJECT *device, HDEVINFO set)
Definition: pnp.c:323
static void load_function_driver(DEVICE_OBJECT *device, HDEVINFO set, SP_DEVINFO_DATA *sp_device)
Definition: pnp.c:195
static void remove_device(DEVICE_OBJECT *device)
Definition: pnp.c:364
static NTSTATUS pnp_manager_driver_entry(DRIVER_OBJECT *driver, UNICODE_STRING *keypath)
Definition: pnp.c:1024
static struct wine_rb_tree root_pnp_devices
Definition: pnp.c:948
void __RPC_FAR *__RPC_USER MIDL_user_allocate(SIZE_T len)
Definition: pnp.c:656
static int root_pnp_devices_rb_compare(const void *key, const struct wine_rb_entry *entry)
Definition: pnp.c:940
NTSTATUS IoSetDeviceInterfaceState(UNICODE_STRING *name, BOOLEAN enable)
Definition: pnp.c:687
static NTSTATUS pnp_manager_device_pnp(DEVICE_OBJECT *device, IRP *irp)
Definition: pnp.c:950
void pnp_manager_start(void)
Definition: pnp.c:1031
static DRIVER_OBJECT * pnp_manager
Definition: pnp.c:931
static BOOL install_device_driver(DEVICE_OBJECT *device, HDEVINFO set, SP_DEVINFO_DATA *sp_device)
Definition: pnp.c:255
static NTSTATUS send_power_irp(DEVICE_OBJECT *device, DEVICE_POWER_STATE power)
Definition: pnp.c:175
static NTSTATUS send_device_irp(DEVICE_OBJECT *device, IRP *irp, ULONG_PTR *info)
Definition: pnp.c:83
void pnp_manager_enumerate_root_devices(const WCHAR *driver_name)
Definition: pnp.c:1069
static const WCHAR servicesW[]
PSecurityUserData *typedef PSECPKG_EXTENDED_INFORMATION *typedef ULONG
Definition: ntsecpkg.h:377
#define STATUS_MORE_PROCESSING_REQUIRED
Definition: ntstatus.h:232
#define STATUS_IMAGE_ALREADY_LOADED
Definition: ntstatus.h:480
#define STATUS_OBJECT_NAME_EXISTS
Definition: ntstatus.h:87
#define STATUS_PENDING
Definition: ntstatus.h:48
#define STATUS_NO_MEMORY
Definition: ntstatus.h:233
#define STATUS_UNSUCCESSFUL
Definition: ntstatus.h:211
#define STATUS_NOT_SUPPORTED
Definition: ntstatus.h:397
#define STATUS_NOT_IMPLEMENTED
Definition: ntstatus.h:212
#define STATUS_BUFFER_TOO_SMALL
Definition: ntstatus.h:245
#define STATUS_INFO_LENGTH_MISMATCH
Definition: ntstatus.h:214
#define STATUS_BUFFER_OVERFLOW
Definition: ntstatus.h:157
#define STATUS_SUCCESS
Definition: ntstatus.h:30
#define STATUS_OBJECT_NAME_NOT_FOUND
Definition: ntstatus.h:262
void plugplay_send_event(DWORD code, const BYTE *data, unsigned int size)
Definition: main.c:140
void * heap_alloc(size_t len)
Definition: util.c:30
static void wine_rb_destroy(struct wine_rb_tree *tree, wine_rb_traverse_func_t *callback, void *context)
Definition: rbtree.h:192
static struct wine_rb_entry * wine_rb_get(const struct wine_rb_tree *tree, const void *key)
Definition: rbtree.h:197
#define WINE_RB_ENTRY_VALUE(element, type, field)
Definition: rbtree.h:26
static int wine_rb_put(struct wine_rb_tree *tree, const void *key, struct wine_rb_entry *entry)
Definition: rbtree.h:209
HKEY key
Definition: registrar.c:33
RPC_STATUS RpcBindingFromStringBindingW(RPC_WSTR StringBinding, RPC_BINDING_HANDLE *Binding)
Definition: rpc_binding.c:875
RPC_STATUS RpcBindingFree(RPC_BINDING_HANDLE *Binding)
Definition: rpc_binding.c:782
RPC_STATUS RpcStringBindingComposeW(RPC_WSTR ObjUuid, RPC_WSTR Protseq, RPC_WSTR NetworkAddr, RPC_WSTR Endpoint, RPC_WSTR Options, RPC_WSTR *StringBinding)
Definition: rpc_binding.c:510
RPCRTAPI int RPC_ENTRY I_RpcExceptionFilter(ULONG)
unsigned short * RPC_WSTR
Definition: rpcdce.h:46
RPC_STATUS RpcStringFreeW(RPC_WSTR *String)
Definition: rpcrt4_main.c:180
LONG RtlCompareUnicodeString(const UNICODE_STRING *s1, const UNICODE_STRING *s2, BOOLEAN CaseInsensitive)
Definition: rtlstr.c:412
BOOLEAN RtlCreateUnicodeString(PUNICODE_STRING target, LPCWSTR src)
Definition: rtlstr.c:233
void RtlInitUnicodeString(PUNICODE_STRING target, PCWSTR source)
Definition: rtlstr.c:171
void RtlFreeUnicodeString(PUNICODE_STRING str)
Definition: rtlstr.c:270
PVOID HDEVINFO
Definition: setupapi.h:47
#define SPDRP_LOCATION_INFORMATION
Definition: setupapi.h:1295
#define DIF_REGISTERDEVICE
Definition: setupapi.h:1092
#define SPDRP_DEVICEDESC
Definition: setupapi.h:1282
#define DIF_INSTALLDEVICEFILES
Definition: setupapi.h:1088
#define SPDRP_CLASS
Definition: setupapi.h:1289
#define SPDRP_LEGACYBUSTYPE
Definition: setupapi.h:1302
#define SPDRP_COMPATIBLEIDS
Definition: setupapi.h:1284
#define SPDRP_BUSTYPEGUID
Definition: setupapi.h:1301
#define DIGCF_DEVICEINTERFACE
Definition: setupapi.h:1252
struct _SP_DEVICE_INTERFACE_DETAIL_DATA_W SP_DEVICE_INTERFACE_DETAIL_DATA_W
#define SPDRP_CLASSGUID
Definition: setupapi.h:1290
#define DIREG_DRV
Definition: setupapi.h:1381
#define SPDRP_UI_NUMBER
Definition: setupapi.h:1298
#define SPDRP_BUSNUMBER
Definition: setupapi.h:1303
#define DIF_REGISTER_COINSTALLERS
Definition: setupapi.h:1101
#define DIF_INSTALLINTERFACES
Definition: setupapi.h:1099
#define DIGCF_ALLCLASSES
Definition: setupapi.h:1250
#define ERROR_DI_DO_DEFAULT
Definition: setupapi.h:1178
#define SPDRP_ADDRESS
Definition: setupapi.h:1310
#define SPDRP_MFG
Definition: setupapi.h:1293
#define SPDRP_SERVICE
Definition: setupapi.h:1286
#define DIF_INSTALLDEVICE
Definition: setupapi.h:1069
#define DIF_ALLOW_INSTALL
Definition: setupapi.h:1091
#define DIF_SELECTBESTCOMPATDRV
Definition: setupapi.h:1090
#define DICS_FLAG_GLOBAL
Definition: setupapi.h:209
#define SPDRP_REMOVAL_POLICY
Definition: setupapi.h:1313
#define SPDRP_HARDWAREID
Definition: setupapi.h:1283
#define SPDRP_FRIENDLYNAME
Definition: setupapi.h:1294
#define SPDIT_COMPATDRIVER
Definition: setupapi.h:1279
#define SPDRP_INSTALL_STATE
Definition: setupapi.h:1316
#define DIF_NEWDEVICEWIZARD_FINISHINSTALL
Definition: setupapi.h:1097
#define offsetof(s, m)
Definition: stddef.h:28
Definition: windef.h:320
ULONG Count
Definition: wdm.h:433
PDEVICE_OBJECT Objects[1]
Definition: wdm.h:434
PDRIVER_ADD_DEVICE AddDevice
Definition: wdm.h:440
PDRIVER_EXTENSION DriverExtension
Definition: wdm.h:453
PEXCEPTION_RECORD ExceptionRecord
Definition: winnt.h:2731
DWORD ExceptionCode
Definition: winnt.h:2694
union _IO_STACK_LOCATION::@1029 Parameters
struct _IO_STACK_LOCATION::@1029::@1048 QueryId
struct _IO_STACK_LOCATION::@1029::@1053 Power
struct _IO_STACK_LOCATION::@1029::@1042 QueryDeviceRelations
struct _IO_STACK_LOCATION::@1029::@1054 StartDevice
UCHAR MinorFunction
Definition: wdm.h:970
NTSTATUS Status
Definition: winternl.h:1470
ULONG_PTR Information
Definition: winternl.h:1474
Definition: wdm.h:511
IO_STATUS_BLOCK IoStatus
Definition: wdm.h:522
Definition: cookie.c:202
Definition: inflate.c:134
DEVICE_OBJECT * device
Definition: pnp.c:61
struct wine_rb_entry entry
Definition: pnp.c:58
BOOL enabled
Definition: pnp.c:63
UNICODE_STRING symbolic_link
Definition: pnp.c:60
GUID interface_class
Definition: pnp.c:62
Definition: filter.c:184
Definition: list.h:27
Definition: name.c:36
DEVICE_OBJECT * device
Definition: main.c:110
struct list entry
Definition: main.c:109
struct wine_rb_entry entry
Definition: pnp.c:936
DEVICE_OBJECT * device
Definition: pnp.c:937
WCHAR id[200]
Definition: pnp.c:935
Definition: ticket.c:41
DEVICE_RELATIONS * children
Definition: rbtree.h:30
struct resource_id_node * ids
Definition: translation.c:865
#define NULL
Definition: ungif.h:66
#define TRUE
Definition: ungif.h:59
#define FALSE
Definition: ungif.h:62
#define wcsrchr(str, ch)
Definition: unix_private.h:475
#define wcslen(str)
Definition: unix_private.h:469
#define wcschr(str, ch)
Definition: unix_private.h:474
#define wcsupr(str)
Definition: unix_private.h:479
#define wcscpy(dst, src)
Definition: unix_private.h:470
#define wcsicmp(s1, s2)
Definition: unix_private.h:477
BATCH_CONTEXT * context
Definition: wcmdmain.c:38
@ BusRelations
Definition: wdm.h:610
#define KernelMode
Definition: wdm.h:1620
#define IoGetNextIrpStackLocation(_Irp)
Definition: wdm.h:1587
@ NonPagedPool
Definition: wdm.h:275
enum _BUS_QUERY_ID_TYPE BUS_QUERY_ID_TYPE
#define IO_NO_INCREMENT
Definition: wdm.h:305
#define IoGetCurrentIrpStackLocation(_Irp)
Definition: wdm.h:1586
#define IRP_MN_START_DEVICE
Definition: wdm.h:351
enum _POWER_STATE_TYPE POWER_STATE_TYPE
#define IRP_MN_QUERY_ID
Definition: wdm.h:369
#define IRP_MN_REMOVE_DEVICE
Definition: wdm.h:353
@ DevicePowerState
Definition: wdm.h:886
DEVICE_REGISTRY_PROPERTY
Definition: wdm.h:843
@ DevicePropertyCompatibleIDs
Definition: wdm.h:846
@ DevicePropertyAddress
Definition: wdm.h:860
@ DevicePropertyEnumeratorName
Definition: wdm.h:859
@ DevicePropertyInstallState
Definition: wdm.h:862
@ DevicePropertyClassGuid
Definition: wdm.h:850
@ DevicePropertyUINumber
Definition: wdm.h:861
@ DevicePropertyBusNumber
Definition: wdm.h:858
@ DevicePropertyRemovalPolicy
Definition: wdm.h:863
@ DevicePropertyPhysicalDeviceObjectName
Definition: wdm.h:855
@ DevicePropertyLegacyBusType
Definition: wdm.h:857
@ DevicePropertyManufacturer
Definition: wdm.h:852
@ DevicePropertyClassName
Definition: wdm.h:849
@ DevicePropertyFriendlyName
Definition: wdm.h:853
@ DevicePropertyLocationInformation
Definition: wdm.h:854
@ DevicePropertyHardwareID
Definition: wdm.h:845
@ DevicePropertyBusTypeGuid
Definition: wdm.h:856
@ DevicePropertyDeviceDescription
Definition: wdm.h:844
#define IRP_MN_SURPRISE_REMOVAL
Definition: wdm.h:373
#define IRP_MN_QUERY_DEVICE_RELATIONS
Definition: wdm.h:358
#define IRP_MN_QUERY_CAPABILITIES
Definition: wdm.h:360
#define IRP_MN_SET_POWER
Definition: wdm.h:378
#define IRP_MJ_PNP
Definition: wdm.h:349
#define IRP_MJ_POWER
Definition: wdm.h:344
static void IoSetCompletionRoutine(IRP *irp, PIO_COMPLETION_ROUTINE routine, void *context, BOOLEAN on_success, BOOLEAN on_error, BOOLEAN on_cancel)
Definition: wdm.h:1595
@ BusQueryCompatibleIDs
Definition: wdm.h:832
@ BusQueryInstanceID
Definition: wdm.h:833
@ BusQueryDeviceID
Definition: wdm.h:830
@ BusQueryHardwareIDs
Definition: wdm.h:831
enum _DEVICE_RELATION_TYPE DEVICE_RELATION_TYPE
YY_BUFFER_STATE state
Definition: parser.l:85
#define ARRAY_SIZE(x)
Definition: utils.h:37
DECLSPEC_IMPORT DWORD WINAPI GetLastError(void)
#define INVALID_HANDLE_VALUE
Definition: winbase.h:336
DECLSPEC_IMPORT BOOL WINAPI HeapFree(HANDLE, DWORD, LPVOID)
#define INFINITE
Definition: winbase.h:377
DECLSPEC_IMPORT HANDLE WINAPI GetProcessHeap(void)
DECLSPEC_IMPORT INT WINAPI lstrlenW(LPCWSTR)
DECLSPEC_IMPORT LPVOID WINAPI HeapAlloc(HANDLE, DWORD, SIZE_T) __WINE_ALLOC_SIZE(3)
DECLSPEC_IMPORT LPWSTR WINAPI lstrcpynW(LPWSTR, LPCWSTR, INT)
unsigned char BYTE
Definition: windef.h:250
unsigned char UCHAR
Definition: windef.h:238
unsigned int DWORD
Definition: windef.h:261
char * keypath(const char *section)
Definition: winecfg.c:690
#define enable(id)
Definition: winecfg.h:125
#define FILE_DEVICE_CONTROLLER
Definition: winioctl.h:31
DWORD ACCESS_MASK
Definition: winnt.h:4351
BYTE BOOLEAN
Definition: winnt.h:453
#define KEY_READ
Definition: winnt.h:6056
unsigned short WCHAR
Definition: winnt.h:468
#define KEY_CREATE_SUB_KEY
Definition: winnt.h:6042
int LONG
Definition: winnt.h:459
@ PowerDeviceD0
Definition: winnt.h:5699
@ PowerDeviceD3
Definition: winnt.h:5702
enum _DEVICE_POWER_STATE DEVICE_POWER_STATE
#define CONTAINING_RECORD(address, type, field)
Definition: winnt.h:826
#define REG_DWORD
Definition: winnt.h:5633
#define REG_OPTION_VOLATILE
Definition: winnt.h:6018
#define HEAP_ZERO_MEMORY
Definition: winnt.h:906
#define KEY_SET_VALUE
Definition: winnt.h:6041
#define OBJ_KERNEL_HANDLE
Definition: winternl.h:2273
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:2270
@ ObjectNameInformation
Definition: winternl.h:1156
struct _OBJECT_NAME_INFORMATION OBJECT_NAME_INFORMATION
#define FILE_AUTOGENERATED_DEVICE_NAME
Definition: winternl.h:2235
static void * heap_alloc_zero(size_t len) __WINE_ALLOC_SIZE(1)
Definition: wusa.h:88