//****************************************************************************** // Function: iiReadWord8(pB) // Parameters: pB - pointer to board structure // // Returns: True if everything appears copacetic. // False if there is any error: the pB->i2eError field has the error // // Description: // // Returns the word read from the data fifo specified by the board-structure // pointer pB. Uses two 8-bit operations. Bytes are assumed to be LSB first. Is // called indirectly through pB->i2eReadWord. // //****************************************************************************** static unsigned short iiReadWord8(i2eBordStrPtr pB) { unsigned short urs; urs = INB ( pB->i2eData ); return ( ( INB ( pB->i2eData ) << 8 ) | urs ); }
int getchar(void) { uint8_t stat; while (!ISSET(stat = INB(com_lsr), LSR_RXRDY)) /* spin */ ; return (INB(com_data)); }
static u_int8_t spic_call1(struct spic_softc *sc, u_int8_t dev) { u_int8_t v1, v2; SPIC_COMMAND(0, INB(sc, SPIC_PORT2) & 2); OUTB(sc, dev, SPIC_PORT2); v1 = INB(sc, SPIC_PORT2); v2 = INB(sc, SPIC_PORT1); return v2; }
int com_getc(dev_t dev) { uint8_t stat; if (dev & 0x80) return ISSET(stat = INB(com_lsr), LSR_RXRDY); while (!ISSET(stat = INB(com_lsr), LSR_RXRDY)) /* spin */ ; return (INB(com_data)); }
static u8 spic_call1(u8 dev) { u8 v1, v2; spic_settle(); OUTB(dev, SPIC_PORT2); v1 = INB(SPIC_PORT2); v2 = INB(SPIC_PORT1); if (debug_level > 2) printf("spic call1(%x) -> %x %x\n", dev, v1, v2); return v2; }
static int get_status (elp_device * adapter) { int timeout = jiffies + TIMEOUT; register int stat1; do { stat1 = INB(adapter->io_addr+PORT_STATUS); } while (stat1 != INB(adapter->io_addr+PORT_STATUS) && jiffies < timeout); if (jiffies >= timeout) TIMEOUT_MSG(); return stat1; }
static int send_packet (elp_device * adapter, unsigned char * ptr, int len) { int i; /* * make sure the length is even and no shorter than 60 bytes */ unsigned int nlen = (((len < 60) ? 60 : len) + 1) & (~1); CHECK_NULL(adapter); CHECK_NULL(ptr); if (nlen < len) printk("Warning, bad length nlen=%d len=%d %s(%d)\n",nlen,len,filename,__LINE__); /* * send the adapter a transmit packet command. Ignore segment and offset * and make sure the length is even */ adapter->tx_pcb.command = CMD_TRANSMIT_PACKET; adapter->tx_pcb.length = sizeof(struct Xmit_pkt); adapter->tx_pcb.data.xmit_pkt.buf_ofs = adapter->tx_pcb.data.xmit_pkt.buf_seg = 0; /* Unused */ adapter->tx_pcb.data.xmit_pkt.pkt_len = nlen; if (!send_pcb(adapter, &adapter->tx_pcb)) return FALSE; /* * make sure the data register is going the right way */ cli(); OUTB(INB(adapter->io_addr+PORT_CONTROL)&(~CONTROL_DIR), adapter->io_addr+PORT_CONTROL); sti(); /* * write data to the adapter */ for (i = 0; i < (nlen/2); i++) { int timeout = jiffies + TIMEOUT; while ((INB(adapter->io_addr+PORT_STATUS)&STATUS_HRDY) == 0 && jiffies < timeout) ; if (jiffies >= timeout) { printk("*** timeout at %s(%d) writing word %d of %d ***\n", filename,__LINE__, i, nlen/2); return FALSE; } outw(*(short *)ptr, adapter->io_addr+PORT_DATA); ptr +=2; } return TRUE; }
static u_int8_t spic_call2(struct spic_softc *sc, u_int8_t dev, u_int8_t fn) { u_int8_t v1; SPIC_COMMAND(0, INB(sc, SPIC_PORT2) & 2); OUTB(sc, dev, SPIC_PORT2); SPIC_COMMAND(0, INB(sc, SPIC_PORT2) & 2); OUTB(sc, fn, SPIC_PORT1); v1 = INB(sc, SPIC_PORT1); return v1; }
char saa9730_getDebugChar(void) { char c; if (!saa9730_kgdb_active) { /* need to init device first */ return 0; } while (!(INB(&kgdb_uart->Lsr) & SAA9730_LSR_DR)) ; c = INB(&kgdb_uart->Thr_Rbr); return(c); }
int getchar(void) { uint8_t stat; int c; while (!sscom_rxrdy()) /* spin */ ; c = INB(SSCOM_URXH); stat = INB(SSCOM_UERSTAT); /* XXX */ return c; }
int spic_jogger(void) { u8 v1, v2, ov1=0, ov2=1; while (1) { v1 = INB(SPIC_PORT1); v2 = INB(SPIC_PORT2); if (v1 != ov1 || v2 != ov2) { printf("jogger %x %x\n", v1, v2); } ov1 = v1; ov2 = v2; } }
void kb_init(void) { void key_int(); char a; register_int(IRQ0 + IRQ_KEYBOARD, (ulong)key_int, KERNEL_CS, 0x8E); enable_irq(IRQ_KEYBOARD); INB(a, 0x64); while (a & 1) { INB(a, 0x60); INB(a, 0x64); } }
static void comc_setup(int speed) { OUTB(com_cfcr, CFCR_DLAB | g_com_port.comc_fmt); OUTB(com_dlbl, COMC_BPS(speed) & 0xff); OUTB(com_dlbh, COMC_BPS(speed) >> 8); OUTB(com_cfcr, g_com_port.comc_fmt); OUTB(com_mcr, MCR_RTS | MCR_DTR); for ( int wait = COMC_TXWAIT; wait > 0; wait-- ) { INB(com_data); if ( !(INB(com_lsr) & LSR_RXRDY) ) break; } }
/*---------------------------------------------------------------------------- * gfx_get_softvga_active * * This returns the active status of SoftVGA *---------------------------------------------------------------------------- */ int gfx_get_softvga_active(void) { unsigned short crtcindex, crtcdata; if (gu1_detect_vsa2()) return (gfx_get_vsa2_softvga_enable()); crtcindex = (INB(0x3CC) & 0x01) ? 0x3D4 : 0x3B4; crtcdata = crtcindex + 1; OUTB(crtcindex, CRTC_MODE_SWITCH_CONTROL); return (INB(crtcdata) & 0x1); }
/*--------------------------------------------------------------------------- * acc_i2c_ack * * This routine looks for acknowledge on the I2C bus. *--------------------------------------------------------------------------- */ int acc_i2c_ack(unsigned char busnum, int fPut, int negAck) { unsigned char reg; unsigned short bus_base_address = base_address_array[busnum]; unsigned long timeout = 0; if (fPut) { /* read operation */ if (!negAck) { /* Push Ack onto I2C bus */ reg = INB((unsigned short) (bus_base_address + ACBCTL1)); reg &= 0xE7; OUTB((unsigned short) (bus_base_address + ACBCTL1), reg); } else { /* Push negAck onto I2C bus */ reg = INB((unsigned short) (bus_base_address + ACBCTL1)); reg |= 0x10; OUTB((unsigned short) (bus_base_address + ACBCTL1), reg); } } else { /* write operation */ /* Receive Ack from I2C bus */ while (1) { reg = INB((unsigned short) (bus_base_address + ACBST)); if ((reg & 0x70) != 0) /* check SDAST, BER and NEGACK */ break; if (timeout++ == ACC_I2C_TIMEOUT) { acc_i2c_bus_recovery(busnum); return (0); } } /* CHECK FOR BUS ERROR */ if (reg & 0x20) { acc_i2c_bus_recovery(busnum); return (0); } /* CHECK NEGATIVE ACKNOWLEDGE */ if (reg & 0x10) { acc_i2c_abort_data(busnum); return (0); } } return (1); }
static u8 spic_call2(u8 dev, u8 fn) { u8 v1; while (INB(SPIC_PORT2) & 2) ; OUTB(dev, SPIC_PORT2); while (INB(SPIC_PORT2) & 2) ; OUTB(fn, SPIC_PORT1); v1 = INB(SPIC_PORT1); if (debug_level > 2) printf("spic call2(%x, %x) -> %x\n", dev, fn, v1); return v1; }
static int ac97_read (void *devc_, int index) { oss_native_word access; unsigned int data; unsigned i, N; unsigned char byte; oss_native_word flags; als300_devc *devc = devc_; MUTEX_ENTER_IRQDISABLE (devc->low_mutex, flags); i = 0; N = 1000; do { byte = INB (devc->osdev, devc->base + 6) & 0x80; if (byte == 0x00) goto next; oss_udelay (10); i++; } while (i < N); if (i >= N) cmn_err (CE_WARN, "\n Write AC97 mixer index time out !!"); next: access = index; access <<= 24; /*index */ access |= 0x80000000; OUTL (devc->osdev, access, devc->base); i = 0; N = 1000; do { byte = INB (devc->osdev, devc->base + 6); if ((byte & 0x40) != 0) goto next1; oss_udelay (10); i++; } while (i < N); if (i >= N) cmn_err (CE_WARN, "Read AC97 mixer data time out !!"); next1: data = INW (devc->osdev, devc->base + 0x04); MUTEX_EXIT_IRQRESTORE (devc->low_mutex, flags); return data; }
/*---------------------------------------------------------------------------- * gfx_vga_set_graphics_bits * * This routine sets the standard VGA sequencer, graphics controller, and * attribute registers to appropriate values for a graphics mode (packed, * 8 BPP or greater). This is also known as "VESA" modes. The timings for * a particular mode are handled by the CRTC registers, which are set by * the "gfx_vga_restore" routine. Most OSs that use VGA to set modes save * and restore the standard VGA registers themselves, which is why these * registers are not part of the save/restore paradigm. *---------------------------------------------------------------------------- */ int gfx_vga_set_graphics_bits(void) { /* SET GRAPHICS BIT IN GRAPHICS CONTROLLER REG 0x06 */ OUTB(0x3CE, 0x06); OUTB(0x3CF, 0x01); /* SET GRAPHICS BIT IN ATTRIBUTE CONTROLLER REG 0x10 */ INB(0x3BA); /* Reset flip-flop */ INB(0x3DA); OUTB(0x3C0, 0x10); OUTB(0x3C0, 0x01); return (GFX_STATUS_OK); }
/*--------------------------------------------------------------------------- * acc_i2c_request_master *--------------------------------------------------------------------------- */ int acc_i2c_request_master(unsigned char busnum) { unsigned char reg; unsigned short bus_base_address = base_address_array[busnum]; unsigned long timeout = 0; acc_i2c_start(busnum); while (1) { reg = INB((unsigned short) (bus_base_address + ACBST)); if (reg & 0x60) break; if (timeout++ == ACC_I2C_TIMEOUT) { acc_i2c_bus_recovery(busnum); return (0); } } /* CHECK FOR BUS ERROR */ if (reg & 0x20) { acc_i2c_abort_data(busnum); return (0); } /* CHECK NEGATIVE ACKNOWLEDGE */ if (reg & 0x10) { acc_i2c_abort_data(busnum); return (0); } return (1); }
/*--------------------------------------------------------------------------- * acc_i2c_write_byte * * This routine writes a byte to the I2C bus *--------------------------------------------------------------------------- */ void acc_i2c_write_byte(unsigned char busnum, unsigned char cData) { unsigned char reg; unsigned short bus_base_address = base_address_array[busnum]; unsigned long timeout = 0; while (1) { reg = INB((unsigned short) (bus_base_address + ACBST)); if (reg & 0x70) break; if (timeout++ == ACC_I2C_TIMEOUT) { acc_i2c_bus_recovery(busnum); return; } } /* CHECK FOR BUS ERROR */ if (reg & 0x20) { acc_i2c_bus_recovery(busnum); return; } /* CHECK NEGATIVE ACKNOWLEDGE */ if (reg & 0x10) { acc_i2c_abort_data(busnum); return; } /* WRITE THE DATA */ OUTB((unsigned short) (bus_base_address + ACBSDA), cData); }
static void set_hsf (elp_device * adapter, int hsf) { cli(); OUTB((INB(adapter->io_addr+PORT_CONTROL)&(~HSF_PCB_MASK))|hsf, adapter->io_addr+PORT_CONTROL); sti(); }
/*----------------------------------------------------------------------------- * gfx_gxm_config_read * * This routine reads the value of the specified GXm configuration register. *----------------------------------------------------------------------------- */ unsigned char gfx_gxm_config_read(unsigned char index) { unsigned char value = 0xFF; unsigned char lock; OUTB(0x22, GXM_CONFIG_CCR3); lock = INB(0x23); OUTB(0x22, GXM_CONFIG_CCR3); OUTB(0x23, (unsigned char)(lock | 0x10)); OUTB(0x22, index); value = INB(0x23); OUTB(0x22, GXM_CONFIG_CCR3); OUTB(0x23, lock); return (value); }
int ipmi_kcs_attach(struct ipmi_softc *sc) { int status; /* Setup function pointers. */ sc->ipmi_startup = kcs_startup; sc->ipmi_enqueue_request = ipmi_polled_enqueue_request; sc->ipmi_driver_request = kcs_driver_request; /* See if we can talk to the controller. */ status = INB(sc, KCS_CTL_STS); if (status == 0xff) { device_printf(sc->ipmi_dev, "couldn't find it\n"); return (ENXIO); } #ifdef KCS_DEBUG device_printf(sc->ipmi_dev, "KCS: initial state: %02x\n", status); #endif if (status & KCS_STATUS_OBF || KCS_STATUS_STATE(status) != KCS_STATUS_STATE_IDLE) kcs_error(sc); return (0); }
//****************************************************************************** // Function: iiTxMailEmptyII(pB) // Parameters: pB - pointer to board structure // // Returns: True if the transmit mailbox is empty. // False if it not empty. // // Description: // // Returns true or false according to whether the transmit mailbox is empty (and // therefore able to accept more mail) // // This version operates on IntelliPort-II - style FIFO's // //****************************************************************************** static int iiTxMailEmptyII(i2eBordStrPtr pB) { int port = pB->i2ePointer; OUTB ( port, SEL_OUTMAIL ); return ( INB(port) == 0 ); }
//****************************************************************************** // Function: iiWaitForTxEmptyIIEX(pB, mSdelay) // Parameters: pB - pointer to board structure // mSdelay - period to wait before returning // // Returns: True if the FIFO is empty. // False if it not empty in the required time: the pB->i2eError // field has the error. // // Description: // // Waits up to "mSdelay" milliseconds for the outgoing FIFO to become empty; if // not empty by the required time, returns false and error in pB->i2eError, // otherwise returns true. // // mSdelay == 0 is taken to mean must be empty on the first test. // // This version operates on IntelliPort-IIEX - style FIFO's // // Note this routine is organized so that if status is ok there is no delay at // all called either before or after the test. Is called indirectly through // pB->i2eWaitForTxEmpty. // //****************************************************************************** static int iiWaitForTxEmptyIIEX(i2eBordStrPtr pB, int mSdelay) { unsigned long flags; for (;;) { // By the nature of this routine, you would be using this as part of a // larger atomic context: i.e., you would use this routine to ensure the // fifo empty, then act on this information. Between these two halves, // you will generally not want to service interrupts or in any way // disrupt the assumptions implicit in the larger context. WRITE_LOCK_IRQSAVE(&Dl_spinlock,flags) if (INB(pB->i2eStatus) & STE_OUT_MT) { UPDATE_FIFO_ROOM(pB); WRITE_UNLOCK_IRQRESTORE(&Dl_spinlock,flags) COMPLETE(pB, I2EE_GOOD); } WRITE_UNLOCK_IRQRESTORE(&Dl_spinlock,flags) if (mSdelay-- == 0) break; iiDelay(pB, 1); // 1 mS granularity on checking condition } COMPLETE(pB, I2EE_TXE_TIME); }
long attach_trix_wss (long mem_start, struct address_info *hw_config) { static unsigned char interrupt_bits[12] = {-1, -1, -1, -1, -1, -1, -1, 0x08, -1, 0x10, 0x18, 0x20}; char bits; static unsigned char dma_bits[4] = {1, 2, 0, 3}; int config_port = hw_config->io_base + 0, version_port = hw_config->io_base + 3; if (!kilroy_was_here) return mem_start; /* * Set the IRQ and DMA addresses. */ bits = interrupt_bits[hw_config->irq]; if (bits == -1) return mem_start; OUTB (bits | 0x40, config_port); if ((INB (version_port) & 0x40) == 0) printk ("[IRQ Conflict?]"); OUTB (bits | dma_bits[hw_config->dma], config_port); /* Write IRQ+DMA setup */ ad1848_init ("AudioTriX Pro", hw_config->io_base + 4, hw_config->irq, hw_config->dma, hw_config->dma); return mem_start; }
static int ac97_write (void *devc_, int index, int data) { oss_native_word access; unsigned i, N; unsigned char byte; als300_devc *devc = devc_; oss_native_word flags; MUTEX_ENTER_IRQDISABLE (devc->low_mutex, flags); i = 0; N = 1000; do { byte = INB (devc->osdev, devc->base + 6) & 0x80; if (byte == 0x00) goto go; oss_udelay (10); i++; } while (i < N); if (i >= N) cmn_err (CE_WARN, "\n Write AC97 mixer index time out !!"); go: access = index; access <<= 24; /*index */ access &= 0x7fffffff; /*write */ access |= data; /*data */ OUTL (devc->osdev, access, devc->base); MUTEX_EXIT_IRQRESTORE (devc->low_mutex, flags); return 0; }
int probe_trix_wss (struct address_info *hw_config) { /* * Check if the IO port returns valid signature. The original MS Sound * system returns 0x04 while some cards (AudioTriX Pro for example) * return 0x00. */ if (!trix_set_wss_port (hw_config)) return 0; if ((INB (hw_config->io_base + 3) & 0x3f) != 0x00) { DDB (printk ("No MSS signature detected on port 0x%x\n", hw_config->io_base)); return 0; } if (hw_config->irq > 11) { printk ("AudioTriX: Bad WSS IRQ %d\n", hw_config->irq); return 0; } if (hw_config->dma != 0 && hw_config->dma != 1 && hw_config->dma != 3) { printk ("AudioTriX: Bad WSS DMA %d\n", hw_config->dma); return 0; } /* * Check that DMA0 is not in use with a 8 bit board. */ if (hw_config->dma == 0 && INB (hw_config->io_base + 3) & 0x80) { printk ("AudioTriX: Can't use DMA0 with a 8 bit card\n"); return 0; } if (hw_config->irq > 7 && hw_config->irq != 9 && INB (hw_config->io_base + 3) & 0x80) { printk ("AudioTriX: Can't use IRQ%d with a 8 bit card\n", hw_config->irq); return 0; } return ad1848_detect (hw_config->io_base + 4); }
static void kb_handle_interrupt(uint8_t irq, struct irq_regs* regs) { uint8_t scan_code = INB(0x60); if(scan_code == 0xFA && !g_initial_ack_received) { // Currently, we seem to be getting an interrupt // right after enabling the keyboard and interrupts. // The scan code is 0xFA, and the current set is 1. // This is not a valid scan code, and we currently do not // know why this is being sent. We have only ever seen it // get "sent" once, in this instance. So we simply ignore it. g_initial_ack_received = true; pic_send_eoi(pic_irq_keyboard); return; } //terminal_write_string("KB IRQ Scan code: "); //terminal_write_hex(scan_code); //terminal_write_string("\n"); // Translate scancode int sc_index = sc_get_entry_index(g_current_map, scan_code); if (sc_index < 0) { // Unknown scan-code terminal_write_string("Unknown scan code value: "); terminal_write_uint32_x(scan_code); terminal_write_string("\n"); // Reset to the first map in the set reset_map(); } else { struct sc_map_entry* sc_entry = &g_current_map->entries[sc_index]; switch (sc_entry->type) { case sc_map_entry_type_press: reset_map(); if(g_current_subscriber->down != NULL) { g_current_subscriber->down(sc_entry->data); } break; case sc_map_entry_type_release: reset_map(); if(g_current_subscriber->up != NULL) { g_current_subscriber->up(sc_entry->data); } break; case sc_map_entry_type_map: g_current_map = &g_current_set->maps[sc_entry->data]; break; } } pic_send_eoi(pic_irq_keyboard); }
/* Complete a transfer via a RD_END transaction after reading the last byte. */ static int smic_read_end(struct ipmi_softc *sc) { u_char error, status; OUTB(sc, SMIC_CTL_STS, SMIC_CC_SMS_RD_END); smic_set_busy(sc); smic_wait_for_not_busy(sc); status = INB(sc, SMIC_CTL_STS); if (status != SMIC_SC_SMS_RDY) { error = INB(sc, SMIC_DATA); device_printf(sc->ipmi_dev, "SMIC: Read did not end %02x\n", error); return (0); } return (1); }