STATIC AGESA_STATUS ReadSmbusByteData ( IN UINT16 Iobase, IN UINT8 Address, OUT UINT8 *ByteData, IN UINTN Offset ) { UINTN Status; UINT64 Limit; Address |= 1; // set read bit __outbyte (Iobase + 0, 0xFF); // clear error status __outbyte (Iobase + 1, 0x1F); // clear error status __outbyte (Iobase + 3, Offset); // offset in eeprom __outbyte (Iobase + 4, Address); // slave address and read bit __outbyte (Iobase + 2, 0x48); // read byte command /* time limit to avoid hanging for unexpected error status (should never happen) */ Limit = __rdtsc () + 2000000000 / 10; for (;;) { Status = __inbyte (Iobase); if (__rdtsc () > Limit) break; if ((Status & 2) == 0) continue; // SMBusInterrupt not set, keep waiting if ((Status & 1) == 1) continue; // HostBusy set, keep waiting break; } *ByteData = __inbyte (Iobase + 5); if (Status == 2) Status = 0; // check for done with no errors return Status; }
STATIC AGESA_STATUS ReadSmbusByte ( IN UINT16 Iobase, IN UINT8 Address, OUT UINT8 *Buffer ) { UINTN Status; UINT64 Limit; __outbyte (Iobase + 0, 0xFF); // clear error status __outbyte (Iobase + 1, 0x1F); // clear error status __outbyte (Iobase + 2, 0x44); // read command // time limit to avoid hanging for unexpected error status Limit = __rdtsc () + 2000000000 / 10; for (;;) { Status = __inbyte (Iobase); if (__rdtsc () > Limit) break; if ((Status & 2) == 0) continue; // SMBusInterrupt not set, keep waiting if ((Status & 1) == 1) continue; // HostBusy set, keep waiting break; } Buffer [0] = __inbyte (Iobase + 5); if (Status == 2) Status = 0; // check for done with no errors return Status; }
VOID NTAPI HalpInitializeClock(VOID) { //PKPRCB Prcb = KeGetCurrentPrcb(); ULONG Increment; USHORT RollOver; ULONG Flags = 0; /* Get increment and rollover for the largest time clock ms possible */ Increment = HalpRolloverTable[HalpLargestClockMS - 1].HighPart; RollOver = (USHORT)HalpRolloverTable[HalpLargestClockMS - 1].LowPart; /* Set the maximum and minimum increment with the kernel */ HalpCurrentTimeIncrement = Increment; KeSetTimeIncrement(Increment, HalpRolloverTable[0].HighPart); /* Disable interrupts */ Flags = __readmsr(); _disable(); /* Set the rollover */ __outbyte(TIMER_CONTROL_PORT, TIMER_SC0 | TIMER_BOTH | TIMER_MD2); __outbyte(TIMER_DATA_PORT0, RollOver & 0xFF); __outbyte(TIMER_DATA_PORT0, RollOver >> 8); /* Restore interrupts if they were previously enabled */ __writemsr(Flags); /* Save rollover and return */ HalpCurrentRollOver = RollOver; }
static int readSmbusByteData (int iobase, int address, char *buffer, int offset) { unsigned int status; UINT64 limit; address |= 1; // set read bit __outbyte (iobase + 0, 0xFF); // clear error status __outbyte (iobase + 1, 0x1F); // clear error status __outbyte (iobase + 3, offset); // offset in eeprom __outbyte (iobase + 4, address); // slave address and read bit __outbyte (iobase + 2, 0x48); // read byte command // time limit to avoid hanging for unexpected error status (should never happen) limit = __rdtsc () + 2000000000 / 10; for (;;) { status = __inbyte (iobase); if (__rdtsc () > limit) break; if ((status & 2) == 0) continue; // SMBusInterrupt not set, keep waiting if ((status & 1) == 1) continue; // HostBusy set, keep waiting break; } buffer [0] = __inbyte (iobase + 5); if (status == 2) status = 0; // check for done with no errors return status; }
STATIC VOID WritePmReg ( IN UINT8 Reg, IN UINT8 Data ) { __outbyte (0xCD6, Reg); __outbyte (0xCD7, Data); }
STATIC VOID SetupFch ( IN UINT16 IN IoBase ) { AMD_CONFIG_PARAMS StdHeader; UINT32 PciData32; UINT8 PciData8; PCI_ADDR PciAddress; /* Set SMBUS MMIO. */ PciAddress.AddressValue = MAKE_SBDFO (0, 0, 20, 0, 0x90); PciData32 = (SMBUS_BASE_ADDR & 0xFFFFFFF0) | BIT0; LibAmdPciWrite(AccessWidth32, PciAddress, &PciData32, &StdHeader); /* Enable SMBUS MMIO. */ PciAddress.AddressValue = MAKE_SBDFO (0, 0, 20, 0, 0xD2); LibAmdPciRead(AccessWidth8, PciAddress, &PciData8, &StdHeader); ; PciData8 |= BIT0; LibAmdPciWrite(AccessWidth8, PciAddress, &PciData8, &StdHeader); /* set SMBus clock to 400 KHz */ __outbyte (IoBase + 0x0E, 66000000 / 400000 / 4); }
/* Initialize the serial device hardware. */ VOID SerialPortInitialize(UINT16 Port, UINTN Baudrate) { // Map 5..8 to 0..3 UINT8 Data = (UINT8)(m_Data - (UINT8)5); // Calculate divisor for baud generator UINTN Divisor = BAUDRATE_MAX / Baudrate; // Set communications format UINT8 OutputData = (UINT8)((DLAB << 7) | (m_BreakSet << 6) | (m_Parity << 3) | (m_Stop << 2) | Data); __outbyte((UINTN)(Port + LCR_OFFSET), OutputData); // Configure baud rate __outbyte((UINTN)(Port + BAUD_HIGH_OFFSET), (UINT8)(Divisor >> 8)); __outbyte((UINTN)(Port + BAUD_LOW_OFFSET), (UINT8)(Divisor & 0xff)); // Switch back to bank 0 OutputData = (UINT8)((~DLAB << 7) | (m_BreakSet << 6) | (m_Parity << 3) | (m_Stop << 2) | Data); __outbyte((UINTN)(Port + LCR_OFFSET), OutputData); }
/** * Write a single smbus byte. */ UINT8 writeSmbusByte(UINT16 iobase, UINT8 address, UINT8 buffer, int offset) { unsigned int status = -1; UINT64 time_limit; /* clear status register */ __outbyte(iobase + SMBUS_STATUS_REG, 0xFF); __outbyte(iobase + SMBUS_SLAVE_STATUS_REG, 0x1F); /* set offset, set slave address, set data and start writing */ __outbyte(iobase + SMBUS_CONTROL_REG, offset); __outbyte(iobase + SMBUS_HOST_CMD_REG, address & (~READ_BIT)); __outbyte(iobase + SMBUS_DATA0_REG, buffer); __outbyte(iobase + SMBUS_COMMAND_REG, SMBUS_WRITE_BYTE_COMMAND); /* time limit to avoid hanging for unexpected error status */ time_limit = __rdtsc() + MAX_READ_TSC_COUNT; while (__rdtsc() <= time_limit) { status = __inbyte(iobase + SMBUS_STATUS_REG); if ((status & SMBUS_INTERRUPT_MASK) == 0) continue; /* SMBusInterrupt not set, keep waiting */ if ((status & HOSTBUSY_MASK) != 0) continue; /* HostBusy set, keep waiting */ break; } if (status != STATUS__COMPLETED_SUCCESSFULLY) return AGESA_ERROR; return AGESA_SUCCESS; }
/* Write data to serial device. */ VOID SerialPortWrite(UINT16 Port, UINT8 Data) { UINT8 Status = 0; do { // Wait for the serail port to be ready Status = __inbyte(Port + LSR_OFFSET); } while ((Status & LSR_TXRDY) == 0); __outbyte(Port, Data); }
// Perform IO instruction according with parameters _Use_decl_annotations_ static void VmmpIoWrapper(bool to_memory, bool is_string, SIZE_T size_of_access, unsigned short port, void *address, unsigned long count) { NT_ASSERT(size_of_access == 1 || size_of_access == 2 || size_of_access == 4); // Update CR3 with that of the guest since below code is going to access // memory. const auto guest_cr3 = UtilVmRead(VmcsField::kGuestCr3); const auto vmm_cr3 = __readcr3(); __writecr3(guest_cr3); // clang-format off if (to_memory) { if (is_string) { // IN switch (size_of_access) { case 1: *reinterpret_cast<UCHAR*>(address) = __inbyte(port); break; case 2: *reinterpret_cast<USHORT*>(address) = __inword(port); break; case 4: *reinterpret_cast<ULONG*>(address) = __indword(port); break; } } else { // INS switch (size_of_access) { case 1: __inbytestring(port, reinterpret_cast<UCHAR*>(address), count); break; case 2: __inwordstring(port, reinterpret_cast<USHORT*>(address), count); break; case 4: __indwordstring(port, reinterpret_cast<ULONG*>(address), count); break; } } } else { if (is_string) { // OUT switch (size_of_access) { case 1: __outbyte(port, *reinterpret_cast<UCHAR*>(address)); break; case 2: __outword(port, *reinterpret_cast<USHORT*>(address)); break; case 4: __outdword(port, *reinterpret_cast<ULONG*>(address)); break; } } else { // OUTS switch (size_of_access) { case 1: __outbytestring(port, reinterpret_cast<UCHAR*>(address), count); break; case 2: __outwordstring(port, reinterpret_cast<USHORT*>(address), count); break; case 4: __outdwordstring(port, reinterpret_cast<ULONG*>(address), count); break; } } } // clang-format on __writecr3(vmm_cr3); }
static int readSmbusByte (int iobase, int address, char *buffer) { unsigned int status; UINT64 limit; __outbyte (iobase + 0, 0xFF); // clear error status __outbyte (iobase + 2, 0x44); // read command // time limit to avoid hanging for unexpected error status limit = __rdtsc () + 2000000000 / 10; for (;;) { status = __inbyte (iobase); if (__rdtsc () > limit) break; if ((status & 2) == 0) continue; // SMBusInterrupt not set, keep waiting if ((status & 1) == 1) continue; // HostBusy set, keep waiting break; } buffer [0] = __inbyte (iobase + 5); if (status == 2) status = 0; // check for done with no errors return status; }
static int smb_write_blk(u8 slave, u8 command, u8 length, const u8 *data) { __outbyte(SMB0_STATUS, 0x1E); // clear error status __outbyte(SMB0_ADDRESS, slave & ~1); // slave addr + direction = out __outbyte(SMB0_HOSTCMD, command); // or destination offset __outbyte(SMB0_DATA0, length); // sent before data __inbyte(SMB0_CONTROL); // reset block data array while (length--) __outbyte(SMB0_BLOCKDATA, *(data++)); __outbyte(SMB0_CONTROL, 0x54); // execute block write, no IRQ while (__inbyte(SMB0_STATUS) == 0x01); // busy, no errors return __inbyte(SMB0_STATUS) ^ 0x02; // 0x02 = completed, no errors }
static void setupFch(UINT16 ioBase) { AMD_CONFIG_PARAMS StdHeader; UINT32 PciData32; UINT8 PciData8; PCI_ADDR PciAddress; /* Set SMBus MMIO. */ PciAddress.AddressValue = MAKE_SBDFO (0, 0, 20, 0, 0x90); PciData32 = (ioBase & 0xFFFFFFF0) | BIT0; LibAmdPciWrite(AccessWidth32, PciAddress, &PciData32, &StdHeader); /* Enable SMBus MMIO. */ PciAddress.AddressValue = MAKE_SBDFO (0, 0, 20, 0, 0xD2); LibAmdPciRead(AccessWidth8, PciAddress, &PciData8, &StdHeader); ; PciData8 |= BIT0; LibAmdPciWrite(AccessWidth8, PciAddress, &PciData8, &StdHeader); /* Set SMBus clock to 400 KHz */ __outbyte(ioBase + SMBUS_CLOCK_REG, SMBUS_FREQUENCY_CONST / 400000); }
/** * Read a single SPD byte. If the first byte is being read, set up the * address and offset. Following bytes auto increment. */ static UINT8 readSmbusByte(UINT16 iobase, UINT8 address, char *buffer, int offset, int initial_offset) { unsigned int status = -1; UINT64 time_limit; /* clear status register */ __outbyte(iobase + SMBUS_STATUS_REG, 0xFF); __outbyte(iobase + SMBUS_SLAVE_STATUS_REG, 0x1F); if (offset == initial_offset) { /* Set offset, set slave address and start reading */ __outbyte(iobase + SMBUS_CONTROL_REG, offset); __outbyte(iobase + SMBUS_HOST_CMD_REG, address | READ_BIT); __outbyte(iobase + SMBUS_COMMAND_REG, SMBUS_READ_BYTE_COMMAND); } else { /* Issue read command - auto increments to next byte */ __outbyte(iobase + SMBUS_COMMAND_REG, SMBUS_READ_COMMAND); } /* time limit to avoid hanging for unexpected error status */ time_limit = __rdtsc() + MAX_READ_TSC_COUNT; while (__rdtsc() <= time_limit) { status = __inbyte(iobase + SMBUS_STATUS_REG); if ((status & SMBUS_INTERRUPT_MASK) == 0) continue; /* SMBusInterrupt not set, keep waiting */ if ((status & HOSTBUSY_MASK) != 0) continue; /* HostBusy set, keep waiting */ break; } if (status != STATUS__COMPLETED_SUCCESSFULLY) return AGESA_ERROR; buffer[0] = __inbyte(iobase + SMBUS_DATA0_REG); return AGESA_SUCCESS; }
NTSTATUS __fastcall DispatchIOCTL(IN PIOCTL_INFO RequestInfo, OUT PULONG ResponseLength) { NTSTATUS Status = STATUS_SUCCESS; #define INPUT(Type) ((Type)(RequestInfo->InputBuffer)) #define OUTPUT(Type) ((Type)(RequestInfo->OutputBuffer)) #define SET_RESPONSE_LENGTH(Length) if (ResponseLength != NULL) {*ResponseLength = (Length);} switch (RequestInfo->ControlCode) { // DriverFunctions: case GET_HANDLES_COUNT: *OUTPUT(PULONG) = GetHandlesCount(); SET_RESPONSE_LENGTH(sizeof(ULONG)); break; // NativeFunctions: case START_BEEPER: __outbyte(0x61, __inbyte(0x61) | 3); break; case STOP_BEEPER: __outbyte(0x61, __inbyte(0x61) & 252); break; case SET_BEEPER_REGIME: __outbyte(0x43, 0xB6); break; case SET_BEEPER_OUT: __outbyte(0x61, __inbyte(0x61) | 2); break; case SET_BEEPER_IN: __outbyte(0x61, __inbyte(0x61) & 253); break; case SET_BEEPER_DIVIDER: SetBeeperDivider(*INPUT(PWORD)); break; case SET_BEEPER_FREQUENCY: SetBeeperFrequency(*INPUT(PWORD)); break; case READ_IO_PORT_BYTE: *OUTPUT(PBYTE) = __inbyte(*INPUT(PWORD)); SET_RESPONSE_LENGTH(sizeof(BYTE)); break; case READ_IO_PORT_WORD: *OUTPUT(PWORD) = __inword(*INPUT(PWORD)); SET_RESPONSE_LENGTH(sizeof(WORD)); break; case READ_IO_PORT_DWORD: *OUTPUT(PDWORD32) = __indword(*INPUT(PWORD)); SET_RESPONSE_LENGTH(sizeof(DWORD)); break; case WRITE_IO_PORT_BYTE: __outbyte( INPUT(PWRITE_IO_PORT_BYTE_INPUT)->PortNumber, INPUT(PWRITE_IO_PORT_BYTE_INPUT)->Data ); break; case WRITE_IO_PORT_WORD: __outword( INPUT(PWRITE_IO_PORT_WORD_INPUT)->PortNumber, INPUT(PWRITE_IO_PORT_WORD_INPUT)->Data ); break; case WRITE_IO_PORT_DWORD: __outdword( INPUT(PWRITE_IO_PORT_DWORD_INPUT)->PortNumber, INPUT(PWRITE_IO_PORT_DWORD_INPUT)->Data ); break; case RDPMC: *OUTPUT(PULONGLONG) = __readpmc(*INPUT(PULONG)); SET_RESPONSE_LENGTH(sizeof(ULONGLONG)); break; case RDMSR: *OUTPUT(PULONGLONG) = __readmsr(*INPUT(PULONG)); SET_RESPONSE_LENGTH(sizeof(ULONGLONG)); break; case WRMSR: __writemsr(INPUT(PWRMSR_INPUT)->Index, INPUT(PWRMSR_INPUT)->Data); break; // MemoryUtils: case ALLOC_KERNEL_MEMORY: *OUTPUT(PUINT64) = (SIZE_T)GetMem(*INPUT(PSIZE_T)); SET_RESPONSE_LENGTH(sizeof(UINT64)); break; case FREE_KERNEL_MEMORY: FreeMem((PVOID)*INPUT(PUINT64)); break; case COPY_MEMORY: RtlCopyMemory( (PVOID)INPUT(PCOPY_MEMORY_INPUT)->Destination, (PVOID)INPUT(PCOPY_MEMORY_INPUT)->Source, (SIZE_T)INPUT(PCOPY_MEMORY_INPUT)->Size ); break; case FILL_MEMORY: RtlFillMemory( (PVOID)INPUT(PFILL_MEMORY_INPUT)->Destination, (SIZE_T)INPUT(PFILL_MEMORY_INPUT)->Size, (BYTE)INPUT(PFILL_MEMORY_INPUT)->FillingByte ); break; case ALLOC_PHYSICAL_MEMORY: *OUTPUT(PUINT64) = (SIZE_T)AllocPhysicalMemory( INPUT(PALLOC_PHYSICAL_MEMORY_INPUT)->PhysicalAddress, (SIZE_T)INPUT(PALLOC_PHYSICAL_MEMORY_INPUT)->Size ); SET_RESPONSE_LENGTH(sizeof(UINT64)); break; case FREE_PHYSICAL_MEMORY: FreePhysicalMemory((PVOID)*INPUT(PUINT64)); break; case GET_PHYSICAL_ADDRESS: *OUTPUT(PPHYSICAL_ADDRESS) = GetPhysicalAddressInProcess( (HANDLE)INPUT(PGET_PHYSICAL_ADDRESS_INPUT)->ProcessID, (PVOID)INPUT(PGET_PHYSICAL_ADDRESS_INPUT)->VirtualAddress ); SET_RESPONSE_LENGTH(sizeof(PHYSICAL_ADDRESS)); break; case READ_PHYSICAL_MEMORY: *OUTPUT(PBOOL) = ReadPhysicalMemory( INPUT(PREAD_PHYSICAL_MEMORY_INPUT)->PhysicalAddress, (PVOID)INPUT(PREAD_PHYSICAL_MEMORY_INPUT)->Buffer, INPUT(PREAD_PHYSICAL_MEMORY_INPUT)->BufferSize ); SET_RESPONSE_LENGTH(sizeof(BOOL)); break; case WRITE_PHYSICAL_MEMORY: *OUTPUT(PBOOL) = WritePhysicalMemory( INPUT(PWRITE_PHYSICAL_MEMORY_INPUT)->PhysicalAddress, (PVOID)INPUT(PWRITE_PHYSICAL_MEMORY_INPUT)->Buffer, INPUT(PWRITE_PHYSICAL_MEMORY_INPUT)->BufferSize ); SET_RESPONSE_LENGTH(sizeof(BOOL)); break; case READ_DMI_MEMORY: ReadDmiMemory((PVOID)*INPUT(PUINT64), DMI_SIZE); SET_RESPONSE_LENGTH(DMI_SIZE); break; // ShellCode: case EXECUTE_SHELL_CODE: *OUTPUT(PSHELL_STATUS) = ExecuteShell( (PVOID)INPUT(PEXECUTE_SHELL_CODE_INPUT)->EntryPoint, (PVOID)INPUT(PEXECUTE_SHELL_CODE_INPUT)->CodeBlock, (PVOID)INPUT(PEXECUTE_SHELL_CODE_INPUT)->InputData, (PVOID)INPUT(PEXECUTE_SHELL_CODE_INPUT)->OutputData, (PVOID)INPUT(PEXECUTE_SHELL_CODE_INPUT)->Result ); SET_RESPONSE_LENGTH(sizeof(SHELL_STATUS)); break; // ProcessesUtils: case ALLOC_VIRTUAL_MEMORY: OUTPUT(PALLOC_VIRTUAL_MEMORY_OUTPUT)->Status = VirtualAllocInProcess( (HANDLE)INPUT(PALLOC_VIRTUAL_MEMORY_INPUT)->ProcessId, (SIZE_T)INPUT(PALLOC_VIRTUAL_MEMORY_INPUT)->Size, (PVOID*)&OUTPUT(PALLOC_VIRTUAL_MEMORY_OUTPUT)->VirtualAddress ); SET_RESPONSE_LENGTH(sizeof(ALLOC_VIRTUAL_MEMORY_OUTPUT)); break; case FREE_VIRTUAL_MEMORY: *OUTPUT(PNTSTATUS) = VirtualFreeInProcess( (HANDLE)INPUT(PFREE_VIRTUAL_MEMORY_INPUT)->ProcessId, (PVOID)INPUT(PFREE_VIRTUAL_MEMORY_INPUT)->VirtualAddress ); SET_RESPONSE_LENGTH(sizeof(NTSTATUS)); break; case MAP_VIRTUAL_MEMORY: OUTPUT(PMAP_VIRTUAL_MEMORY_OUTPUT)->MappedMemory = MapVirtualMemory( (HANDLE)INPUT(PMAP_VIRTUAL_MEMORY_INPUT)->ProcessId, INPUT(PMAP_VIRTUAL_MEMORY_INPUT)->VirtualAddress, INPUT(PMAP_VIRTUAL_MEMORY_INPUT)->MapToVirtualAddress, INPUT(PMAP_VIRTUAL_MEMORY_INPUT)->Size, UserMode, (PMDL*)&(OUTPUT(PMAP_VIRTUAL_MEMORY_OUTPUT)->Mdl) ); SET_RESPONSE_LENGTH(sizeof(MAP_VIRTUAL_MEMORY_OUTPUT)); break; case UNMAP_VIRTUAL_MEMORY: UnmapVirtualMemory( INPUT(PUNMAP_VIRTUAL_MEMORY_INPUT)->Mdl, INPUT(PUNMAP_VIRTUAL_MEMORY_INPUT)->MappedMemory ); break; case READ_PROCESS_MEMORY: *OUTPUT(PBOOL) = ReadProcessMemory( (HANDLE)INPUT(PREAD_PROCESS_MEMORY_INPUT)->ProcessId, (PVOID)INPUT(PREAD_PROCESS_MEMORY_INPUT)->VirtualAddress, (PVOID)INPUT(PREAD_PROCESS_MEMORY_INPUT)->Buffer, INPUT(PREAD_PROCESS_MEMORY_INPUT)->BytesToRead, TRUE, (MEMORY_ACCESS_TYPE)INPUT(PREAD_PROCESS_MEMORY_INPUT)->AccessType ); SET_RESPONSE_LENGTH(sizeof(BOOL)); break; case WRITE_PROCESS_MEMORY: *OUTPUT(PBOOL) = WriteProcessMemory( (HANDLE)INPUT(PWRITE_PROCESS_MEMORY_INPUT)->ProcessId, (PVOID)INPUT(PWRITE_PROCESS_MEMORY_INPUT)->VirtualAddress, (PVOID)INPUT(PWRITE_PROCESS_MEMORY_INPUT)->Buffer, INPUT(PWRITE_PROCESS_MEMORY_INPUT)->BytesToWrite, TRUE, (MEMORY_ACCESS_TYPE)INPUT(PWRITE_PROCESS_MEMORY_INPUT)->AccessType ); SET_RESPONSE_LENGTH(sizeof(BOOL)); break; case RAISE_IOPL_BY_TF: #ifdef _AMD64_ RaiseIOPLByTrapFrame(); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; case RESET_IOPL_BY_TF: #ifdef _AMD64_ ResetIOPLByTrapFrame(); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; case RAISE_IOPL_BY_TF_SCAN: RaiseIOPLByTrapFrameScan(); break; case RESET_IOPL_BY_TF_SCAN: ResetIOPLByTrapFrameScan(); break; case RAISE_IOPL_BY_TSS: #ifdef _X86_ RaiseIOPLByTSS(); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; case RESET_IOPL_BY_TSS: #ifdef _x86_ ResetIOPLByTSS(); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; case RAISE_IOPM: #ifdef _X86_ *OUTPUT(PNTSTATUS) = RaiseIOPM((HANDLE)*INPUT(PUINT64)); SET_RESPONSE_LENGTH(sizeof(NTSTATUS)); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; case RESET_IOPM: #ifdef _X86_ *OUTPUT(PNTSTATUS) = ResetIOPM((HANDLE)*INPUT(PUINT64)); SET_RESPONSE_LENGTH(sizeof(NTSTATUS)); #else Status = STATUS_NOT_IMPLEMENTED; #endif break; // PCI: case READ_PCI_CONFIG: OUTPUT(PREAD_PCI_CONFIG_OUTPUT)->Status = ReadPciConfig( INPUT(PREAD_PCI_CONFIG_INPUT)->PciAddress, INPUT(PREAD_PCI_CONFIG_INPUT)->PciOffset, (PVOID)INPUT(PREAD_PCI_CONFIG_INPUT)->Buffer, INPUT(PREAD_PCI_CONFIG_INPUT)->BufferSize, &OUTPUT(PREAD_PCI_CONFIG_OUTPUT)->BytesRead ); SET_RESPONSE_LENGTH(sizeof(READ_PCI_CONFIG_OUTPUT)); break; case WRITE_PCI_CONFIG: OUTPUT(PWRITE_PCI_CONFIG_OUTPUT)->Status = WritePciConfig( INPUT(PWRITE_PCI_CONFIG_INPUT)->PciAddress, INPUT(PWRITE_PCI_CONFIG_INPUT)->PciOffset, (PVOID)INPUT(PWRITE_PCI_CONFIG_INPUT)->Buffer, INPUT(PWRITE_PCI_CONFIG_INPUT)->BufferSize, &OUTPUT(PWRITE_PCI_CONFIG_OUTPUT)->BytesWritten ); SET_RESPONSE_LENGTH(sizeof(WRITE_PCI_CONFIG_OUTPUT)); break; default: Status = STATUS_NOT_IMPLEMENTED; break; } return Status; #undef INPUT #undef OUTPUT #undef SET_RESPONSE_LENGTH }
static void writePmReg(UINT8 reg, UINT8 data) { __outbyte(PMIO_INDEX_REG, reg); __outbyte(PMIO_DATA_REG, data); }
VOID NTAPI HalpInitializeLegacyPIC(VOID) { I8259_ICW1 Icw1; I8259_ICW2 Icw2; I8259_ICW3 Icw3; I8259_ICW4 Icw4; /* Initialize ICW1 for master, interval 8, edge-triggered mode with ICW4 */ Icw1.NeedIcw4 = TRUE; Icw1.OperatingMode = Cascade; Icw1.Interval = Interval8; Icw1.InterruptMode = EdgeTriggered; Icw1.Init = TRUE; Icw1.InterruptVectorAddress = 0; __outbyte(PIC1_CONTROL_PORT, Icw1.Bits); /* ICW2 - interrupt vector offset */ Icw2.Bits = PRIMARY_VECTOR_BASE; __outbyte(PIC1_DATA_PORT, Icw2.Bits); /* Connect slave to IRQ 2 */ Icw3.Bits = 0; Icw3.SlaveIrq2 = TRUE; __outbyte(PIC1_DATA_PORT, Icw3.Bits); /* Enable 8086 mode, non-automatic EOI, non-buffered mode, non special fully nested mode */ Icw4.SystemMode = New8086Mode; Icw4.EoiMode = NormalEoi; Icw4.BufferedMode = NonBuffered; Icw4.SpecialFullyNestedMode = FALSE; Icw4.Reserved = 0; __outbyte(PIC1_DATA_PORT, Icw4.Bits); /* Mask all interrupts */ __outbyte(PIC1_DATA_PORT, 0xFF); /* Initialize ICW1 for slave, interval 8, edge-triggered mode with ICW4 */ Icw1.NeedIcw4 = TRUE; Icw1.InterruptMode = EdgeTriggered; Icw1.OperatingMode = Cascade; Icw1.Interval = Interval8; Icw1.Init = TRUE; Icw1.InterruptVectorAddress = 0; /* This is only used in MCS80/85 mode */ __outbyte(PIC2_CONTROL_PORT, Icw1.Bits); /* Set interrupt vector base */ Icw2.Bits = PRIMARY_VECTOR_BASE + 8; __outbyte(PIC2_DATA_PORT, Icw2.Bits); /* Slave ID */ Icw3.Bits = 0; Icw3.SlaveId = 2; __outbyte(PIC2_DATA_PORT, Icw3.Bits); /* Enable 8086 mode, non-automatic EOI, non-buffered mode, non special fully nested mode */ Icw4.SystemMode = New8086Mode; Icw4.EoiMode = NormalEoi; Icw4.BufferedMode = NonBuffered; Icw4.SpecialFullyNestedMode = FALSE; Icw4.Reserved = 0; __outbyte(PIC2_DATA_PORT, Icw4.Bits); /* Mask all interrupts */ __outbyte(PIC2_DATA_PORT, 0xFF); }
static void writePmReg (int reg, int data) { __outbyte (0xCD6, reg); __outbyte (0xCD7, data); }