ReactOS 0.4.15-dev-8413-gc1c91f2
config.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS NDIS library
4 * FILE: ndis/config.c
5 * PURPOSE: NDIS Configuration Services
6 * PROGRAMMERS: Vizzini (vizzini@plasmic.com)
7 * REVISIONS:
8 * Vizzini 07-28-2003 Created
9 * NOTES:
10 * - Resource tracking has to be implemented here because of the design of the NDIS API.
11 * Whenever a read operation is performed, the NDIS library allocates space and returns
12 * it. A linked list is kept associated with every handle of the memory allocated to
13 * it. When the handle is closed, the resources are systematically released.
14 * - The NDIS_HANDLE Configuration context is no longer a registry handle. An opaque struct
15 * had to be created to allow for resource tracking. This means that Miniports cannot just
16 * pass this NDIS_HANDLE to things like ZwQueryValueKey(). I don't thknk they do (they
17 * certainly should not), but it should be kept in mind.
18 * UPDATE: I just found this in the NTDDK:
19 * NdisOpenProtocolConfiguration returns a handle for the
20 * HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\NICDriverInstance\Parameters\ProtocolName
21 * registry key. XXX This is a problem. Following that, the DDK instructs programmers
22 * to use NdisReadConfiguration and NdisWriteConfiguration. No telling what the world's idiots
23 * have done with this.
24 * - I have tried to stick to the DDK's definition of what return values are possible, which
25 * has resulted in stupid return values in some cases. I do use STATUS_RESOURCES in a few
26 * places that the DDK doesn't explicitly mention it, though.
27 * - There's a general reliance on the fact that UNICODE_STRING.Length doesn't include a trailing
28 * 0, which it shouldn't
29 * - I added support for NdisParameterBinary. It's at the end of the struct. I wonder if
30 * it'll break things.
31 * - All the routines in this file are PASSIVE_LEVEL only, and all memory is PagedPool
32 */
33
34#include "ndissys.h"
35
36#include <ntifs.h>
37
38#define PARAMETERS_KEY L"Parameters" /* The parameters subkey under the device-specific key */
39
40/*
41 * @implemented
42 */
43VOID
50/*
51 * FUNCTION: Writes a configuration value to the registry
52 * ARGUMENTS:
53 * Status: Pointer to a caller-supplied NDIS_STATUS where we return status
54 * ConfigurationHandle: The Configuration Handle passed back from the call to one of the Open functions
55 * Keyword: The registry value name to write
56 * ParameterValue: The value data to write
57 * RETURNS:
58 * NDIS_STATUS_SUCCESS - the operation completed successfully
59 * NDIS_STATUS_NOT_SUPPORTED - The parameter type is not supported
60 * NDIS_STATUS_RESOURCES - out of memory, etc.
61 * NDIS_STATUS_FAILURE - any other failure
62 * NOTES:
63 * There's a cryptic comment in the ddk implying that this function allocates and keeps memory.
64 * I don't know why tho so i free everything before return. comments welcome.
65 */
66{
69 PVOID Data;
70 WCHAR Buff[11];
71
72 NDIS_DbgPrint(MAX_TRACE, ("Called.\n"));
73
74 NDIS_DbgPrint(MID_TRACE, ("Parameter type: %d\n", ParameterValue->ParameterType));
75
76 /* reset parameter type to standard reg types */
77 switch(ParameterValue->ParameterType)
78 {
81 {
83
84 Str.Buffer = (PWSTR) &Buff;
85 Str.MaximumLength = (USHORT)sizeof(Buff);
86 Str.Length = 0;
87
90 ParameterValue->ParameterData.IntegerData,
91 (ParameterValue->ParameterType == NdisParameterInteger) ? 10 : 16, &Str)))
92 {
93 NDIS_DbgPrint(MIN_TRACE, ("RtlIntegerToUnicodeString failed (%x)\n", *Status));
95 return;
96 }
97 Data = Str.Buffer;
98 DataSize = Str.Length;
99 }
100 break;
104 Data = ParameterValue->ParameterData.StringData.Buffer;
105 DataSize = ParameterValue->ParameterData.StringData.Length;
106 break;
107
108 /* New (undocumented) addition to 2k ddk */
111 Data = ParameterValue->ParameterData.BinaryData.Buffer;
112 DataSize = ParameterValue->ParameterData.BinaryData.Length;
113 break;
114
115 default:
117 return;
118 }
119
122
123 if(*Status != STATUS_SUCCESS) {
124 NDIS_DbgPrint(MIN_TRACE, ("ZwSetValueKey failed (%x)\n", *Status));
126 } else
128}
129
130
131/*
132 * @implemented
133 */
134VOID
135EXPORT
138/*
139 * FUNCTION: Closes handles and releases per-handle resources
140 * ARGUMENTS:
141 * ConfigurationHandle - pointer to the context with the resources to free
142 */
143{
147 PLIST_ENTRY CurrentEntry;
148
149 while((CurrentEntry = ExInterlockedRemoveHeadList(&ConfigurationContext->ResourceListHead,
150 &ConfigurationContext->ResourceLock)) != NULL)
151 {
152 Resource = CONTAINING_RECORD(CurrentEntry, MINIPORT_RESOURCE, ListEntry);
153 switch(Resource->ResourceType)
154 {
156 ParameterValue = Resource->Resource;
157
158 switch (ParameterValue->ParameterType)
159 {
161 ExFreePool(ParameterValue->ParameterData.BinaryData.Buffer);
162 break;
163
166 ExFreePool(ParameterValue->ParameterData.StringData.Buffer);
167 break;
168
169 default:
170 break;
171 }
172
173 /* Fall through to free NDIS_CONFIGURATION_PARAMETER struct */
174
176 NDIS_DbgPrint(MAX_TRACE,("freeing 0x%x\n", Resource->Resource));
177 ExFreePool(Resource->Resource);
178 break;
179
180 default:
181 NDIS_DbgPrint(MIN_TRACE,("Unknown resource type: %d\n", Resource->ResourceType));
182 break;
183 }
184
186 }
187
188 ZwClose(ConfigurationContext->Handle);
189}
190
191
192/*
193 * @implemented
194 */
195VOID
196EXPORT
201/*
202 * FUNCTION: Opens the configuration key and sets up resource tracking for the returned handle
203 * ARGUMENTS:
204 * Status: Pointer to a caller-supplied NDIS_STATUS that is filled in with a return value
205 * ConfigurationHandle: Pointer to an opaque configuration handle returned on success
206 * WrapperConfigurationContext: handle originally passed back from NdisInitializeWrapper
207 * RETURNS:
208 * NDIS_STATUS_SUCCESS: the operation completed successfully
209 * NDIS_STATUS_FAILURE: the operation failed
210 * NOTES:
211 * I think this is the parameters key; please verify.
212 */
213{
215 PMINIPORT_CONFIGURATION_CONTEXT ConfigurationContext;
217 HANDLE RootKeyHandle = WrapperContext->RegistryHandle;
220
221 NDIS_DbgPrint(MAX_TRACE, ("Called\n"));
222
224
226 &NoName,
228 RootKeyHandle,
229 NULL);
231 if(!NT_SUCCESS(*Status))
232 {
233 NDIS_DbgPrint(MIN_TRACE, ("Failed to open registry configuration for this miniport\n"));
235 return;
236 }
237
238 ConfigurationContext = ExAllocatePool(NonPagedPool, sizeof(MINIPORT_CONFIGURATION_CONTEXT));
239 if(!ConfigurationContext)
240 {
241 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
244 return;
245 }
246
247 KeInitializeSpinLock(&ConfigurationContext->ResourceLock);
248 InitializeListHead(&ConfigurationContext->ResourceListHead);
249
250 ConfigurationContext->Handle = KeyHandle;
251
252 *ConfigurationHandle = (NDIS_HANDLE)ConfigurationContext;
254
255 NDIS_DbgPrint(MAX_TRACE,("returning success\n"));
256}
257
258
259/*
260 * @implemented
261 */
262VOID
263EXPORT
268/*
269 * FUNCTION: Open the configuration key and set up resource tracking for the protocol
270 * ARGUMENTS:
271 * Status: caller-allocated buffer where status is returned
272 * ConfigurationHandle: spot to return the opaque configuration context
273 * ProtocolSection: configuration string originally passed in to ProtocolBindAdapter
274 * RETURNS:
275 * NDIS_STATUS_SUCCESS: the operation was a success
276 * NDIS_STATUS_FAILURE: the operation was not a success
277 * NOTES:
278 * I think this is the per-device (adapter) parameters\{ProtocolName} key; please verify.
279 */
280{
282 UNICODE_STRING KeyNameU;
284 PMINIPORT_CONFIGURATION_CONTEXT ConfigurationContext;
285
286 KeyNameU.Length = 0;
287 KeyNameU.MaximumLength = ProtocolSection->Length + sizeof(PARAMETERS_KEY) + sizeof(UNICODE_NULL);
288 KeyNameU.Buffer = ExAllocatePool(PagedPool, KeyNameU.MaximumLength);
289 if(!KeyNameU.Buffer)
290 {
291 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
294 return;
295 }
296
300
302
303 ExFreePool(KeyNameU.Buffer);
304
306 {
307 NDIS_DbgPrint(MIN_TRACE, ("ZwOpenKey failed (%x)\n", *Status));
310 return;
311 }
312
313 ConfigurationContext = ExAllocatePool(NonPagedPool, sizeof(MINIPORT_CONFIGURATION_CONTEXT));
314 if(!ConfigurationContext)
315 {
316 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
320 return;
321 }
322
323 KeInitializeSpinLock(&ConfigurationContext->ResourceLock);
324 InitializeListHead(&ConfigurationContext->ResourceListHead);
325
326 ConfigurationContext->Handle = KeyHandle;
327
328 *ConfigurationHandle = (NDIS_HANDLE)ConfigurationContext;
330}
331
333/*
334 * FUNCTION: Converts a unicode hex character to its numerical value
335 * ARGUMENTS:
336 * chr: Unicode character to convert
337 * RETURNS:
338 * The numerical value of chr
339 */
340{
341 switch(chr)
342 {
343 case L'0': return 0;
344 case L'1': return 1;
345 case L'2': return 2;
346 case L'3': return 3;
347 case L'4': return 4;
348 case L'5': return 5;
349 case L'6': return 6;
350 case L'7': return 7;
351 case L'8': return 8;
352 case L'9': return 9;
353 case L'A':
354 case L'a':
355 return 10;
356 case L'B':
357 case L'b':
358 return 11;
359 case L'C':
360 case L'c':
361 return 12;
362 case L'D':
363 case L'd':
364 return 13;
365 case L'E':
366 case L'e':
367 return 14;
368 case L'F':
369 case L'f':
370 return 15;
371 }
372 return 0xFF;
373}
374
377/*
378 * FUNCTION: Determines if a string is a valid number
379 * ARGUMENTS:
380 * String: Unicode string to evaluate
381 * RETURNS:
382 * TRUE if it is valid, FALSE if not
383 */
384{
385 ULONG i;
386
387 /* I don't think this will ever happen, but we warn it if it does */
388 if (String->Length == 0)
389 {
390 NDIS_DbgPrint(MIN_TRACE, ("Got an empty string; not sure what to do here\n"));
391 return FALSE;
392 }
393
394 for (i = 0; i < String->Length / sizeof(WCHAR); i++)
395 {
396 /* Skip any NULL characters we find */
397 if (String->Buffer[i] == UNICODE_NULL)
398 continue;
399
400 /* Make sure the character is valid for a numeric string of this base */
401 if (UnicodeToHexByte(String->Buffer[i]) >= Base)
402 return FALSE;
403 }
404
405 /* It's valid */
406 return TRUE;
407}
408
409/*
410 * @implemented
411 */
412VOID
413EXPORT
420/*
421 * FUNCTION: Read a configuration value from the registry, tracking its resources
422 * ARGUMENTS:
423 * Status: points to a place to write status into
424 * ParameterValue: Pointer to receive a newly-allocated parameter structure
425 * ConfigurationHandle: handle originally returned by an open function
426 * Keyword: Value name to read, or one of the following constants:
427 * Environment - returns NdisEnvironmentWindowsNt
428 * ProcessorType - returns NdisProcessorX86 until more architectures are added
429 * NdisVersion - returns NDIS_VERSION
430 * ParameterType: the type of the value to be queried
431 * RETURNS:
432 * - A status in Status
433 * - A parameter value in ParameterValue
434 */
435{
436 KEY_VALUE_PARTIAL_INFORMATION *KeyInformation;
437 ULONG KeyDataLength;
438 PMINIPORT_RESOURCE MiniportResource;
441
442 //*ParameterValue = NULL;
444
445 NDIS_DbgPrint(MAX_TRACE,("requested read of %wZ\n", Keyword));
446 NDIS_DbgPrint(MID_TRACE,("requested parameter type: %d\n", ParameterType));
447
448 if (ConfigurationContext == NULL)
449 {
450 NDIS_DbgPrint(MIN_TRACE,("invalid parameter ConfigurationContext (0x%x)\n",ConfigurationContext));
451 return;
452 }
453
454 if(!wcsncmp(Keyword->Buffer, L"Environment", Keyword->Length/sizeof(WCHAR)) &&
455 wcslen(L"Environment") == Keyword->Length/sizeof(WCHAR))
456 {
458 if(!*ParameterValue)
459 {
460 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
462 return;
463 }
464
465 MiniportResource = ExAllocatePool(PagedPool, sizeof(MINIPORT_RESOURCE));
466 if(!MiniportResource)
467 {
468 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
472 return;
473 }
474
476 MiniportResource->Resource = *ParameterValue;
477
478 NDIS_DbgPrint(MID_TRACE,("inserting 0x%x into the resource list\n",
479 MiniportResource->Resource));
480
481 ExInterlockedInsertTailList(&ConfigurationContext->ResourceListHead,
482 &MiniportResource->ListEntry, &ConfigurationContext->ResourceLock);
483
484 (*ParameterValue)->ParameterType = NdisParameterInteger;
485 (*ParameterValue)->ParameterData.IntegerData = NdisEnvironmentWindowsNt;
487
488 return;
489 }
490
491 if(!wcsncmp(Keyword->Buffer, L"ProcessorType", Keyword->Length/sizeof(WCHAR)) &&
492 wcslen(L"ProcessorType") == Keyword->Length/sizeof(WCHAR))
493 {
495 if(!*ParameterValue)
496 {
497 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
499 return;
500 }
501
502 MiniportResource = ExAllocatePool(PagedPool, sizeof(MINIPORT_RESOURCE));
503 if(!MiniportResource)
504 {
505 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
509 return;
510 }
511
513 MiniportResource->Resource = *ParameterValue;
514 NDIS_DbgPrint(MID_TRACE,("inserting 0x%x into the resource list\n", MiniportResource->Resource));
515 ExInterlockedInsertTailList(&ConfigurationContext->ResourceListHead,
516 &MiniportResource->ListEntry, &ConfigurationContext->ResourceLock);
517
518 (*ParameterValue)->ParameterType = NdisParameterInteger;
519 (*ParameterValue)->ParameterData.IntegerData = NdisProcessorX86; /* XXX non-portable */
521
522 return;
523 }
524
525 if(!wcsncmp(Keyword->Buffer, L"NdisVersion", Keyword->Length/sizeof(WCHAR)) &&
526 wcslen(L"NdisVersion") == Keyword->Length/sizeof(WCHAR))
527 {
529 if(!*ParameterValue)
530 {
531 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
533 return;
534 }
535
536 MiniportResource = ExAllocatePool(PagedPool, sizeof(MINIPORT_RESOURCE));
537 if(!MiniportResource)
538 {
539 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
543 return;
544 }
545
547 MiniportResource->Resource = *ParameterValue;
548 NDIS_DbgPrint(MID_TRACE,("inserting 0x%x into the resource list\n", MiniportResource->Resource));
549 ExInterlockedInsertTailList(&ConfigurationContext->ResourceListHead,
550 &MiniportResource->ListEntry, &ConfigurationContext->ResourceLock);
551
552 (*ParameterValue)->ParameterType = NdisParameterInteger;
553 (*ParameterValue)->ParameterData.IntegerData = NDIS_VERSION;
555
556 NDIS_DbgPrint(MAX_TRACE,("ParameterType = 0x%x, ParameterValue = 0x%x\n",
557 (*ParameterValue)->ParameterType, (*ParameterValue)->ParameterData.IntegerData));
558 return;
559 }
560
561 /* figure out how much buffer i should allocate */
562 *Status = ZwQueryValueKey(ConfigurationContext->Handle, Keyword, KeyValuePartialInformation, NULL, 0, &KeyDataLength);
564 {
565 NDIS_DbgPrint(MID_TRACE,("ZwQueryValueKey #1 failed for %wZ, status 0x%x\n", Keyword, *Status));
567 return;
568 }
569
570 /* allocate it */
571 KeyInformation = ExAllocatePool(PagedPool, KeyDataLength + sizeof(KEY_VALUE_PARTIAL_INFORMATION));
572 if(!KeyInformation)
573 {
574 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
576 return;
577 }
578
579 /* grab the value */
580 *Status = ZwQueryValueKey(ConfigurationContext->Handle, Keyword, KeyValuePartialInformation,
581 KeyInformation, KeyDataLength + sizeof(KEY_VALUE_PARTIAL_INFORMATION), &KeyDataLength);
582 if(*Status != STATUS_SUCCESS)
583 {
584 ExFreePool(KeyInformation);
585 NDIS_DbgPrint(MIN_TRACE,("ZwQueryValueKey #2 failed for %wZ, status 0x%x\n", Keyword, *Status));
587 return;
588 }
589
590 MiniportResource = ExAllocatePool(PagedPool, sizeof(MINIPORT_RESOURCE));
591 if(!MiniportResource)
592 {
593 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
594 ExFreePool(KeyInformation);
596 return;
597 }
598
600 if (!*ParameterValue)
601 {
602 NDIS_DbgPrint(MIN_TRACE, ("Insufficient resources.\n"));
603 ExFreePool(MiniportResource);
604 ExFreePool(KeyInformation);
606 return;
607 }
608
610
611 if (KeyInformation->Type == REG_BINARY)
612 {
613 NDIS_DbgPrint(MAX_TRACE, ("NdisParameterBinary\n"));
614
615 (*ParameterValue)->ParameterType = NdisParameterBinary;
616
617 Buffer = ExAllocatePool(PagedPool, KeyInformation->DataLength);
618 if (!Buffer)
619 {
620 NDIS_DbgPrint(MIN_TRACE, ("Insufficient resources.\n"));
621 ExFreePool(MiniportResource);
622 ExFreePool(KeyInformation);
624 return;
625 }
626
627 RtlCopyMemory(Buffer, KeyInformation->Data, KeyInformation->DataLength);
628
629 (*ParameterValue)->ParameterData.BinaryData.Buffer = Buffer;
630 (*ParameterValue)->ParameterData.BinaryData.Length = KeyInformation->DataLength;
631 }
632 else if (KeyInformation->Type == REG_MULTI_SZ)
633 {
634 NDIS_DbgPrint(MAX_TRACE, ("NdisParameterMultiString\n"));
635
636 (*ParameterValue)->ParameterType = NdisParameterMultiString;
637
638 Buffer = ExAllocatePool(PagedPool, KeyInformation->DataLength);
639 if (!Buffer)
640 {
641 NDIS_DbgPrint(MIN_TRACE, ("Insufficient resources.\n"));
642 ExFreePool(MiniportResource);
643 ExFreePool(KeyInformation);
645 return;
646 }
647
648 RtlCopyMemory(Buffer, KeyInformation->Data, KeyInformation->DataLength);
649
650 (*ParameterValue)->ParameterData.StringData.Buffer = Buffer;
651 (*ParameterValue)->ParameterData.StringData.Length = KeyInformation->DataLength;
652 }
653 else if (KeyInformation->Type == REG_DWORD)
654 {
655 ASSERT(KeyInformation->DataLength == sizeof(ULONG));
656 NDIS_DbgPrint(MAX_TRACE, ("NdisParameterInteger\n"));
657 (*ParameterValue)->ParameterType = NdisParameterInteger;
658 (*ParameterValue)->ParameterData.IntegerData = * (ULONG *) &KeyInformation->Data[0];
659 }
660 else if (KeyInformation->Type == REG_SZ)
661 {
663 ULONG Base;
664
666 Base = 10;
668 Base = 16;
669 else
670 Base = 0;
671
672 str.Length = str.MaximumLength = (USHORT)KeyInformation->DataLength;
673 str.Buffer = (PWCHAR)KeyInformation->Data;
674
675 if (Base != 0 && IsValidNumericString(&str, Base))
676 {
677 *Status = RtlUnicodeStringToInteger(&str, Base, &(*ParameterValue)->ParameterData.IntegerData);
679
680 NDIS_DbgPrint(MAX_TRACE, ("NdisParameter(Hex)Integer\n"));
681
682 /* MSDN documents that this is returned for all integers, regardless of the ParameterType passed in */
683 (*ParameterValue)->ParameterType = NdisParameterInteger;
684 }
685 else
686 {
687 NDIS_DbgPrint(MAX_TRACE, ("NdisParameterString\n"));
688
689 (*ParameterValue)->ParameterType = NdisParameterString;
690
691 Buffer = ExAllocatePool(PagedPool, KeyInformation->DataLength);
692 if (!Buffer)
693 {
694 NDIS_DbgPrint(MIN_TRACE, ("Insufficient resources.\n"));
695 ExFreePool(MiniportResource);
696 ExFreePool(KeyInformation);
698 return;
699 }
700
701 RtlCopyMemory(Buffer, KeyInformation->Data, KeyInformation->DataLength);
702
703 (*ParameterValue)->ParameterData.StringData.Buffer = Buffer;
704 (*ParameterValue)->ParameterData.StringData.Length = KeyInformation->DataLength;
705 }
706 }
707 else
708 {
709 NDIS_DbgPrint(MIN_TRACE, ("Invalid type for NdisReadConfiguration (%d)\n", KeyInformation->Type));
710 NDIS_DbgPrint(MIN_TRACE, ("Requested type: %d\n", ParameterType));
711 NDIS_DbgPrint(MIN_TRACE, ("Registry entry: %wZ\n", Keyword));
713 ExFreePool(KeyInformation);
714 return;
715 }
716
717 if (((*ParameterValue)->ParameterType != ParameterType) &&
718 !((ParameterType == NdisParameterHexInteger) && ((*ParameterValue)->ParameterType == NdisParameterInteger)))
719 {
720 NDIS_DbgPrint(MIN_TRACE, ("Parameter type mismatch! (Requested: %d | Received: %d)\n",
721 ParameterType, (*ParameterValue)->ParameterType));
722 NDIS_DbgPrint(MIN_TRACE, ("Registry entry: %wZ\n", Keyword));
723 }
724
726 MiniportResource->Resource = *ParameterValue;
727
728 ExInterlockedInsertTailList(&ConfigurationContext->ResourceListHead, &MiniportResource->ListEntry, &ConfigurationContext->ResourceLock);
729
730 ExFreePool(KeyInformation);
731
733}
734
735/*
736 * @implemented
737 */
738VOID
739EXPORT
745/*
746 * FUNCTION: Reads the network address from the registry
747 * ARGUMENTS:
748 * Status - variable to receive status
749 * NetworkAddress - pointer to a buffered network address array
750 * NetworkAddressLength - length of the NetworkAddress array
751 * ConfigurationHandle: handle passed back from one of the open routines
752 * RETURNS:
753 * NDIS_STATUS_SUCCESS on success
754 * NDIS_STATUS_FAILURE on failure
755 * The network address is placed in the NetworkAddress buffer
756 */
757{
759 PMINIPORT_RESOURCE MiniportResource = NULL;
762 UINT *IntArray = 0;
763 UINT i,j = 0;
764 WCHAR Buff[11];
766
767 NdisInitUnicodeString(&Keyword, L"NetworkAddress");
770 {
771 NDIS_DbgPrint(MID_TRACE, ("NdisReadConfiguration failed (%x)\n", *Status));
773 return;
774 }
775
776 if (ParameterValue->ParameterType == NdisParameterInteger)
777 {
778 NDIS_DbgPrint(MAX_TRACE, ("Read integer data %lx\n",
779 ParameterValue->ParameterData.IntegerData));
780
781 str.Buffer = Buff;
782 str.MaximumLength = (USHORT)sizeof(Buff);
783 str.Length = 0;
784
785 *Status = RtlIntegerToUnicodeString(ParameterValue->ParameterData.IntegerData,
786 10,
787 &str);
788
790 {
791 NDIS_DbgPrint(MIN_TRACE, ("RtlIntegerToUnicodeString failed (%x)\n", *Status));
793 return;
794 }
795
796 NDIS_DbgPrint(MAX_TRACE, ("Converted integer data into %wZ\n", &str));
797 }
798 else
799 {
800 ASSERT(ParameterValue->ParameterType == NdisParameterString);
801 str = ParameterValue->ParameterData.StringData;
802 }
803
804 while (j < str.Length && str.Buffer[j] != '\0') j++;
805
806 *NetworkAddressLength = (j+1) >> 1;
807
808 if ((*NetworkAddressLength) == 0)
809 {
810 NDIS_DbgPrint(MIN_TRACE,("Empty NetworkAddress registry entry.\n"));
812 return;
813 }
814
815 IntArray = ExAllocatePool(PagedPool, (*NetworkAddressLength)*sizeof(UINT));
816 if(!IntArray)
817 {
818 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
820 return;
821 }
822
823 MiniportResource = ExAllocatePool(PagedPool, sizeof(MINIPORT_RESOURCE));
824 if(!MiniportResource)
825 {
826 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
827 ExFreePool(IntArray);
829 return;
830 }
831
833 MiniportResource->Resource = IntArray;
834 NDIS_DbgPrint(MID_TRACE,("inserting 0x%x into the resource list\n", MiniportResource->Resource));
835 ExInterlockedInsertTailList(&ConfigurationContext->ResourceListHead, &MiniportResource->ListEntry, &ConfigurationContext->ResourceLock);
836
837 /* convert from string to bytes */
838 for(i=0; i<(*NetworkAddressLength); i++)
839 {
840 IntArray[i] = (UnicodeToHexByte((str.Buffer)[2*i]) << 4) +
841 UnicodeToHexByte((str.Buffer)[2*i+1]);
842 }
843
844 *NetworkAddress = IntArray;
845
847}
848
849
850/*
851 * @implemented
852 */
853VOID
854EXPORT
858 IN ULONG Index,
861/*
862 * FUNCTION: Opens a configuration subkey by index number
863 * ARGUMENTS:
864 * Status: pointer to an NDIS_STATUS to receive status info
865 * ConfigurationHandle: the handle passed back from a previous open function
866 * Index: the zero-based index of the subkey to open
867 * KeyName: the name of the key that was opened
868 * KeyHandle: a handle to the key that was opened
869 * RETURNS:
870 * NDIS_STATUS_SUCCESS on success
871 * NDIS_STATUS_FAILURE on failure
872 * KeyName holds the name of the opened key
873 * KeyHandle holds a handle to the new key
874 */
875{
876 KEY_BASIC_INFORMATION *KeyInformation;
877 ULONG KeyInformationLength;
879 NDIS_HANDLE RegKeyHandle;
880 PMINIPORT_CONFIGURATION_CONTEXT ConfigurationContext;
881
882 *KeyHandle = NULL;
883
884 *Status = ZwEnumerateKey(ConfigurationHandle, Index, KeyBasicInformation, NULL, 0, &KeyInformationLength);
886 {
887 NDIS_DbgPrint(MIN_TRACE, ("ZwEnumerateKey failed (%x)\n", *Status));
889 return;
890 }
891
892 KeyInformation = ExAllocatePool(PagedPool, KeyInformationLength + sizeof(KEY_BASIC_INFORMATION));
893 if(!KeyInformation)
894 {
895 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
897 return;
898 }
899
900 *Status = ZwEnumerateKey(ConfigurationHandle, Index, KeyBasicInformation, KeyInformation,
901 KeyInformationLength + sizeof(KEY_BASIC_INFORMATION), &KeyInformationLength);
902
903 if(*Status != STATUS_SUCCESS)
904 {
905 NDIS_DbgPrint(MIN_TRACE, ("ZwEnumerateKey failed (%x)\n", *Status));
906 ExFreePool(KeyInformation);
908 return;
909 }
910
911 /* should i fail instead if the passed-in string isn't long enough? */
912 wcsncpy(KeyName->Buffer, KeyInformation->Name, KeyName->MaximumLength/sizeof(WCHAR));
913 KeyName->Length = (USHORT)min(KeyInformation->NameLength, KeyName->MaximumLength);
914
916
917 *Status = ZwOpenKey(&RegKeyHandle, KEY_ALL_ACCESS, &KeyAttributes);
918
919 ExFreePool(KeyInformation);
920
921 if(*Status != STATUS_SUCCESS)
922 {
923 NDIS_DbgPrint(MIN_TRACE, ("ZwOpenKey failed (%x)\n", *Status));
925 return;
926 }
927
928 ConfigurationContext = ExAllocatePool(NonPagedPool, sizeof(MINIPORT_CONFIGURATION_CONTEXT));
929 if(!ConfigurationContext)
930 {
931 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
932 ZwClose(RegKeyHandle);
934 return;
935 }
936
937 KeInitializeSpinLock(&ConfigurationContext->ResourceLock);
938 InitializeListHead(&ConfigurationContext->ResourceListHead);
939
940 ConfigurationContext->Handle = RegKeyHandle;
941
942 *KeyHandle = (NDIS_HANDLE)ConfigurationContext;
943
945}
946
947
948/*
949 * @implemented
950 */
951VOID
952EXPORT
958/*
959 * FUNCTION: Opens a configuration subkey by name
960 * ARGUMENTS:
961 * Status: points to an NDIS_STATUS where status is returned
962 * ConfigurationHandle: handle returned by a previous open call
963 * KeyName: the name of the key to open
964 * KeyHandle: a handle to the opened key
965 * RETURNS:
966 * NDIS_STATUS_SUCCESS on success
967 * NDIS_STATUS_FAILURE on failure
968 * KeyHandle holds a handle to the newly-opened key
969 * NOTES:
970 */
971{
972 PMINIPORT_CONFIGURATION_CONTEXT ConfigurationContext;
974 NDIS_HANDLE RegKeyHandle;
975
976 *KeyHandle = NULL;
977
979 *Status = ZwOpenKey(&RegKeyHandle, KEY_ALL_ACCESS, &KeyAttributes);
980
981 if(*Status != STATUS_SUCCESS)
982 {
983 NDIS_DbgPrint(MIN_TRACE, ("ZwOpenKey failed (%x)\n", *Status));
985 return;
986 }
987
988 ConfigurationContext = ExAllocatePool(NonPagedPool, sizeof(MINIPORT_CONFIGURATION_CONTEXT));
989 if(!ConfigurationContext)
990 {
991 NDIS_DbgPrint(MIN_TRACE,("Insufficient resources.\n"));
992 ZwClose(RegKeyHandle);
994 return;
995 }
996
997 KeInitializeSpinLock(&ConfigurationContext->ResourceLock);
998 InitializeListHead(&ConfigurationContext->ResourceListHead);
999
1000 ConfigurationContext->Handle = RegKeyHandle;
1001
1002 *KeyHandle = (NDIS_HANDLE)ConfigurationContext;
1003
1005}
unsigned char BOOLEAN
#define MIN_TRACE
Definition: debug.h:14
#define MID_TRACE
Definition: debug.h:15
#define MAX_TRACE
Definition: debug.h:16
_Acquires_exclusive_lock_ Resource _Acquires_shared_lock_ Resource _Inout_ PERESOURCE Resource
Definition: cdprocs.h:843
_In_opt_ PWSTR _In_ PWSTR _Inout_ PULONG ParameterValue
Definition: cdrom.h:963
Definition: bufpool.h:45
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:36
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:33
#define NDIS_DbgPrint(_t_, _x_)
Definition: debug.h:40
#define MINIPORT_RESOURCE_TYPE_REGISTRY_DATA
Definition: miniport.h:41
#define MINIPORT_RESOURCE_TYPE_MEMORY
Definition: miniport.h:42
struct _NDIS_WRAPPER_CONTEXT * PNDIS_WRAPPER_CONTEXT
struct _MINIPORT_CONFIGURATION_CONTEXT * PMINIPORT_CONFIGURATION_CONTEXT
VOID EXPORT NdisOpenConfigurationKeyByName(OUT PNDIS_STATUS Status, IN NDIS_HANDLE ConfigurationHandle, IN PNDIS_STRING KeyName, OUT PNDIS_HANDLE KeyHandle)
Definition: config.c:953
VOID EXPORT NdisCloseConfiguration(IN NDIS_HANDLE ConfigurationHandle)
Definition: config.c:136
VOID EXPORT NdisWriteConfiguration(OUT PNDIS_STATUS Status, IN NDIS_HANDLE ConfigurationHandle, IN PNDIS_STRING Keyword, IN PNDIS_CONFIGURATION_PARAMETER ParameterValue)
Definition: config.c:45
BOOLEAN IsValidNumericString(PNDIS_STRING String, ULONG Base)
Definition: config.c:376
VOID EXPORT NdisOpenProtocolConfiguration(OUT PNDIS_STATUS Status, OUT PNDIS_HANDLE ConfigurationHandle, IN PNDIS_STRING ProtocolSection)
Definition: config.c:264
VOID EXPORT NdisReadConfiguration(OUT PNDIS_STATUS Status, OUT PNDIS_CONFIGURATION_PARAMETER *ParameterValue, IN NDIS_HANDLE ConfigurationHandle, IN PNDIS_STRING Keyword, IN NDIS_PARAMETER_TYPE ParameterType)
Definition: config.c:414
VOID EXPORT NdisReadNetworkAddress(OUT PNDIS_STATUS Status, OUT PVOID *NetworkAddress, OUT PUINT NetworkAddressLength, IN NDIS_HANDLE ConfigurationHandle)
Definition: config.c:740
#define PARAMETERS_KEY
Definition: config.c:38
VOID EXPORT NdisOpenConfiguration(OUT PNDIS_STATUS Status, OUT PNDIS_HANDLE ConfigurationHandle, IN NDIS_HANDLE WrapperConfigurationContext)
Definition: config.c:197
UCHAR UnicodeToHexByte(WCHAR chr)
Definition: config.c:332
VOID EXPORT NdisOpenConfigurationKeyByIndex(OUT PNDIS_STATUS Status, IN NDIS_HANDLE ConfigurationHandle, IN ULONG Index, OUT PNDIS_STRING KeyName, OUT PNDIS_HANDLE KeyHandle)
Definition: config.c:855
VOID EXPORT NdisInitUnicodeString(IN OUT PNDIS_STRING DestinationString, IN PCWSTR SourceString)
Definition: string.c:130
NTSTATUS RtlAppendUnicodeToString(IN PUNICODE_STRING Str1, IN PWSTR Str2)
Definition: string_lib.cpp:62
#define ExFreePool(addr)
Definition: env_spec_w32.h:352
#define NonPagedPool
Definition: env_spec_w32.h:307
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define KeInitializeSpinLock(sl)
Definition: env_spec_w32.h:604
#define PagedPool
Definition: env_spec_w32.h:308
#define ExAllocatePool(type, size)
Definition: fbtusb.h:44
ULONG Handle
Definition: gdb_input.c:15
Status
Definition: gdiplustypes.h:25
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
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 GLint GLint j
Definition: glfuncs.h:250
_CRTIMP size_t __cdecl wcslen(_In_z_ const wchar_t *_Str)
#define OBJ_KERNEL_HANDLE
Definition: winternl.h:231
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
PLIST_ENTRY NTAPI ExInterlockedInsertTailList(IN OUT PLIST_ENTRY ListHead, IN OUT PLIST_ENTRY ListEntry, IN OUT PKSPIN_LOCK Lock)
Definition: interlocked.c:140
PLIST_ENTRY NTAPI ExInterlockedRemoveHeadList(IN OUT PLIST_ENTRY ListHead, IN OUT PKSPIN_LOCK Lock)
Definition: interlocked.c:166
#define REG_SZ
Definition: layer.c:22
#define ASSERT(a)
Definition: mode.c:44
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
#define min(a, b)
Definition: monoChain.cc:55
_Must_inspect_result_ _Out_ PNDIS_STATUS _Outptr_result_bytebuffer_to_ NetworkAddressLength PVOID * NetworkAddress
Definition: ndis.h:3956
_Must_inspect_result_ _Out_ PNDIS_STATUS _Out_ PNDIS_CONFIGURATION_PARAMETER _In_ NDIS_HANDLE _In_ PNDIS_STRING _In_ NDIS_PARAMETER_TYPE ParameterType
Definition: ndis.h:4417
@ NdisParameterBinary
Definition: ndis.h:930
@ NdisParameterInteger
Definition: ndis.h:926
@ NdisParameterString
Definition: ndis.h:928
@ NdisParameterMultiString
Definition: ndis.h:929
@ NdisParameterHexInteger
Definition: ndis.h:927
_In_ NDIS_STATUS _In_ ULONG _In_ USHORT _In_opt_ PVOID _In_ ULONG DataSize
Definition: ndis.h:4755
unsigned int * PUINT
Definition: ndis.h:50
unsigned int UINT
Definition: ndis.h:50
PVOID NDIS_HANDLE
Definition: ndis.h:338
#define NDIS_STATUS_NOT_SUPPORTED
Definition: ndis.h:479
@ NdisProcessorX86
Definition: ndis.h:885
_Must_inspect_result_ _Out_ PNDIS_STATUS _Outptr_result_bytebuffer_to_ NetworkAddressLength PVOID _Out_ PUINT NetworkAddressLength
Definition: ndis.h:3958
#define NDIS_STATUS_FAILURE
Definition: ndis.h:465
#define NDIS_STATUS_SUCCESS
Definition: ndis.h:346
_Must_inspect_result_ _Out_ PNDIS_STATUS _Out_ PNDIS_HANDLE _In_ NDIS_HANDLE WrapperConfigurationContext
Definition: ndis.h:3946
@ NdisEnvironmentWindowsNt
Definition: ndis.h:895
_Must_inspect_result_ _Out_ PNDIS_STATUS _Out_ PNDIS_HANDLE ConfigurationHandle
Definition: ndis.h:3945
enum _NDIS_PARAMETER_TYPE NDIS_PARAMETER_TYPE
* PNDIS_STATUS
Definition: ndis.h:45
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ ULONG _Out_ PNDIS_STRING _Out_ PNDIS_HANDLE KeyHandle
Definition: ndis.h:4715
_Out_ PNDIS_HANDLE _In_ PNDIS_STRING ProtocolSection
Definition: ndis.h:6073
#define NDIS_STATUS_RESOURCES
Definition: ndis.h:466
#define NDIS_VERSION
Definition: ndissys.h:27
NTSYSAPI NTSTATUS NTAPI ZwClose(_In_ HANDLE Handle)
_In_opt_ ULONG Base
Definition: rtlfuncs.h:2451
NTSYSAPI VOID NTAPI RtlCopyUnicodeString(PUNICODE_STRING DestinationString, PUNICODE_STRING SourceString)
@ KeyBasicInformation
Definition: nt_native.h:1131
#define REG_BINARY
Definition: nt_native.h:1496
@ KeyValuePartialInformation
Definition: nt_native.h:1182
#define KEY_ALL_ACCESS
Definition: nt_native.h:1041
NTSYSAPI NTSTATUS NTAPI RtlUnicodeStringToInteger(PUNICODE_STRING String, ULONG Base, PULONG Value)
#define REG_MULTI_SZ
Definition: nt_native.h:1501
NTSYSAPI NTSTATUS NTAPI RtlIntegerToUnicodeString(ULONG Value, ULONG Base, PUNICODE_STRING String)
#define UNICODE_NULL
#define L(x)
Definition: ntvdm.h:50
unsigned short USHORT
Definition: pedump.c:61
const WCHAR * str
#define REG_DWORD
Definition: sdbapi.c:596
_CRTIMP wchar_t *__cdecl wcsncpy(wchar_t *_Dest, const wchar_t *_Source, size_t _Count)
_Check_return_ _CRTIMP int __cdecl wcsncmp(_In_reads_or_z_(_MaxCount) const wchar_t *_Str1, _In_reads_or_z_(_MaxCount) const wchar_t *_Str2, _In_ size_t _MaxCount)
#define STATUS_SUCCESS
Definition: shellext.h:65
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:69
#define STATUS_BUFFER_OVERFLOW
Definition: shellext.h:66
Definition: typedefs.h:120
LIST_ENTRY ListEntry
Definition: miniport.h:44
ULONG ResourceType
Definition: miniport.h:45
NDIS_PARAMETER_TYPE ParameterType
Definition: ndis.h:939
USHORT MaximumLength
Definition: env_spec_w32.h:370
#define RTL_CONSTANT_STRING(s)
Definition: tunneltest.c:14
uint16_t * PWSTR
Definition: typedefs.h:56
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define IN
Definition: typedefs.h:39
uint16_t * PWCHAR
Definition: typedefs.h:56
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40
_In_ WDFCOLLECTION _In_ ULONG Index
_Must_inspect_result_ _In_ WDFDEVICE _In_ ULONG _In_ ACCESS_MASK _In_opt_ PWDF_OBJECT_ATTRIBUTES KeyAttributes
Definition: wdfdevice.h:2660
_Must_inspect_result_ _In_ WDFDEVICE _In_ PCUNICODE_STRING KeyName
Definition: wdfdevice.h:2699
_Must_inspect_result_ _In_ WDFDEVICE _In_ WDFSTRING String
Definition: wdfdevice.h:2433
unsigned char UCHAR
Definition: xmlstorage.h:181
__wchar_t WCHAR
Definition: xmlstorage.h:180