Exemplo n.º 1
0
phantom_device_t * driver_isa_ps2m_probe( int port, int irq, int stage )
{
    (void) port;
    (void) stage;

    //dpc_request_init( &mouse_dpc, push_event );
    //hal_mutex_init( &mouse_mutex, "MouseDrv" );
    //hal_cond_init( &mouse_cond );
    hal_sem_init( &mouse_sem, "MouseDrv" );
    hal_spin_init( &elock );

    if( seq_number || ps2ms_do_init() )
        return 0;

    if( hal_irq_alloc( irq, ps2ms_int_handler, 0, HAL_IRQ_SHAREABLE ) )
        return 0;

    phantom_device_t * dev = malloc(sizeof(phantom_device_t));
    dev->name = "ps2-mouse";
    dev->seq_number = seq_number++;

    hal_start_kernel_thread((void*)mouse_push_event_thread);

    return dev;
}
phantom_device_t * driver_isa_com_probe( int port, int irq, int stage )
{
    (void) stage;
    if( !com_detect( seq_number, port) )
        return 0;


    phantom_device_t * dev = calloc(sizeof(phantom_device_t), 1);

    dev->iobase = port;
    dev->irq = irq;

    dev->name = "com";
    dev->seq_number = seq_number++;


    dev->dops.start = com_start;
    dev->dops.stop = com_stop;

    dev->dops.read = com_read;
    dev->dops.write = com_write;

    if( hal_irq_alloc( irq, &com_interrupt, dev, HAL_IRQ_SHAREABLE ) )
    {
        SHOW_ERROR( 0, "IRQ %d is busy", irq );
        free(dev);
        return 0;
    }


    com_port_t *cp = calloc( sizeof(com_port_t), 1 );
    dev->drv_private = cp;

    hal_sem_init( &(cp->rsem), "serialRd" );
    hal_sem_init( &(cp->wsem), "serialWr" );

    cp->rdq = wtty_init(); assert(cp->rdq);
    cp->wrq = wtty_init(); assert(cp->wrq);


    cp->baudRate = 9600;
    cp->stopBits = 1;
    cp->dataBits = 8;
    cp->parity = 0;

    com_setbaud(dev, cp->baudRate);

    hal_start_kernel_thread_arg( com_rd_thread, dev );
    hal_start_kernel_thread_arg( com_wr_thread, dev );

    return dev;
}
Exemplo n.º 3
0
int int_enable_irq( int shared, int irqNum,
                    unsigned int bmAddr, unsigned int ataAddr )
{

   // error if interrupts enabled now
   // error if invalid irq number
   // error if bmAddr is < 100H
   // error if shared and bmAddr is 0
   // error if ataAddr is < 100H

   if ( ata->int_use_intr_flag )      		return 1;
   if ( ( irqNum < 1 ) || ( irqNum > 15 ) )     return 2;
   if ( irqNum == 2 )      			return 2;
   if ( bmAddr && ( bmAddr < 0x0100 ) )      	return 3;
   if ( shared && ( ! bmAddr ) )      		return 4;
   if ( ataAddr < 0x0100 )      		return 5;

   // save the input parameters

   //int_shared     = shared;
   ata->int_irq_number = irqNum;
   ata->int_bmide_addr  = bmAddr;
   ata->int_ata_addr   = ataAddr;

   SHOW_INFO( 0, "IDE Set IRQ %d\n", irqNum );

   if( hal_irq_alloc( irqNum, int_handler, 0, HAL_IRQ_SHAREABLE ) )
       return 2;

   // interrupts use is now enabled

   ata->int_use_intr_flag = 1;
   //ata->int_got_it_now = 0;

   // Done.

   return 0;
}
static int rtl8169_init(rtl8169 *r)
{
    //bigtime_t time;
    int err = -1;
    //addr_t temp;
    //int i;

    hal_mutex_init(&r->lock,DEBUG_MSG_PREFIX);


    SHOW_FLOW(2, "rtl8169_init: r %p\n", r);

    /*
     r->region = vm_map_physical_memory(vm_get_kernel_aspace_id(), "rtl8169_region", (void **)&r->virt_base, REGION_ADDR_ANY_ADDRESS, r->phys_size, LOCK_KERNEL|LOCK_RW, r->phys_base);
    if(r->region < 0) {
        SHOW_ERROR0(1, "rtl8169_init: error creating memory mapped region\n");
        err = -1;
        goto err;
    }*/

    size_t n_pages = BYTES_TO_PAGES(r->phys_size);

    hal_alloc_vaddress( (void **)&r->virt_base, n_pages); // alloc address of a page, but not memory
    hal_pages_control_etc( r->phys_base, (void *)r->virt_base, n_pages, page_map_io, page_rw, 0 );

    SHOW_INFO(2, "rtl8169 mapped at address 0x%lx\n", r->virt_base);

#if 0
    /* create regions for tx and rx descriptors */
    r->rxdesc_region = vm_create_anonymous_region(vm_get_kernel_aspace_id(), "rtl8169_rxdesc", (void **)&r->rxdesc,
                                                  REGION_ADDR_ANY_ADDRESS, NUM_RX_DESCRIPTORS * DESCRIPTOR_LEN, REGION_WIRING_WIRED_CONTIG, LOCK_KERNEL|LOCK_RW);
    r->rxdesc_phys = vtophys(r->rxdesc);
    SHOW_INFO(2, "rtl8169: rx descriptors at %p, phys 0x%x\n", r->rxdesc, r->rxdesc_phys);
    r->txdesc_region = vm_create_anonymous_region(vm_get_kernel_aspace_id(), "rtl8169_txdesc", (void **)&r->txdesc,
                                                  REGION_ADDR_ANY_ADDRESS, NUM_TX_DESCRIPTORS * DESCRIPTOR_LEN, REGION_WIRING_WIRED_CONTIG, LOCK_KERNEL|LOCK_RW);
    r->txdesc_phys = vtophys(r->txdesc);
    SHOW_INFO(2, "rtl8169: tx descriptors at %p, phys 0x%x\n", r->txdesc, r->txdesc_phys);
    r->reg_spinlock = 0;

    /* create a large tx and rx buffer for the descriptors to point to */
    r->rxbuf_region = vm_create_anonymous_region(vm_get_kernel_aspace_id(), "rtl8169_rxbuf", (void **)&r->rxbuf,
                                                 REGION_ADDR_ANY_ADDRESS, NUM_RX_DESCRIPTORS * BUFSIZE_PER_FRAME, REGION_WIRING_WIRED, LOCK_KERNEL|LOCK_RW);
    r->txbuf_region = vm_create_anonymous_region(vm_get_kernel_aspace_id(), "rtl8169_txbuf", (void **)&r->txbuf,
                                                 REGION_ADDR_ANY_ADDRESS, NUM_TX_DESCRIPTORS * BUFSIZE_PER_FRAME, REGION_WIRING_WIRED, LOCK_KERNEL|LOCK_RW);
#endif

    hal_pv_alloc( &r->rxdesc_phys, (void**)&r->rxdesc, NUM_RX_DESCRIPTORS * DESCRIPTOR_LEN );
    hal_pv_alloc( &r->txdesc_phys, (void**)&r->txdesc, NUM_TX_DESCRIPTORS * DESCRIPTOR_LEN );

    SHOW_INFO(2, "rx descriptors at %p, phys 0x%x\n", r->rxdesc, r->rxdesc_phys);
    SHOW_INFO(2, "tx descriptors at %p, phys 0x%x\n", r->txdesc, r->txdesc_phys);

    hal_pv_alloc( &r->rxbuf_phys, (void**)&r->rxbuf, NUM_RX_DESCRIPTORS * BUFSIZE_PER_FRAME );
    hal_pv_alloc( &r->txbuf_phys, (void**)&r->txbuf, NUM_TX_DESCRIPTORS * BUFSIZE_PER_FRAME );

    /* create a receive sem */
    hal_sem_init( &r->rx_sem, "rtl8169 rx_sem");

    /* transmit sem */
    hal_sem_init(  &r->tx_sem, "rtl8169 tx_sem");

    /* reset the chip */
    int repeats = 100;
    RTL_WRITE_8(r, REG_CR, (1<<4)); // reset the chip, disable tx/rx
    do {
        hal_sleep_msec(10); // 10ms
        if(repeats -- <= 0 )
            break;
    } while(RTL_READ_8(r, REG_CR) & (1<<4));

    /* read in the mac address */
    r->mac_addr[0] = RTL_READ_8(r, REG_IDR0);
    r->mac_addr[1] = RTL_READ_8(r, REG_IDR1);
    r->mac_addr[2] = RTL_READ_8(r, REG_IDR2);
    r->mac_addr[3] = RTL_READ_8(r, REG_IDR3);
    r->mac_addr[4] = RTL_READ_8(r, REG_IDR4);
    r->mac_addr[5] = RTL_READ_8(r, REG_IDR5);
    SHOW_INFO(2, "rtl8169: mac addr %x:%x:%x:%x:%x:%x\n",
              r->mac_addr[0], r->mac_addr[1], r->mac_addr[2],
              r->mac_addr[3], r->mac_addr[4], r->mac_addr[5]);

    /* some voodoo from BSD driver */
    RTL_WRITE_16(r, REG_CCR, RTL_READ_16(r, REG_CCR));
    RTL_SETBITS_16(r, REG_CCR, 0x3);

    /* mask all interrupts */
    RTL_WRITE_16(r, REG_IMR, 0);

    /* set up the tx/rx descriptors */
    rtl8169_setup_descriptors(r);

    /* enable tx/rx */
    RTL_SETBITS_8(r, REG_CR, (1<<3)|(1<<2));

    /* set up the rx state */
    /* 1024 byte dma threshold, 1024 dma max burst, CRC calc 8 byte+, accept all packets */
    RTL_WRITE_32(r, REG_RCR, (1<<16) | (6<<13) | (6<<8) | (0xf << 0));
    RTL_SETBITS_16(r, REG_CCR, (1<<5)); // rx checksum enable
    RTL_WRITE_16(r, REG_RMS, 1518); // rx mtu

    /* set up the tx state */
    RTL_WRITE_32(r, REG_TCR, (RTL_READ_32(r, REG_TCR) & ~0x1ff) | (6<<8)); // 1024 max burst dma
    RTL_WRITE_8(r, REG_MTPS, 0x3f); // max tx packet size (must be careful to not actually transmit more than mtu)

    /* set up the interrupt handler */
    //int_set_io_interrupt_handler(r->irq, &rtl8169_int, r, "rtl8169");
    if(hal_irq_alloc( r->irq, &rtl8169_int, r, HAL_IRQ_SHAREABLE ))
    {
        SHOW_ERROR( 0, "unable to allocate irq %d", r->irq );
        goto err1;
    }

    /* clear all pending interrupts */
    RTL_WRITE_16(r, REG_ISR, 0xffff);

    /* unmask interesting interrupts */
    RTL_WRITE_16(r, REG_IMR, IMR_SYSERR | IMR_LINKCHG | IMR_TER | IMR_TOK | IMR_RER | IMR_ROK | IMR_RXOVL);

    return 0;

err1:
    // TODO free what?
    //vm_delete_region(vm_get_kernel_aspace_id(), r->region);
//err:
    return err;
}
Exemplo n.º 5
0
phantom_device_t * driver_lanc111_probe( int port, int irq, int stage )
{
    (void) stage;



    lanc111_nic_t *nic = NULL;

    SHOW_INFO0( 0, "probe");
    nic = calloc( 1, sizeof(lanc111_nic_t) );

    assert(nic != NULL);



    hal_sleep_msec(10);

    if(LancInit(nic) < 0)
    {
        SHOW_ERROR0( 0, "init failed");
        goto free1;
    }

    // Disable NIC interrupt.
    //cbi(EIMSK, LANC111_SIGNAL_IRQ);



    phantom_device_t * dev = calloc(1, sizeof(phantom_device_t));
    dev->name = "lanc111";
    dev->seq_number = seq_number++;
    dev->drv_private = nic;

    //NutEtherInput,              /*!< \brief Routine to pass received data to, if_recv(). */
    //LancOutput,                 /*!< \brief Driver output routine, if_send(). */
    //NutEtherOutput              /*!< \brief Media output routine, if_output(). */

    //dev->dops.read = pcnet32_read;
    //dev->dops.write = pcnet32_write;
    //dev->dops.get_address = pcnet32_get_address;

    dev->iobase = port;
    dev->irq = irq;
    //dev->iomem = ;
    //dev->iomemsize = ;


    if( hal_irq_alloc( irq, &NicInterrupt, dev, HAL_IRQ_SHAREABLE ) )
    {
        SHOW_ERROR( 0, "IRQ %d is busy", irq );
        goto free2;
    }

    static CONST uint8_t mac[6] = { 0x52, 0x54, 0x00, 0x12, 0x34, 0x86 }; // QEMU's range

    if( NicStart(dev, mac) ) goto free2;

    /*
     * Start the receiver thread.
     *
     */
    //NutThreadCreate("rxi5", NicRxLanc, dev, (NUT_THREAD_LANCRXSTACK * NUT_THREAD_STACK_MULT) + NUT_THREAD_STACK_ADD);

    ifnet *interface;
    if( if_register_interface( IF_TYPE_ETHERNET, &interface, dev) )
    {
        SHOW_ERROR( 0, "Failed to register interface for %s", dev->name );
    }
    else
    {
        if_simple_setup(interface, WIRED_ADDRESS, WIRED_NETMASK, WIRED_BROADCAST, WIRED_NET, WIRED_ROUTER, DEF_ROUTE_ROUTER );
    }


    return dev;

free2:
    free( dev );
free1:
    free( nic );

    return 0;
}
phantom_device_t * driver_isa_mipsnet_probe( int port, int irq, int stage )
{
    (void) stage;
    SHOW_FLOW( 0, "Looking for MipsNet at 0x%x", port );

    if( mipsnet_probe(port) )
    {
        SHOW_ERROR( 1, "failed for port 0x%X", port );
        return 0;
    }


    phantom_device_t * dev = calloc(1, sizeof(phantom_device_t));
    assert(dev != 0);

    dev->name = "NE2000";
    dev->seq_number = seq_number++;

    dev->iobase = port;
    dev->irq = irq;
    dev->iomem = 0; // TODO map mem

    //dev->dops.stop = mipsnet_disable;
    dev->dops.read = mipsnet_read;
    dev->dops.write = mipsnet_write;
    dev->dops.get_address = mipsnet_get_address;

    dev->drv_private = calloc( 1, sizeof(struct mipsnet));
    assert( dev->drv_private != 0 );

    struct mipsnet *pvt = dev->drv_private;

    //hal_sem_init( &(pvt->reset_sem), "Ne2kReset" );

    hal_sem_init( &(pvt->recv_interrupt_sem), "mipsRecv" );
    hal_sem_init( &(pvt->send_interrupt_sem), "mipsSend" );

    mipsnet_reset(dev);

    if( hal_irq_alloc( irq, &mipsnet_interrupt, dev, HAL_IRQ_SHAREABLE ) )
    {
        SHOW_ERROR( 0, "IRQ %d is busy", irq );
        //goto free2;
    //free2:
        free(dev->drv_private);
        free(dev);
        return 0;
    }

    //pvt->thread = hal_start_kernel_thread_arg( mipsnet_thread, dev );

    //mipsnet_ei(dev);

    //pvt->active = 1;


    ifnet *interface;
    if( if_register_interface( IF_TYPE_ETHERNET, &interface, dev) )
    {
        SHOW_ERROR( 0, "Failed to register interface for %s", dev->name );
    }
    else
        if_simple_setup(interface, WIRED_ADDRESS, WIRED_NETMASK, WIRED_BROADCAST, WIRED_NET, WIRED_ROUTER, DEF_ROUTE_ROUTER );


    return dev;
}