📄 plf_misc.c
字号:
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR,
CYGARC_REG_PCI_CFG_ADDR_ENABLE |
(bus << CYGARC_REG_PCI_CFG_ADDR_BUSNO_shift) |
(devfn << CYGARC_REG_PCI_CFG_ADDR_FUNC_shift) |
(offset & ~3));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, CYGARC_REG_PCI_CFG_CMD_RCFG);
_DELAY();
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_DATA, config_dword);
shift = (offset & 3) * 8;
config_dword &= ~(0xffff << shift);
config_dword |= (data << shift);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR,
CYGARC_REG_PCI_CFG_ADDR_ENABLE |
(bus << CYGARC_REG_PCI_CFG_ADDR_BUSNO_shift) |
(devfn << CYGARC_REG_PCI_CFG_ADDR_FUNC_shift) |
(offset & ~3));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_DATA, config_dword);
_DELAY();
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, CYGARC_REG_PCI_CFG_CMD_WCFG);
_DELAY();
}
void
cyg_hal_plf_pci_cfg_write_byte (cyg_uint32 bus, cyg_uint32 devfn,
cyg_uint32 offset, cyg_uint8 data)
{
cyg_uint32 config_dword, shift;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR,
CYGARC_REG_PCI_CFG_ADDR_ENABLE |
(bus << CYGARC_REG_PCI_CFG_ADDR_BUSNO_shift) |
(devfn << CYGARC_REG_PCI_CFG_ADDR_FUNC_shift) |
(offset & ~3));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, CYGARC_REG_PCI_CFG_CMD_RCFG);
_DELAY();
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_DATA, config_dword);
shift = (offset & 3) * 8;
config_dword &= ~(0xff << shift);
config_dword |= (data << shift);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR,
CYGARC_REG_PCI_CFG_ADDR_ENABLE |
(bus << CYGARC_REG_PCI_CFG_ADDR_BUSNO_shift) |
(devfn << CYGARC_REG_PCI_CFG_ADDR_FUNC_shift) |
(offset & ~3));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_DATA, config_dword);
_DELAY();
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, CYGARC_REG_PCI_CFG_CMD_WCFG);
_DELAY();
}
//--------------------------------------------------------------------------
// IO space accessor functions
#if 0 // Don't need these after all. But keep them around just in case...
static void
pci_io_delay(void)
{
int i = 100;
cyg_uint32 flg;
do {
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_FLG, flg);
} while (i-- && (flg & CYGARC_REG_PCI_CFG_FLG_ACTIVE));
// FIXME: what happens on timeout? Do we need to fill in 0xfffffff
// in read data, by any chance?
}
static void
pci_io_status(void)
{
// FIXME: check status...
}
void
cyg_hal_plf_pci_io_write_byte (cyg_uint32 addr, cyg_uint8 data)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
int shift = io_addr & 3;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_DATA, ((cyg_uint32)data << (8*shift)));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, (CYGARC_REG_PCI_CFG_CMD_BE0 << shift)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_WRITE
| CYGARC_REG_PCI_CFG_CMD_WT);
pci_io_delay();
}
void
cyg_hal_plf_pci_io_write_word (cyg_uint32 addr, cyg_uint16 data)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
int shift = io_addr & 2;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_DATA, ((cyg_uint32)data << (8*shift)));
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, ((CYGARC_REG_PCI_CFG_CMD_BE1|CYGARC_REG_PCI_CFG_CMD_BE0) << shift)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_WRITE
| CYGARC_REG_PCI_CFG_CMD_WT);
pci_io_delay();
}
void
cyg_hal_plf_pci_io_write_dword (cyg_uint32 addr, cyg_uint32 data)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_DATA, data);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD,
(CYGARC_REG_PCI_CFG_CMD_BE3|CYGARC_REG_PCI_CFG_CMD_BE2
| CYGARC_REG_PCI_CFG_CMD_BE1|CYGARC_REG_PCI_CFG_CMD_BE0)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_WRITE
| CYGARC_REG_PCI_CFG_CMD_WT);
pci_io_delay();
}
cyg_uint8
cyg_hal_plf_pci_io_read_byte (cyg_uint32 addr)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
cyg_uint32 data;
int shift = io_addr & 3;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, (CYGARC_REG_PCI_CFG_CMD_BE0 << shift)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_READ
| CYGARC_REG_PCI_CFG_CMD_RD);
pci_io_delay();
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_DATA, data);
return (cyg_uint8)(0xff & (data >> (8*shift)));
}
cyg_uint16
cyg_hal_plf_pci_io_read_word (cyg_uint32 addr)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
cyg_uint32 data;
int shift = io_addr & 2;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD, ((CYGARC_REG_PCI_CFG_CMD_BE1|CYGARC_REG_PCI_CFG_CMD_BE0) << shift)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_READ
| CYGARC_REG_PCI_CFG_CMD_RD);
pci_io_delay();
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_DATA, data);
return (cyg_uint16)(0xffff & (data >> (shift*8)));
}
cyg_uint32
cyg_hal_plf_pci_io_read_dword (cyg_uint32 addr)
{
cyg_uint32 io_addr = addr - HAL_PCI_PHYSICAL_IO_BASE;
cyg_uint32 data;
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_ADDR, io_addr & ~3);
HAL_WRITE_UINT32(CYGARC_REG_PCI_CFG_CMD,
(CYGARC_REG_PCI_CFG_CMD_BE3|CYGARC_REG_PCI_CFG_CMD_BE2
| CYGARC_REG_PCI_CFG_CMD_BE1|CYGARC_REG_PCI_CFG_CMD_BE0)
| CYGARC_REG_PCI_CFG_CMD_CMDEN
| CYGARC_REG_PCI_CFG_CMD_IO_READ
| CYGARC_REG_PCI_CFG_CMD_RD);
pci_io_delay();
HAL_READ_UINT32(CYGARC_REG_PCI_CFG_DATA, data);
return data;
}
#endif
//--------------------------------------------------------------------------
// PCI interrupt decoding
static cyg_uint32
cyg_hal_plf_pci_arbiter(CYG_ADDRWORD vector, CYG_ADDRWORD data)
{
cyg_uint32 isr_ret, int_sts;
HAL_READ_UINT32(CYGARC_REG_SD0001_INT_STS1, int_sts);
if (int_sts & CYGARC_REG_SD0001_INT_INTA) {
isr_ret = hal_call_isr (CYGNUM_HAL_INTERRUPT_PCIA);
#ifdef CYGIMP_HAL_COMMON_INTERRUPTS_CHAIN
if (isr_ret & CYG_ISR_HANDLED)
#endif
return isr_ret;
}
if (int_sts & CYGARC_REG_SD0001_INT_INTB) {
isr_ret = hal_call_isr (CYGNUM_HAL_INTERRUPT_PCIB);
#ifdef CYGIMP_HAL_COMMON_INTERRUPTS_CHAIN
if (isr_ret & CYG_ISR_HANDLED)
#endif
return isr_ret;
}
if (int_sts & CYGARC_REG_SD0001_INT_INTC) {
isr_ret = hal_call_isr (CYGNUM_HAL_INTERRUPT_PCIC);
#ifdef CYGIMP_HAL_COMMON_INTERRUPTS_CHAIN
if (isr_ret & CYG_ISR_HANDLED)
#endif
return isr_ret;
}
if (int_sts & CYGARC_REG_SD0001_INT_INTD) {
isr_ret = hal_call_isr (CYGNUM_HAL_INTERRUPT_PCID);
#ifdef CYGIMP_HAL_COMMON_INTERRUPTS_CHAIN
if (isr_ret & CYG_ISR_HANDLED)
#endif
return isr_ret;
}
return 0;
}
#endif // CYGPKG_IO_PCI
//--------------------------------------------------------------------------
// eof plf_misc.c
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -