⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 legacy.c

📁 串口Windows驱动
💻 C
📖 第 1 页 / 共 5 页
字号:
   pPartial++;


   //
   // Interrupt information
   //

   pPartial->Type = CmResourceTypeInterrupt;

      //
      // We have to globally share resources even though this is a **BAD**
      // thing.  We must do it for multiport cards.  DO NOT replicate
      // this in other drivers.
      //

      pPartial->ShareDisposition = CmResourceShareDriverExclusive;

   if (PUserData->UserInterruptMode == Latched) {
      pPartial->Flags = CM_RESOURCE_INTERRUPT_LATCHED;
   } else {
      pPartial->Flags = CM_RESOURCE_INTERRUPT_LEVEL_SENSITIVE;
   }

   pPartial->u.Interrupt.Vector = PUserData->UserVector;

   if (PUserData->UserLevel == 0) {
      pPartial->u.Interrupt.Level = PUserData->UserVector;
   } else {
      pPartial->u.Interrupt.Level = PUserData->UserLevel;
   }


   //
   // ISR register information (if needed)
   //

   if (countOfPartials == 3) {

      pPartial++;

      pPartial->Type = CmResourceTypePort;

      //
      // We have to globally share resources even though this is a **BAD**
      // thing.  We must do it for multiport cards.  DO NOT replicate
      // this in other drivers.
      //

      pPartial->ShareDisposition = CmResourceShareDriverExclusive;

      pPartial->Flags = (USHORT)PUserData->UserAddressSpace;
      pPartial->u.Port.Start = PUserData->UserInterruptStatus;
      pPartial->u.Port.Length = SERIAL_STATUS_LENGTH;
   }

   *PPartialCount = countOfPartials;

   SerialDbgPrintEx(SERTRACECALLS, "Leave SerialBuildResourceList\n");

   return status;
}


NTSTATUS
SerialMigrateLegacyRegistry(IN PDEVICE_OBJECT PPdo,
                            IN PSERIAL_USER_DATA PUserData, BOOLEAN IsMulti)
/*++

Routine Description:

    This routine will copy information stored in the registry for a legacy
    device over to the PnP Device Parameters section.


    This is pageable INIT because it is only called from SerialEnumerateLegacy
    which is also pageable INIT.


Arguments:

    PPdo - Pointer to the Device Object we are migrating.

    PUserData - Pointer to user supplied values.


Return Value:

    STATUS_SUCCESS on success, apropriate error value otherwise.

--*/
{
   NTSTATUS status;
   HANDLE pnpKey;
   UNICODE_STRING pnpNameBuf;
   ULONG isMultiport = 1;
   ULONG one = 1;

   PAGED_CODE();

   SerialDbgPrintEx(SERTRACECALLS, "Enter SerialMigrateLegacyRegistry\n");

   status = IoOpenDeviceRegistryKey(PPdo, PLUGPLAY_REGKEY_DEVICE,
                                    STANDARD_RIGHTS_WRITE, &pnpKey);

   if (!NT_SUCCESS(status)) {
      SerialDbgPrintEx(SERTRACECALLS, "Leave (1) SerialMigrateLegacyRegistry"
                                 "\n");
      return status;
   }

   //
   // Allocate a buffer to copy the port name over.
   //

   pnpNameBuf.MaximumLength = sizeof(WCHAR) * 256;
   pnpNameBuf.Length = 0;
   pnpNameBuf.Buffer = ExAllocatePool(PagedPool, sizeof(WCHAR) * 257);

   if (pnpNameBuf.Buffer == NULL) {
      SerialLogError(PPdo->DriverObject, NULL, PUserData->UserPort,
                     SerialPhysicalZero, 0, 0, 0, 63, STATUS_SUCCESS,
                     SERIAL_INSUFFICIENT_RESOURCES, 0, NULL, 0, NULL);

      SerialDbgPrintEx(SERERRORS, "Couldn't allocate buffer for the PnP "
                             "link\n");
      status = STATUS_INSUFFICIENT_RESOURCES;
      goto MigrateLegacyExit;

   }

   RtlZeroMemory(pnpNameBuf.Buffer, pnpNameBuf.MaximumLength + sizeof(WCHAR));


   //
   // Add the port name -- ALWAYS
   //

   RtlAppendUnicodeStringToString(&pnpNameBuf, &PUserData->UserSymbolicLink);
   RtlZeroMemory(((PUCHAR)(&pnpNameBuf.Buffer[0])) + pnpNameBuf.Length,
                 sizeof(WCHAR));

   status = SerialPutRegistryKeyValue(pnpKey, L"PortName", sizeof(L"PortName"),
                                      REG_SZ, pnpNameBuf.Buffer,
                                      pnpNameBuf.Length + sizeof(WCHAR));

   ExFreePool(pnpNameBuf.Buffer);

   if (!NT_SUCCESS(status)) {
      SerialDbgPrintEx(SERERRORS, "Couldn't migrate PortName\n");
      goto MigrateLegacyExit;
   }

   //
   // If it was part of a multiport card, save that info as well
   //

   if (IsMulti) {
      status = SerialPutRegistryKeyValue(pnpKey, L"MultiportDevice",
                                         sizeof(L"MultiportDevice"), REG_DWORD,
                                         &isMultiport, sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't mark multiport\n");
         goto MigrateLegacyExit;
      }
   }




   //
   // If a port index was specified, save it
   //

   if (PUserData->UserPortIndex != 0) {
      status = SerialPutRegistryKeyValue(pnpKey, L"PortIndex",
                                         sizeof(L"PortIndex"), REG_DWORD,
                                         &PUserData->UserPortIndex,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate PortIndex\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If not default clock rate, save it
   //

   if (PUserData->UserClockRate != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"ClockRate",
                                         sizeof(L"ClockRate"), REG_DWORD,
                                         &PUserData->UserClockRate,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate ClockRate\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If there is a user index, save it.
   //

   if (PUserData->UserIndexed != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"Indexed", sizeof(L"Indexed"),
                                         REG_DWORD, &PUserData->UserIndexed,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate Indexed\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If the port was disabled, save that.
   //

   if (PUserData->DisablePort != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"DisablePort",
                                         sizeof(L"DisablePort"), REG_DWORD,
                                         &PUserData->DisablePort,
                                         sizeof(ULONG));
      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate DisablePort\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If Fifo's were forced enabled, save that.
   //
   if (PUserData->ForceFIFOEnable != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"ForceFifoEnable",
                                         sizeof(L"ForceFifoEnable"), REG_DWORD,
                                         &PUserData->ForceFIFOEnable,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate ForceFifoEnable\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If RxFIFO had an override, save that.
   //

   if (PUserData->RxFIFO != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"RxFIFO", sizeof(L"RxFIFO"),
                                         REG_DWORD, &PUserData->RxFIFO,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate RxFIFO\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If TxFIFO had an override, save that.
   //

   if (PUserData->TxFIFO != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"TxFIFO", sizeof(L"TxFIFO"),
                                         REG_DWORD, &PUserData->TxFIFO,
                                         sizeof(ULONG));

      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate TxFIFO\n");
         goto MigrateLegacyExit;
      }
   }


   //
   // If MaskInverted had an override, save that.
   //

   if (PUserData->MaskInverted != SERIAL_BAD_VALUE) {
      status = SerialPutRegistryKeyValue(pnpKey, L"MaskInverted",
                                         sizeof(L"MaskInverted"), REG_DWORD,
                                         &PUserData->MaskInverted,
                                         sizeof(ULONG));
      if (!NT_SUCCESS(status)) {
         SerialDbgPrintEx(SERERRORS, "Couldn't migrate MaskInverted\n");
         goto MigrateLegacyExit;
      }
   }


   MigrateLegacyExit:;

   ZwClose(pnpKey);

   SerialDbgPrintEx(SERTRACECALLS, "Leave (2) SerialMigrateLegacyRegistry"
                              "\n");

   return status;
}




BOOLEAN
SerialIsUserDataValid(IN PDRIVER_OBJECT DriverObject,
                      IN PKEY_BASIC_INFORMATION UserSubKey,
                      IN PRTL_QUERY_REGISTRY_TABLE Parameters,
                      IN ULONG DefaultInterfaceType,
                      IN PSERIAL_USER_DATA PUserData)
/*++

Routine Description:

    This routine will do some basic sanity checking on the data
    found in the registry.


    This is pageable INIT because it is only called from SerialEnumerateLegacy
    which is also pageable INIT.


Arguments:

    DriverObject - Used only for logging.

    UserSubKey -  Used only for logging.

    Parameters - Used only for logging.

    DefaultInterfaceType - Default bus type we found.

    PUserData - Pointer to the values found in the registry we need to validate.


Return Value:

    TRUE if data appears valid, FALSE otherwise.

--*/
{
   ULONG zero = 0;
   BOOLEAN rval = TRUE;

   PAGED_CODE();


   SerialDbgPrintEx(SERTRACECALLS, "Enter SerialIsUserDataValid\n");

   //
   // Make sure that the interrupt is non zero (which we defaulted
   // it to).
   //
   // Make sure that the portaddress is non zero (which we defaulted
   // it to).
   //
   // Make sure that the DosDevices is not NULL (which we defaulted
   // it to).
   //
   // We need to make sure that if an interrupt status
   // was specified, that a port index was also specfied,
   // and if so that the port index is <= maximum ports
   // on a board.
   //
   // We should also validate that the bus type and number
   // are correct.
   //
   // We will also validate that the interrupt mode makes
   // sense for the bus.
   //

   if (!PUserData->UserPort.LowPart) {

      //
      // Ehhhh! Lose Game.
      //

      SerialLogError(
                    DriverObject,
                    NULL,
                    PUserData->UserPort,
                    SerialPhysicalZero,
                    0,
                    0,
                    0,
                    64,
                    STATUS_SUCCESS,
                    SERIAL_INVALID_USER_CONFIG,
                    UserSubKey->NameLength+sizeof(WCHAR),
                    &UserSubKey->Name[0],
                    (wcslen(Parameters[1].Name)*sizeof(WCHAR))
                    + sizeof(WCHAR),
                    Parameters[1].Name
                    );
      SerialDbgPrintEx(SERERRORS, "Bogus port address %ws\n",
                       Parameters[1].Name);
      rval = FALSE;
      goto SerialIsUserDataValidError;
   }

   if (!PUserData->UserVector) {

      //
      // Ehhhh! Lose Game.
      //

      SerialLogError(
                    DriverObject,
                    NULL,
                    PUserData->UserPort,
                    SerialPhysicalZero,
                    0,
                    0,

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -