mirror of
https://github.com/reactos/reactos.git
synced 2025-08-03 04:07:29 +00:00
[ISAPNP] Refactor the configuration code
- Remove useless checks - Increase code readability
This commit is contained in:
parent
76ec8411a4
commit
2981e63a31
3 changed files with 168 additions and 181 deletions
|
@ -1079,7 +1079,7 @@ ReadCurrentResources(
|
|||
{
|
||||
LogDevice->Dma[i].CurrentChannel = ReadDmaChannel(ReadDataPort, i);
|
||||
|
||||
if (LogDevice->Dma[i].CurrentChannel == 4)
|
||||
if (LogDevice->Dma[i].CurrentChannel == DMACHANNEL_NONE)
|
||||
break;
|
||||
}
|
||||
for (i = 0; i < RTL_NUMBER_OF(LogDevice->MemRange); i++)
|
||||
|
@ -1128,165 +1128,119 @@ ReadCurrentResources(
|
|||
static
|
||||
CODE_SEG("PAGE")
|
||||
VOID
|
||||
WriteResources(
|
||||
_In_ PUCHAR ReadDataPort,
|
||||
_In_ PISAPNP_LOGICAL_DEVICE LogDevice,
|
||||
_In_ PCM_PARTIAL_RESOURCE_LIST PartialResourceList)
|
||||
IsaProgramIoDecoder(
|
||||
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor,
|
||||
_In_ UCHAR Index)
|
||||
{
|
||||
UCHAR i,
|
||||
NumberOfIo = 0,
|
||||
NumberOfIrq = 0,
|
||||
NumberOfDma = 0,
|
||||
NumberOfMemory = 0,
|
||||
NumberOfMemory32 = 0;
|
||||
PAGED_CODE();
|
||||
|
||||
ASSERT(Descriptor->u.Port.Start.QuadPart <= 0xFFFF);
|
||||
|
||||
WriteWord(ISAPNP_IOBASE(Index), Descriptor->u.Port.Start.LowPart);
|
||||
}
|
||||
|
||||
static
|
||||
CODE_SEG("PAGE")
|
||||
VOID
|
||||
IsaProgramIrqSelect(
|
||||
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor,
|
||||
_In_ UCHAR Index)
|
||||
{
|
||||
UCHAR TypeSelect;
|
||||
|
||||
PAGED_CODE();
|
||||
|
||||
WriteLogicalDeviceNumber(LogDevice->LDN);
|
||||
ASSERT(Descriptor->u.Interrupt.Level <= 15);
|
||||
|
||||
for (i = 0; i < PartialResourceList->Count; i++)
|
||||
if (Descriptor->Flags & CM_RESOURCE_INTERRUPT_LATCHED)
|
||||
TypeSelect = IRQTYPE_HIGH_EDGE;
|
||||
else
|
||||
TypeSelect = IRQTYPE_LOW_LEVEL;
|
||||
|
||||
WriteByte(ISAPNP_IRQNO(Index), Descriptor->u.Interrupt.Level);
|
||||
WriteByte(ISAPNP_IRQTYPE(Index), TypeSelect);
|
||||
}
|
||||
|
||||
static
|
||||
CODE_SEG("PAGE")
|
||||
VOID
|
||||
IsaProgramDmaSelect(
|
||||
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor,
|
||||
_In_ UCHAR Index)
|
||||
{
|
||||
PAGED_CODE();
|
||||
|
||||
ASSERT(Descriptor->u.Dma.Channel <= 7);
|
||||
|
||||
WriteByte(ISAPNP_DMACHANNEL(Index), Descriptor->u.Dma.Channel);
|
||||
}
|
||||
|
||||
static
|
||||
CODE_SEG("PAGE")
|
||||
NTSTATUS
|
||||
IsaProgramMemoryDecoder(
|
||||
_In_ PUCHAR ReadDataPort,
|
||||
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor,
|
||||
_In_ BOOLEAN IsMemory32,
|
||||
_In_ UCHAR Information,
|
||||
_In_ UCHAR Index)
|
||||
{
|
||||
UCHAR MemoryControl;
|
||||
ULONG LengthLimit;
|
||||
|
||||
PAGED_CODE();
|
||||
|
||||
if (!IsMemory32)
|
||||
{
|
||||
PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor = &PartialResourceList->PartialDescriptors[i];
|
||||
/* The 24-bit memory address decoder always considers bits 0:7 to be zeros */
|
||||
if (Descriptor->u.Memory.Start.LowPart & 0xFF)
|
||||
return STATUS_INVALID_PARAMETER;
|
||||
|
||||
switch (Descriptor->Type)
|
||||
if (Information & MEMRANGE_16_BIT_MEMORY_MASK)
|
||||
MemoryControl = MEMORY_USE_16_BIT_DECODER;
|
||||
else
|
||||
MemoryControl = MEMORY_USE_8_BIT_DECODER;
|
||||
|
||||
if (ReadMemoryControl(ReadDataPort, Index) & MEMORY_UPPER_LIMIT)
|
||||
{
|
||||
case CmResourceTypePort:
|
||||
{
|
||||
(VOID)FindIoDescriptor(LogDevice,
|
||||
0,
|
||||
Descriptor->u.Port.Start.LowPart,
|
||||
Descriptor->u.Port.Start.LowPart +
|
||||
Descriptor->u.Port.Length - 1,
|
||||
NULL,
|
||||
NULL);
|
||||
|
||||
WriteWord(ISAPNP_IOBASE(NumberOfIo), (USHORT)Descriptor->u.Port.Start.LowPart);
|
||||
|
||||
++NumberOfIo;
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeInterrupt:
|
||||
{
|
||||
(VOID)FindIrqDescriptor(LogDevice, Descriptor->u.Interrupt.Level);
|
||||
|
||||
WriteByte(ISAPNP_IRQNO(NumberOfIrq), (UCHAR)Descriptor->u.Interrupt.Level);
|
||||
WriteByte(ISAPNP_IRQTYPE(NumberOfIrq),
|
||||
Descriptor->Flags & CM_RESOURCE_INTERRUPT_LATCHED
|
||||
? IRQTYPE_HIGH_EDGE : IRQTYPE_LOW_LEVEL);
|
||||
|
||||
++NumberOfIrq;
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeDma:
|
||||
{
|
||||
(VOID)FindDmaDescriptor(LogDevice, Descriptor->u.Dma.Channel);
|
||||
|
||||
WriteByte(ISAPNP_DMACHANNEL(NumberOfDma), (UCHAR)Descriptor->u.Dma.Channel);
|
||||
|
||||
++NumberOfDma;
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeMemory:
|
||||
{
|
||||
UCHAR Information;
|
||||
UCHAR MemoryControl = MEMORY_USE_8_BIT_DECODER;
|
||||
|
||||
(VOID)FindMemoryDescriptor(LogDevice,
|
||||
Descriptor->u.Memory.Start.LowPart,
|
||||
Descriptor->u.Memory.Start.LowPart +
|
||||
Descriptor->u.Memory.Length - 1,
|
||||
&Information);
|
||||
|
||||
if (LogicalDevice->Flags & ISAPNP_HAS_MEM24_DECODER)
|
||||
{
|
||||
if (Information & MEMRANGE_16_BIT_MEMORY_MASK)
|
||||
MemoryControl = MEMORY_USE_16_BIT_DECODER;
|
||||
|
||||
WriteWord(ISAPNP_MEMBASE(NumberOfMemory),
|
||||
(USHORT)(Descriptor->u.Memory.Start.LowPart >> 8));
|
||||
|
||||
if (ReadMemoryControl(ReadDataPort, NumberOfMemory) & MEMORY_UPPER_LIMIT)
|
||||
{
|
||||
WriteByte(ISAPNP_MEMCONTROL(NumberOfMemory),
|
||||
MemoryControl | MEMORY_UPPER_LIMIT);
|
||||
WriteWord(ISAPNP_MEMLIMIT(NumberOfMemory),
|
||||
(USHORT)((Descriptor->u.Memory.Start.LowPart +
|
||||
Descriptor->u.Memory.Length) >> 8));
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteByte(ISAPNP_MEMCONTROL(NumberOfMemory), MemoryControl);
|
||||
WriteWord(ISAPNP_MEMLIMIT(NumberOfMemory),
|
||||
(USHORT)(LENGTH_TO_RANGE_LENGTH(Descriptor->
|
||||
u.Memory.Length) >> 8));
|
||||
}
|
||||
|
||||
++NumberOfMemory;
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteDoubleWord(ISAPNP_MEMBASE32(NumberOfMemory32),
|
||||
Descriptor->u.Memory.Start.LowPart);
|
||||
|
||||
if ((Information & MEMRANGE_16_BIT_MEMORY_MASK) == MEMRANGE_32_BIT_MEMORY_ONLY)
|
||||
MemoryControl = MEMORY_USE_32_BIT_DECODER;
|
||||
else if (Information & MEMRANGE_16_BIT_MEMORY_MASK)
|
||||
MemoryControl = MEMORY_USE_16_BIT_DECODER;
|
||||
|
||||
if (ReadMemoryControl32(ReadDataPort, NumberOfMemory32) & MEMORY_UPPER_LIMIT)
|
||||
{
|
||||
WriteByte(ISAPNP_MEMCONTROL32(NumberOfMemory32),
|
||||
MemoryControl | MEMORY_UPPER_LIMIT);
|
||||
WriteDoubleWord(ISAPNP_MEMLIMIT32(NumberOfMemory32),
|
||||
Descriptor->u.Memory.Start.LowPart +
|
||||
Descriptor->u.Memory.Length);
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteByte(ISAPNP_MEMCONTROL32(NumberOfMemory32), MemoryControl);
|
||||
WriteDoubleWord(ISAPNP_MEMLIMIT32(NumberOfMemory32),
|
||||
LENGTH_TO_RANGE_LENGTH(Descriptor->u.Memory.Length));
|
||||
}
|
||||
|
||||
++NumberOfMemory32;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
break;
|
||||
MemoryControl |= MEMORY_UPPER_LIMIT;
|
||||
LengthLimit = Descriptor->u.Memory.Start.LowPart + Descriptor->u.Memory.Length;
|
||||
}
|
||||
else
|
||||
{
|
||||
LengthLimit = LENGTH_TO_RANGE_LENGTH(Descriptor->u.Memory.Length);
|
||||
}
|
||||
LengthLimit >>= 8;
|
||||
|
||||
WriteWord(ISAPNP_MEMBASE(Index), Descriptor->u.Memory.Start.LowPart >> 8);
|
||||
WriteByte(ISAPNP_MEMCONTROL(Index), MemoryControl);
|
||||
WriteWord(ISAPNP_MEMLIMIT(Index), LengthLimit);
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((Information & MEMRANGE_16_BIT_MEMORY_MASK) == MEMRANGE_32_BIT_MEMORY_ONLY)
|
||||
MemoryControl = MEMORY_USE_32_BIT_DECODER;
|
||||
else if (Information & MEMRANGE_16_BIT_MEMORY_MASK)
|
||||
MemoryControl = MEMORY_USE_16_BIT_DECODER;
|
||||
else
|
||||
MemoryControl = MEMORY_USE_8_BIT_DECODER;
|
||||
|
||||
if (ReadMemoryControl32(ReadDataPort, Index) & MEMORY_UPPER_LIMIT)
|
||||
{
|
||||
MemoryControl |= MEMORY_UPPER_LIMIT;
|
||||
LengthLimit = Descriptor->u.Memory.Start.LowPart + Descriptor->u.Memory.Length;
|
||||
}
|
||||
else
|
||||
{
|
||||
LengthLimit = LENGTH_TO_RANGE_LENGTH(Descriptor->u.Memory.Length);
|
||||
}
|
||||
|
||||
WriteDoubleWord(ISAPNP_MEMBASE32(Index), Descriptor->u.Memory.Start.LowPart);
|
||||
WriteByte(ISAPNP_MEMCONTROL32(Index), MemoryControl);
|
||||
WriteDoubleWord(ISAPNP_MEMLIMIT32(Index), LengthLimit);
|
||||
}
|
||||
|
||||
for (i = NumberOfIo; i < RTL_NUMBER_OF(LogDevice->Io); i++)
|
||||
{
|
||||
WriteWord(ISAPNP_IOBASE(i), 0);
|
||||
}
|
||||
for (i = NumberOfIrq; i < RTL_NUMBER_OF(LogDevice->Irq); i++)
|
||||
{
|
||||
WriteByte(ISAPNP_IRQNO(i), 0);
|
||||
WriteByte(ISAPNP_IRQTYPE(i), 0);
|
||||
}
|
||||
for (i = NumberOfDma; i < RTL_NUMBER_OF(LogDevice->Dma); i++)
|
||||
{
|
||||
WriteByte(ISAPNP_DMACHANNEL(i), 4);
|
||||
}
|
||||
for (i = NumberOfMemory; i < RTL_NUMBER_OF(LogDevice->MemRange); i++)
|
||||
{
|
||||
WriteWord(ISAPNP_MEMBASE(i), 0);
|
||||
WriteByte(ISAPNP_MEMCONTROL(i), 0);
|
||||
WriteWord(ISAPNP_MEMLIMIT(i), 0);
|
||||
}
|
||||
for (i = NumberOfMemory32; i < RTL_NUMBER_OF(LogDevice->MemRange32); i++)
|
||||
{
|
||||
WriteDoubleWord(ISAPNP_MEMBASE32(i), 0);
|
||||
WriteByte(ISAPNP_MEMCONTROL32(i), 0);
|
||||
WriteDoubleWord(ISAPNP_MEMLIMIT32(i), 0);
|
||||
}
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
CODE_SEG("PAGE")
|
||||
|
@ -1554,18 +1508,20 @@ IsaHwConfigureDevice(
|
|||
_In_ PISAPNP_LOGICAL_DEVICE LogicalDevice,
|
||||
_In_ PCM_RESOURCE_LIST Resources)
|
||||
{
|
||||
UCHAR i,
|
||||
NumberOfIo = 0,
|
||||
ULONG i;
|
||||
UCHAR NumberOfIo = 0,
|
||||
NumberOfIrq = 0,
|
||||
NumberOfDma = 0,
|
||||
NumberOfMemory = 0;
|
||||
NumberOfMemory = 0,
|
||||
NumberOfMemory32 = 0;
|
||||
|
||||
PAGED_CODE();
|
||||
|
||||
if (!Resources)
|
||||
return STATUS_INSUFFICIENT_RESOURCES;
|
||||
|
||||
/* Validate the resource list */
|
||||
WriteLogicalDeviceNumber(LogicalDevice->LDN);
|
||||
|
||||
for (i = 0; i < Resources->List[0].PartialResourceList.Count; i++)
|
||||
{
|
||||
PCM_PARTIAL_RESOURCE_DESCRIPTOR Descriptor =
|
||||
|
@ -1575,63 +1531,68 @@ IsaHwConfigureDevice(
|
|||
{
|
||||
case CmResourceTypePort:
|
||||
{
|
||||
if (++NumberOfIo > RTL_NUMBER_OF(LogicalDevice->Io))
|
||||
if (NumberOfIo >= RTL_NUMBER_OF(LogicalDevice->Io))
|
||||
return STATUS_INVALID_PARAMETER_1;
|
||||
|
||||
if (!FindIoDescriptor(LogicalDevice,
|
||||
0,
|
||||
Descriptor->u.Port.Start.LowPart,
|
||||
Descriptor->u.Port.Start.LowPart +
|
||||
Descriptor->u.Port.Length - 1,
|
||||
NULL,
|
||||
NULL))
|
||||
{
|
||||
return STATUS_RESOURCE_DATA_NOT_FOUND;
|
||||
}
|
||||
|
||||
IsaProgramIoDecoder(Descriptor, NumberOfIo++);
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeInterrupt:
|
||||
{
|
||||
if (++NumberOfIrq > RTL_NUMBER_OF(LogicalDevice->Irq))
|
||||
if (NumberOfIrq >= RTL_NUMBER_OF(LogicalDevice->Irq))
|
||||
return STATUS_INVALID_PARAMETER_2;
|
||||
|
||||
if (!FindIrqDescriptor(LogicalDevice, Descriptor->u.Interrupt.Level))
|
||||
return STATUS_RESOURCE_DATA_NOT_FOUND;
|
||||
|
||||
IsaProgramIrqSelect(Descriptor, NumberOfIrq++);
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeDma:
|
||||
{
|
||||
if (++NumberOfDma > RTL_NUMBER_OF(LogicalDevice->Dma))
|
||||
if (NumberOfDma >= RTL_NUMBER_OF(LogicalDevice->Dma))
|
||||
return STATUS_INVALID_PARAMETER_3;
|
||||
|
||||
if (!FindDmaDescriptor(LogicalDevice, Descriptor->u.Dma.Channel))
|
||||
return STATUS_RESOURCE_DATA_NOT_FOUND;
|
||||
|
||||
IsaProgramDmaSelect(Descriptor, NumberOfDma++);
|
||||
break;
|
||||
}
|
||||
|
||||
case CmResourceTypeMemory:
|
||||
{
|
||||
BOOLEAN Memory32;
|
||||
BOOLEAN IsMemory32;
|
||||
UCHAR Index, Information;
|
||||
NTSTATUS Status;
|
||||
|
||||
if (++NumberOfMemory > RTL_NUMBER_OF(LogicalDevice->MemRange))
|
||||
if ((NumberOfMemory + NumberOfMemory32) >= RTL_NUMBER_OF(LogicalDevice->MemRange))
|
||||
return STATUS_INVALID_PARAMETER_4;
|
||||
|
||||
/*
|
||||
* The PNP ROM provides an information byte for each memory descriptor
|
||||
* which is then used to program the memory control register.
|
||||
*/
|
||||
if (!FindMemoryDescriptor(LogicalDevice,
|
||||
Descriptor->u.Memory.Start.LowPart,
|
||||
Descriptor->u.Memory.Start.LowPart +
|
||||
Descriptor->u.Memory.Length - 1,
|
||||
NULL))
|
||||
&Information))
|
||||
{
|
||||
return STATUS_RESOURCE_DATA_NOT_FOUND;
|
||||
}
|
||||
|
||||
if ((LogicalDevice->Flags & ISAPNP_HAS_MEM24_DECODER) && (Descriptor->u.Memory.Start.LowPart & 0xFF))
|
||||
return STATUS_INVALID_PARAMETER;
|
||||
/* We can have a 24- or 32-bit memory decoder, but not both */
|
||||
IsMemory32 = !!(LogicalDevice->Flags & ISAPNP_HAS_MEM32_DECODER);
|
||||
|
||||
if (IsMemory32)
|
||||
Index = NumberOfMemory32++;
|
||||
else
|
||||
Index = NumberOfMemory++;
|
||||
|
||||
Status = IsaProgramMemoryDecoder(FdoExt->ReadDataPort,
|
||||
Descriptor,
|
||||
IsMemory32,
|
||||
Information,
|
||||
Index);
|
||||
if (!NT_SUCCESS(Status))
|
||||
return Status;
|
||||
|
||||
break;
|
||||
}
|
||||
|
@ -1641,7 +1602,32 @@ IsaHwConfigureDevice(
|
|||
}
|
||||
}
|
||||
|
||||
WriteResources(FdoExt->ReadDataPort, LogicalDevice, &Resources->List[0].PartialResourceList);
|
||||
/* Disable the unclaimed device resources */
|
||||
for (i = NumberOfIo; i < RTL_NUMBER_OF(LogicalDevice->Io); i++)
|
||||
{
|
||||
WriteWord(ISAPNP_IOBASE(i), 0);
|
||||
}
|
||||
for (i = NumberOfIrq; i < RTL_NUMBER_OF(LogicalDevice->Irq); i++)
|
||||
{
|
||||
WriteByte(ISAPNP_IRQNO(i), 0);
|
||||
WriteByte(ISAPNP_IRQTYPE(i), 0);
|
||||
}
|
||||
for (i = NumberOfDma; i < RTL_NUMBER_OF(LogicalDevice->Dma); i++)
|
||||
{
|
||||
WriteByte(ISAPNP_DMACHANNEL(i), DMACHANNEL_NONE);
|
||||
}
|
||||
for (i = NumberOfMemory; i < RTL_NUMBER_OF(LogicalDevice->MemRange); i++)
|
||||
{
|
||||
WriteWord(ISAPNP_MEMBASE(i), 0);
|
||||
WriteByte(ISAPNP_MEMCONTROL(i), 0);
|
||||
WriteWord(ISAPNP_MEMLIMIT(i), 0);
|
||||
}
|
||||
for (i = NumberOfMemory32; i < RTL_NUMBER_OF(LogicalDevice->MemRange32); i++)
|
||||
{
|
||||
WriteDoubleWord(ISAPNP_MEMBASE32(i), 0);
|
||||
WriteByte(ISAPNP_MEMCONTROL32(i), 0);
|
||||
WriteDoubleWord(ISAPNP_MEMLIMIT32(i), 0);
|
||||
}
|
||||
|
||||
KeStallExecutionProcessor(10000);
|
||||
|
||||
|
|
|
@ -652,7 +652,7 @@ IsaPnpCreateLogicalDeviceResources(
|
|||
}
|
||||
for (i = 0; i < RTL_NUMBER_OF(LogDev->Dma); i++)
|
||||
{
|
||||
if (LogDev->Dma[i].CurrentChannel != 4)
|
||||
if (LogDev->Dma[i].CurrentChannel != DMACHANNEL_NONE)
|
||||
ResourceCount++;
|
||||
else
|
||||
break;
|
||||
|
@ -736,7 +736,7 @@ IsaPnpCreateLogicalDeviceResources(
|
|||
}
|
||||
for (i = 0; i < RTL_NUMBER_OF(LogDev->Dma); i++)
|
||||
{
|
||||
if (LogDev->Dma[i].CurrentChannel == 4)
|
||||
if (LogDev->Dma[i].CurrentChannel == DMACHANNEL_NONE)
|
||||
break;
|
||||
|
||||
Descriptor = &ResourceList->List[0].PartialResourceList.PartialDescriptors[ResourceCount++];
|
||||
|
|
|
@ -46,6 +46,7 @@ extern "C" {
|
|||
#define IRQTYPE_LOW_LEVEL 0x01
|
||||
#define IRQTYPE_HIGH_EDGE 0x02
|
||||
#define ISAPNP_DMACHANNEL(n) (0x74 + (n))
|
||||
#define DMACHANNEL_NONE 4
|
||||
#define ISAPNP_MEMBASE32(n) ((n) == 0 ? 0x76 : (0x70 + (n) * 16))
|
||||
#define ISAPNP_MEMCONTROL32(n) ((n) == 0 ? 0x7A : (0x74 + (n) * 16))
|
||||
#define ISAPNP_MEMLIMIT32(n) ((n) == 0 ? 0x7B : (0x75 + (n) * 16))
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue