* Replaced the VIA Rhine driver in the network boot archive as well.

* Removed the old non-working VIA driver.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@22823 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler 2007-11-03 23:10:10 +00:00
parent 4e44040df4
commit f6d16d80f5
11 changed files with 2 additions and 1540 deletions

View File

@ -19,8 +19,8 @@ BEOS_NETWORK_DATALINK_PROTOCOLS = ethernet_frame <module>arp loopback_frame
ipv4_datagram ;
BEOS_NETWORK_PROTOCOLS = ipv4 tcp udp icmp ;
BEOS_ADD_ONS_DRIVERS_NET = etherpci ipro1000 rtl8139 rtl8169 sis900
via-rhine wb840 net_stack vlance
BEOS_ADD_ONS_DRIVERS_NET = 3com etherpci ipro1000 rtl8139 rtl8169 sis900
via_rhine wb840 net_stack vlance
$(GPL_ONLY)bcm440x $(GPL_ONLY)bcm570x
;
BEOS_ADD_ONS_BUS_MANAGERS = pci $(X86_ONLY)isa ide scsi

View File

@ -1,47 +1,4 @@
SubDir HAIKU_TOP src add-ons kernel drivers network via-rhine ;
SetSubDirSupportedPlatformsBeOSCompatible ;
# set some additional flags
SubDirCcFlags -Wall ;
# For ether_driver.h
UsePrivateHeaders net ;
KernelAddon via-rhine :
entry.c
hook.c
cmd.c
mdio.c
pci.c
res.c
ring.c
util.c
;
# Package haiku-via-rhine-cvs :
# via-rhine :
# boot home config add-ons kernel drivers bin ;
# Package haiku-via-rhine-cvs :
# <kernel!drivers!dev!net>via-rhine :
# boot home config add-ons kernel drivers dev net ;
Package haiku-networkingkit-cvs :
via-rhine :
boot home config add-ons kernel drivers bin ;
PackageDriverSymLink haiku-networkingkit-cvs : net via-rhine ;
# Installation
HaikuInstall install-networking : /boot/home/config/add-ons/kernel/drivers/bin :
via-rhine
;
HaikuInstallRelSymLink install-networking : /boot/home/config/add-ons/kernel/drivers/dev/net :
<installed>via-rhine :
installed-symlink
;
SubInclude HAIKU_TOP src add-ons kernel drivers network via-rhine dev ;
SubInclude HAIKU_TOP src add-ons kernel drivers network via-rhine pci ;

View File

@ -1,56 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
/*
* VIA Rhine Commands
*/
void cmd_reset(viarhine_private *device)
{
write16(device->addr + ChipCmd, CmdReset);
#ifdef __VIARHINE_DEBUG__
debug_printf("cmd_reset\n");
#endif
}
void cmd_getmacaddr(viarhine_private *device)
{
int i;
for (i = 0; i < 6; i++)
device->macaddr.ebyte[i] = read8(device->addr + StationAddr + i);
#ifdef __VIARHINE_DEBUG__
debug_printf("cmd_getmacaddr (%02x:%02x:%02x:%02x:%02x:%02x)\n",
(unsigned char)device->macaddr.ebyte[0],
(unsigned char)device->macaddr.ebyte[1],
(unsigned char)device->macaddr.ebyte[2],
(unsigned char)device->macaddr.ebyte[3],
(unsigned char)device->macaddr.ebyte[4],
(unsigned char)device->macaddr.ebyte[5]);
#endif
}

View File

@ -1,142 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
/*
* Standard Driver Entry Functions
*/
status_t init_driver (void);
void uninit_driver (void);
const char **publish_devices(void);
device_hooks *find_device (const char *name);
char *pDevNameList[MAX_CARDS+1];
pci_info *pDevList [MAX_CARDS+1];
pci_module_info *pModuleInfo;
const char **publish_devices(void)
{
#ifdef __VIARHINE_DEBUG__
debug_printf("publish_devices\n");
#endif
return (const char **)pDevNameList;
}
status_t init_hardware(void )
{
#ifdef __VIARHINE_DEBUG__
debug_printf("init_hardware\n");
#endif
return B_NO_ERROR;
}
status_t init_driver()
{
status_t status;
int32 entries;
char devName[64];
int32 i;
#ifdef __VIARHINE_DEBUG__
debug_printf("init_driver\n");
#endif
if ((status = get_module(B_PCI_MODULE_NAME, (module_info **)&pModuleInfo)) != B_OK)
{
#ifdef __VIARHINE_DEBUG__
debug_printf(DevName ": init_driver: get_module failed! (%s)\n", strerror(status));
#endif
return status;
}
// Find VIA Rhine Cards
if ((entries = pci_getlist(pDevList, MAX_CARDS)) == 0)
{
#ifdef __VIARHINE_DEBUG__
debug_printf(DevName ": init_driver: Device(s) Not Found\n");
#endif
pci_freelist(pDevList);
put_module (B_PCI_MODULE_NAME);
return B_ERROR;
}
// Create Device Name List
for (i = 0; i < entries; i++)
{
sprintf(devName, "%s%ld", DevDir, i );
pDevNameList[i] = (char*)malloc(strlen(devName) + 1);
strcpy(pDevNameList[i], devName);
}
pDevNameList[i] = NULL;
return B_OK;
}
void uninit_driver(void)
{
int32 i;
void *item;
#ifdef __VIARHINE_DEBUG__
debug_printf("uninit_driver\n");
#endif
// Free Device Name List
for (i = 0; (item = pDevNameList[i]); i++)
free(item);
// Free Device List
pci_freelist(pDevList);
put_module (B_PCI_MODULE_NAME);
}
device_hooks *find_device(const char *name)
{
int32 i;
char *item;
if (name == NULL)
return NULL;
// Find Device Name
for (i = 0; (item = pDevNameList[i]); i++)
{
if (strcmp(name, item) == 0)
{
#ifdef __VIARHINE_DEBUG__
debug_printf("find_device: Device Found (%s)\n", name);
#endif
return &pDeviceHooks;
}
}
#ifdef __VIARHINE_DEBUG__
debug_printf("find_device: Device (%s) Not Found\n", name);
#endif
return NULL;
}
int32 api_version = B_CUR_DRIVER_API_VERSION;

View File

@ -1,504 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
int32 nOpenMask = 0;
int32 hook_interrupt(void *_device)
{
viarhine_private *device = (viarhine_private*)_device;
int32 handled = B_UNHANDLED_INTERRUPT;
int16 worklimit = 20;
uint16 reg;
uint32 i, j;
int wakeup_reader = 0;
int wakeup_writer = 0;
do
{
reg = read16(device->addr + IntrStatus);
// Acknowledge All of the Current Interrupt Sources ASAP.
write16(device->addr + IntrStatus, reg & 0xffff);
if (reg == 0)
break;
if (reg & IntrRxDone)
{
wakeup_reader++;
//write16(device->addr + ChipCmd, CmdRxDemand | read16(device->addr + ChipCmd));
handled = B_HANDLED_INTERRUPT;
continue;
}
if (reg & IntrTxDone)
{
wakeup_writer++;
//write16(device->addr + ChipCmd, CmdTxDemand | read16(device->addr + ChipCmd));
handled = B_HANDLED_INTERRUPT;
continue;
}
if (reg & (IntrRxErr | IntrRxDropped | IntrRxWakeUp | IntrRxEmpty | IntrRxNoBuf))
{
write16(device->addr + ChipCmd, CmdRxDemand | read16(device->addr + ChipCmd));
handled = B_HANDLED_INTERRUPT;
continue;
}
if (reg & IntrTxAbort)
{
/* Just restart Tx. */
write16(device->addr + ChipCmd, CmdTxDemand | read16(device->addr + ChipCmd));
handled = B_HANDLED_INTERRUPT;
continue;
}
if (reg & IntrTxUnderrun)
{
if (device->tx_thresh < 0xE0)
write8(device->addr + TxConfig, device->tx_thresh += 0x20);
write16(device->addr + ChipCmd, CmdTxDemand | read16(device->addr + ChipCmd));
handled = B_HANDLED_INTERRUPT;
continue;
}
/* if (reg & IntrTxDone)
{
if (device->tx > 0)
device->tx--;
if (device->tx > 0)
write16(device->addr + ChipCmd, CmdTxDemand | read16(device->addr + ChipCmd));
}
*/
if (--worklimit < 0)
break;
} while (true);
if (wakeup_reader)
{
/* for (i = 0, j = 0; i < RX_BUFFERS; i++)
{
if (!(device->rx_desc[i].rx_status & DescOwn))
{
j++;
}
}
device->cur_rx = j;
*/
input_unwait(device, 1);
}
if (wakeup_writer)
{
output_unwait(device, 1);
}
return handled;
}
status_t hook_open(const char *name, uint32 flags, void **cookie)
{
char *devName;
int i;
int32 devID;
int32 mask;
area_id cookieID;
status_t status;
uint32 size;
viarhine_private *device;
(void)flags; /* get rid of compiler warning */
// Find Device Name
for (devID = 0; (devName = pDevNameList[devID]); devID++)
{
if (strcmp(name, devName) == 0)
break;
}
if (!devName)
return EINVAL;
// Check if the Device is Busy and Set in-use Flag if Not
mask = 1 << devID;
if (atomic_or(&nOpenMask, mask) & mask)
return B_BUSY;
// Allocate Storage for the Cookie
size = RNDUP(sizeof(viarhine_private), B_PAGE_SIZE);
cookieID = create_area( DevName " cookie",
cookie,
B_ANY_KERNEL_ADDRESS,
size,
B_FULL_LOCK,
B_READ_AREA | B_WRITE_AREA);
if (cookieID < 0)
{
status = B_NO_MEMORY;
goto Err0;
}
device = (viarhine_private*)(*cookie);
memset(device, 0, sizeof(viarhine_private));
// Setup the Cookie
device->cookieID = cookieID;
device->devID = devID;
device->pciInfo = pDevList[devID];
device->addr = device->pciInfo->u.h0.base_registers[0];
if ((status = res_allocate(device)) != B_OK)
goto Err1;
cmd_reset(device);
snooze(2000);
cmd_getmacaddr(device);
// Initialize MII Chip
if (cap_tbl[device->devID].flags & CanHaveMII)
{
int phy,
phy_idx = 0;
device->mii_phys[0] = 1; // Standard for this chip.
for (phy = 1; (phy < 32) && (phy_idx < 4); phy++)
{
int mii_status = mdio_read(device, phy, 1);
if ((mii_status != 0xffff) && (mii_status != 0x0000))
{
device->mii_phys[phy_idx++] = phy;
device->mii_advertising = mdio_read(device, phy, 4);
#ifdef __VIARHINE_DEBUG__
debug_printf("mii status=%lx, advertising=%lx\n", mii_status, device->mii_advertising);
#endif
}
}
device->mii_cnt = phy_idx;
}
// Allocate and Initialize Frame Buffer Rings & Descriptors
if (ring_init(device) != B_OK)
goto Err2;
for (i = 0; i < 6; i++)
write8(device->addr + StationAddr + i, device->macaddr.ebyte[i]);
write32(device->addr + TxRingPtr, mem_virt2phys(&device->tx_desc[0], sizeof(device->tx_desc[0])));
write32(device->addr + RxRingPtr, mem_virt2phys(&device->rx_desc[0], sizeof(device->rx_desc[0])));
// Initialize Other Registers.
write16(device->addr + PCIBusConfig, 0x0006);
// Configure the FIFO Thresholds.
device->tx_thresh = 0x20;
device->rx_thresh = 0x60; /* Written in device_rx_setmode(). */
write8(device->addr + TxConfig, 0x20);
rx_setmode(device);
// Setup Interrupt Handler
install_io_interrupt_handler(device->pciInfo->u.h0.interrupt_line, hook_interrupt, *cookie, 0);
// Enable interrupts by setting the interrupt mask.
write16(device->addr + IntrEnable,
IntrRxDone | IntrRxErr | IntrRxEmpty | IntrRxOverflow |
IntrTxDone | IntrTxAbort | IntrTxUnderrun | IntrRxDropped |
IntrPCIErr | IntrStatsMax | IntrLinkChange | IntrMIIChange);
device->cmd = CmdStart | CmdTxOn | CmdRxOn | /*CmdNoTxPoll |*/ CmdRxDemand;
if (device->duplex_lock)
device->cmd |= CmdFDuplex;
write16(device->addr + ChipCmd, device->cmd);
duplex_check(device);
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_open success!\n");
#endif
return B_NO_ERROR;
Err2:
ring_free(device);
Err1:
res_free(device);
delete_area(device->cookieID);
Err0:
atomic_and(&nOpenMask, ~mask);
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_open failed!\n");
#endif
return status;
}
status_t hook_close(void *_data)
{
viarhine_private *device = (viarhine_private*)_data;
device->interrupted = 1;
input_unwait(device, 1);
output_unwait(device, 1);
res_free(device);
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_close\n");
#endif
return B_NO_ERROR;
}
status_t hook_free(void *_data)
{
viarhine_private *device = (viarhine_private*)_data;
// Remove Interrupt Handler
remove_io_interrupt_handler(device->pciInfo->u.h0.interrupt_line, hook_interrupt, _data);
write16(device->addr + ChipCmd, CmdStop);
ring_free(device);
// Device is Now Available Again
atomic_and(&nOpenMask, ~(1 << device->devID));
delete_area(device->cookieID);
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_free\n");
#endif
return B_NO_ERROR;
}
status_t hook_ioctl(void *_data, uint32 msg, void *buf, size_t len)
{
viarhine_private *device = (viarhine_private*)_data;
(void)len; /* get rid of compiler warning */
switch (msg)
{
case ETHER_GETADDR:
if (_data == NULL)
return B_ERROR;
memcpy(buf, &device->macaddr, 6);
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: getaddr\n");
#endif
return B_NO_ERROR;
case ETHER_INIT:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: init\n");
#endif
return B_NO_ERROR;
case ETHER_GETFRAMESIZE:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: getframesize (%u)\n", MAX_FRAME_SIZE);
#endif
*(uint32*)buf = MAX_FRAME_SIZE;
return B_NO_ERROR;
case ETHER_SETPROMISC:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: setpromiscuous\n");
#endif
break;
case ETHER_NONBLOCK:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: nonblock\n");
#endif
if (device == NULL)
return B_ERROR;
memcpy(&device->nonblocking, buf, sizeof(device->nonblocking));
return B_NO_ERROR;
case ETHER_ADDMULTI:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: add multicast\n");
#endif
break;
default:
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_control: unknown msg %x\n", msg);
#endif
break;
}
return B_ERROR;
}
status_t hook_read(void *_data, off_t pos, void *buf, size_t *len)
{
viarhine_private *device = (viarhine_private*)_data;
ulong buflen;
unsigned int entry;
char *addr;
uint32 data_size;
uint32 desc_status;
(void)pos; /* get rid of compiler warning */
buflen = *len;
//write16(device->addr + ChipCmd, CmdRxDemand | read16(device->addr + ChipCmd));
input_wait(device);
if (device->interrupted)
{
*len = 0;
return B_INTERRUPTED;
}
if (device->nonblocking)
{
*len = 0;
return 0;
}
entry = device->cur_rx;
while (device->rx_desc[entry].rx_status & DescOwn)
{
entry++;
entry %= RX_BUFFERS;
}
desc_status = device->rx_desc[entry].rx_status;
data_size = (desc_status >> 16) - 4;
if (buflen < data_size)
{
data_size = buflen;
}
addr = &device->rx_buf[entry * BUFFER_SIZE];
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_read: received (%u)(%u) (%02x:%02x:%02x:%02x:%02x:%02x)\n",
data_size,
entry,
(unsigned char)addr[0],
(unsigned char)addr[1],
(unsigned char)addr[2],
(unsigned char)addr[3],
(unsigned char)addr[4],
(unsigned char)addr[5]);
#endif
*len = data_size;
memcpy(buf, addr, data_size);
device->rx_desc[entry].desc_length = MAX_FRAME_SIZE;
device->rx_desc[entry].rx_status = DescOwn;
entry++;
entry %= RX_BUFFERS;
device->cur_rx = entry;
return B_OK;
}
status_t hook_write(void *_data, off_t pos, const void *buf, size_t *len)
{
viarhine_private *device = (viarhine_private*)_data;
ulong buflen;
status_t status;
unsigned int entry;
void *addr;
(void)pos; /* get rid of compiler warning */
if (device->interrupted)
return B_INTERRUPTED;
status = output_wait(device, ETHER_TRANSMIT_TIMEOUT);
if (status != B_OK) {
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_write: leave (%s)\n", strerror(status));
#endif
return status;
}
entry = device->cur_tx;
while(device->tx_desc[entry].tx_status & DescOwn)
{
entry++;
entry %= RX_BUFFERS;
}
buflen = *len;
device->tx_desc[entry].tx_status = DescOwn;
addr = &device->tx_buf[entry * BUFFER_SIZE];
memcpy(addr, buf, buflen);
if (buflen < 60)
buflen = 60;
if (buflen & 3) {
buflen &= (~3);
buflen += 4;
}
device->tx_desc[entry].desc_length = 0x00E08000 | buflen;
entry++;
entry %= TX_BUFFERS;
device->cur_tx = entry;
//write16(device->addr + ChipCmd, CmdTxDemand | read16(device->addr + ChipCmd));
#ifdef __VIARHINE_DEBUG__
debug_printf("hook_write: sent (%u)(%u)\n", buflen, entry);
#endif
*len = buflen;
return B_OK;
}
device_hooks pDeviceHooks =
{
hook_open, // open entry point
hook_close, // close entry point
hook_free, // free entry point
hook_ioctl, // ioctl entry point
hook_read, // read entry point
hook_write, // write entry point
NULL, // select entry point
NULL, // deselect entry point
NULL, // readv entry point
NULL // writev entry point
};

View File

@ -1,65 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
int mdio_read(viarhine_private *device, int phy_id, int regnum)
{
int boguscnt = 1024;
/* Wait for a previous command to complete. */
while ((read8(device->addr + MIICmd) & 0x60) && --boguscnt > 0)
;
write8(device->addr + MIICmd, 0x00);
write8(device->addr + MIIPhyAddr, phy_id);
write8(device->addr + MIIRegAddr, regnum);
write8(device->addr + MIICmd, 0x40); /* Trigger Read */
boguscnt = 1024;
while ((read8(device->addr + MIICmd) & 0x40) && --boguscnt > 0)
;
return read16(device->addr + MIIData);
}
void mdio_write(viarhine_private *device, int phy_id, int regnum, int value)
{
int boguscnt = 1024;
if ((phy_id == device->mii_phys[0]) && (regnum == 4))
device->mii_advertising = value;
/* Wait for a previous command to complete. */
while ((read8(device->addr + MIICmd) & 0x60) && --boguscnt > 0)
;
write8(device->addr + MIICmd, 0x00);
write8(device->addr + MIIPhyAddr, phy_id);
write8(device->addr + MIIRegAddr, regnum);
write8(device->addr + MIIData, value);
write8(device->addr + MIICmd, 0x20); /* Trigger Write. */
}

View File

@ -1,144 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
/*
* PCI Information Table
*/
struct viarhine_pci_id_info pci_tbl[] =
{
{"VIA VT3042 Rhine", 0x1106, 0x3043, 0xffff, PCI_command_io | PCI_command_master, 128},
{"VIA VT6102 Rhine-II", 0x1106, 0x3065, 0xffff, PCI_command_io | PCI_command_master, 128},
{"VIA VT86C100A Rhine-II", 0x1106, 0x6100, 0xffff, PCI_command_io | PCI_command_master, 128},
// {"VIA VT6105M/LOM Rhine-III", 0x1106, 0x3106, 0xffff, PCI_command_io | PCI_command_master, 128},
// {"VIA VT6105M Rhine-III Management Adaptor", 0x1106, 0x3053, 0xffff, PCI_command_io | PCI_command_master, 128},
{0}
};
/*
* Chip Information Table
*/
struct viarhine_chip_info cap_tbl[] =
{
{128, CanHaveMII},
{128, CanHaveMII},
{128, CanHaveMII}
};
/*
* VIA Rhine PCI Functions
*/
int32 pci_getlist(pci_info *info[], int32 maxEntries)
{
status_t status;
int32 i, j;
int32 entries;
pci_info *item;
item = (pci_info*)malloc(sizeof(pci_info));
for (i = 0, entries = 0; entries < maxEntries; i++)
{
if ((status = pModuleInfo->get_nth_pci_info(i, item)) != B_OK)
break;
j = 0;
while (pci_tbl[j].name != NULL)
{
if ((pci_tbl[j].vendor_id == item->vendor_id) &&
(pci_tbl[j].device_id == item->device_id))
{
// Check if the Device Really has an IRQ
if ((item->u.h0.interrupt_line == 0) ||
(item->u.h0.interrupt_line == 0xFF))
{
#ifdef __VIARHINE_DEBUG__
debug_printf("pci_getlist: Found with Invalid IRQ - Check IRQ Assignement\n");
#endif
goto next_entry;
}
#ifdef __VIARHINE_DEBUG__
debug_printf("pci_getlist: Found at IRQ %u\n", item->u.h0.interrupt_line);
#endif
pModuleInfo->write_pci_config(
item->bus,
item->device,
item->function,
PCI_command,
2,
pci_tbl[j].flags | pModuleInfo->read_pci_config(
item->bus,
item->device,
item->function,
PCI_command,
2));
if (pci_tbl[j].flags & PCI_command_master)
{
if (item->latency < MIN_PCI_LATENCY)
{
#ifdef __VIARHINE_DEBUG__
debug_printf("pci_getlist: latency too slow\n");
#endif
pModuleInfo->write_pci_config(
item->bus,
item->device,
item->function,
PCI_latency,
1,
MIN_PCI_LATENCY);
}
}
info[entries++] = item;
item = (pci_info *)malloc(sizeof(pci_info));
goto next_entry;
}
j++;
}
next_entry:
; // gcc 4 doesn't like labels at the end of a compound statement
}
info[entries] = NULL;
free(item);
return entries;
}
status_t pci_freelist(pci_info *info[])
{
int32 i;
pci_info *item;
for (i = 0; (item = info[i]); i++)
free(item);
return B_OK;
}

View File

@ -1,51 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
status_t res_allocate(viarhine_private *device)
{
#ifdef __VIARHINE_DEBUG__
debug_printf("device_allocate_resources\n");
#endif
device->olock = create_sem(TX_BUFFERS, "via-rhine output");
set_sem_owner(device->olock, B_SYSTEM_TEAM);
device->ilock = create_sem(0, "via-rhine input");
set_sem_owner(device->ilock, B_SYSTEM_TEAM);
return B_OK;
}
void res_free(viarhine_private *device)
{
#ifdef __VIARHINE_DEBUG__
debug_printf("device_free_resources\n");
#endif
delete_sem(device->olock);
delete_sem(device->ilock);
}

View File

@ -1,92 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
status_t ring_init(viarhine_private *device)
{
uint32 size;
uint16 i;
// Create Transmit Buffer Area
size = RNDUP(BUFFER_SIZE * TX_BUFFERS, B_PAGE_SIZE);
if ((device->tx_buf_area = create_area( DevName " tx buffers",
(void **)&device->tx_buf,
B_ANY_KERNEL_ADDRESS,
size,
B_FULL_LOCK,
B_READ_AREA | B_WRITE_AREA)) < 0)
{
#ifdef __VIARHINE_DEBUG__
debug_printf(DevName ": Create TX Buffer Area Failed %x\n", device->tx_buf_area);
#endif
return device->tx_buf_area;
}
// Initialize TX Buffer Descriptors
for ( i = 0; i < TX_BUFFERS; i++)
{
device->tx_desc[i].tx_status = 0;
device->tx_desc[i].desc_length = 0;
device->tx_desc[i].addr = mem_virt2phys(&device->tx_buf[i * BUFFER_SIZE], BUFFER_SIZE);
device->tx_desc[i].next = mem_virt2phys(&device->tx_desc[i + 1], sizeof(device->tx_desc[0]));
}
device->tx_desc[i - 1].next = mem_virt2phys(&device->tx_desc[0], sizeof(device->tx_desc[0]));
// Create RX Buffer Area
size = RNDUP(BUFFER_SIZE * RX_BUFFERS, B_PAGE_SIZE);
if ((device->rx_buf_area = create_area( DevName " rx buffers",
(void **)&device->rx_buf,
B_ANY_KERNEL_ADDRESS,
size,
B_FULL_LOCK,
B_READ_AREA | B_WRITE_AREA)) < 0)
{
#ifdef __VIARHINE_DEBUG__
debug_printf(DevName ": Create RX Buffer Area Failed %x\n", device->rx_buf_area);
#endif
delete_area(device->tx_buf_area);
return device->rx_buf_area;
}
// Initialize RX Buffer Descriptors
for ( i = 0; i < RX_BUFFERS; i++)
{
device->rx_desc[i].rx_status = DescOwn;
device->rx_desc[i].desc_length = MAX_FRAME_SIZE;
device->rx_desc[i].addr = mem_virt2phys(&device->rx_buf[i * BUFFER_SIZE], BUFFER_SIZE);
device->rx_desc[i].next = mem_virt2phys(&device->rx_desc[i + 1], sizeof(device->rx_desc[0]));
}
device->rx_desc[i - 1].next = mem_virt2phys(&device->rx_desc[0], sizeof(device->tx_desc[0]));
return B_OK;
}
void ring_free(viarhine_private *device)
{
delete_area(device->tx_buf_area);
delete_area(device->rx_buf_area);
}

View File

@ -1,129 +0,0 @@
/*
* VIA VT86C100A Rhine-II and VIA VT3043 Rhine Based Card Driver
* for the BeOS Release 5
*/
/*
* Standard Libraries
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
/*
* Driver-Related Libraries
*/
#include <OS.h>
#include <KernelExport.h>
#include <Drivers.h>
#include <PCI.h>
#include <SupportDefs.h>
/*
* VIA Rhine Libraries
*/
#include "via-rhine.h"
uint32 mem_virt2phys(void *addr, unsigned int length)
{
physical_entry tbl;
get_memory_map(addr, length, &tbl, 1);
return (uint32)tbl.address;
}
void rx_setmode(viarhine_private *device)
{
uint8 rx_mode; // Note: 0x02 = Accept Runt, 0x01 = Accept Errors
#if defined(__VIARHINE_PROMISCUOUS___)
{
rx_mode = 0x1C;
}
#elif defined(__VIARHINE_ALLOW_MULTICAST__)
{
uint32 nMCFilter[2]; /* Multicast Hash Filter */
int i;
memset(nMCFilter, 0, sizeof(nMCFilter);
for (i = 0; i < device->nMulti; i++)
{
#error TODO: Code Multicast Filter
}
}
rx_mode = 0x0C;
#else
write32(device->addr + MulticastFilter0, 0);
write32(device->addr + MulticastFilter1, 0);
rx_mode = 0xA; // was 0x1A => PRO should not be set
#endif
write8(device->addr + RxConfig, device->rx_thresh | rx_mode);
}
void duplex_check(viarhine_private *device)
{
int mii_reg5;
int negotiated;
int duplex;
mii_reg5 = mdio_read(device, device->mii_phys[0], 5);
negotiated = mii_reg5 & device->mii_advertising;
if (device->duplex_lock || mii_reg5 == 0xffff)
return;
duplex = (negotiated & 0x0100) || (negotiated & 0x01C0) == 0x0040;
if (device->duplex_full != duplex)
{
device->duplex_full = duplex;
if (duplex)
device->cmd |= CmdFDuplex;
else
device->cmd &= ~CmdFDuplex;
write16(device->addr + ChipCmd, device->cmd);
}
}
bool is_mine(viarhine_private *device, char *addr)
{
static char broadcast[6] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
if (memcmp(&device->macaddr, addr, 6) == 0)
{
return true;
}
if (memcmp(broadcast, addr, 6) == 0)
{
return true;
}
return false;
}
#ifdef __VIARHINE_DEBUG__
int debug_printf(char *format, ...)
{
va_list vl;
char c[2048];
int i;
static int f = 0;
va_start(vl, format);
i = vsprintf(c, format, vl);
va_end(vl);
if (f == 0)
f = open("/boot/via-rhine.log", O_WRONLY | O_APPEND | O_TEXT);
write(f, c, strlen(c));
return i;
}
#endif

View File

@ -1,312 +0,0 @@
/*
* I/O Ctls: Belongs in a Public Header File
*/
enum
{
ETHER_GETADDR = B_DEVICE_OP_CODES_END, /* Get ethernet address */
ETHER_INIT, /* Set irq and port */
ETHER_NONBLOCK, /* Set/unset nonblocking mode */
ETHER_ADDMULTI, /* Add multicast addr */
ETHER_REMMULTI, /* Rem multicast addr */
ETHER_SETPROMISC, /* Set promiscuous */
ETHER_GETFRAMESIZE /* Get frame size */
};
/*
* Driver Informations
*/
#define DevName "via-rhine"
#define DevDir "net/" DevName "/"
#define DEVNAME_LENGTH 64
#define MAX_CARDS 4
#define TX_BUFFERS 8
#define RX_BUFFERS 16
#define BUFFER_SIZE 2048L /* Enough to hold a 1536 Frame */
#define MAX_FRAME_SIZE 1536 /* 1536 */
#define MAX_MULTI 32 /* Hardware Related, Do not change */
#define TRANSMIT_TIMEOUT ((bigtime_t)10000) /* 1/100 Second */
#define ETHER_TRANSMIT_TIMEOUT ((bigtime_t)1000000) /* One Second */
#define MIN_PCI_LATENCY 64
/*
* PCI Communications
*/
#define IO_PORT_PCI_ACCESS true
//#define MEMORY_MAPPED_PCI_ACCESS true
#if IO_PORT_PCI_ACCESS
#define write8(address, value) (*pModuleInfo->write_io_8)((address), (value))
#define write16(address, value) (*pModuleInfo->write_io_16)((address), (value))
#define write32(address, value) (*pModuleInfo->write_io_32)((address), (value))
#define read8(address) ((*pModuleInfo->read_io_8)(address))
#define read16(address) ((*pModuleInfo->read_io_16)(address))
#define read32(address) ((*pModuleInfo->read_io_32)(address))
#else /* MEMORY_MAPPED_PCI_ACCESS */
#define read8(address) (*((volatile uint8*)(address))); __eieio()
#define read16(address) (*((volatile uint16*)(address))); __eieio()
#define read32(address) (*((volatile uint32*)(address))); __eieio()
#define write8(address, data) (*((volatile uint8 *)(address)) = data); __eieio()
#define write16(address, data) (*((volatile uint16 *)(address)) = (data)); __eieio()
#define write32(address, data) (*((volatile uint32 *)(address)) = (data)); __eieio()
#endif
/*
* Registers Offsets
*/
enum viarhine_register_offsets
{
StationAddr = 0x00,
RxConfig = 0x06,
TxConfig = 0x07,
ChipCmd = 0x08,
IntrStatus = 0x0C,
IntrEnable = 0x0E,
MulticastFilter0 = 0x10,
MulticastFilter1 = 0x14,
RxRingPtr = 0x18,
TxRingPtr = 0x1C,
MIIPhyAddr = 0x6C,
MIIStatus = 0x6D,
PCIBusConfig = 0x6E,
MIICmd = 0x70,
MIIRegAddr = 0x71,
MIIData = 0x72,
Config = 0x78,
RxMissed = 0x7C,
RxCRCErrs = 0x7E,
};
/*
* Command Bits
*/
enum viarhine_chip_cmd_bits
{
CmdInit = 0x0001,
CmdStart = 0x0002,
CmdStop = 0x0004,
CmdRxOn = 0x0008,
CmdTxOn = 0x0010,
CmdTxDemand = 0x0020,
CmdRxDemand = 0x0040,
CmdEarlyRx = 0x0100,
CmdEarlyTx = 0x0200,
CmdFDuplex = 0x0400,
CmdNoTxPoll = 0x0800,
CmdReset = 0x8000
};
/*
* Interrupt Status Bits
*/
enum viarhine_intr_status_bits
{
IntrRxDone = 0x0001,
IntrRxErr = 0x0004,
IntrRxEmpty = 0x0020,
IntrTxDone = 0x0002,
IntrTxAbort = 0x0008,
IntrTxUnderrun = 0x0010,
IntrPCIErr = 0x0040,
IntrStatsMax = 0x0080,
IntrRxEarly = 0x0100,
IntrMIIChange = 0x0200,
IntrRxOverflow = 0x0400,
IntrRxDropped = 0x0800,
IntrRxNoBuf = 0x1000,
IntrTxAborted = 0x2000,
IntrLinkChange = 0x4000,
IntrRxWakeUp = 0x8000,
IntrNormalSummary = 0x0003,
IntrAbnormalSummary = 0xC260,
};
/*
* RX Status Bits
*/
enum viarhine_rx_status_bits
{
RxOK = 0x8000,
RxWholePkt = 0x0300,
RxErr = 0x008F
};
/*
* Desc Status Bits
*/
enum viarhine_desc_status_bits
{
DescOwn = 0x80000000,
DescEndPacket = 0x4000,
DescIntr = 0x1000
};
/*
* PCI ID Information
*/
struct viarhine_pci_id_info
{
const char *name;
uint16 vendor_id,
device_id,
device_id_mask,
flags;
int io_size;
};
/*
* Chip Compatibility
*/
enum viarhine_chip_capability_flags
{
CanHaveMII = 1
};
/*
* Chip Information
*/
struct viarhine_chip_info
{
int io_size;
int flags;
};
/*
* RX Descriptor
*/
typedef struct
{
uint32 rx_status;
uint32 desc_length;
uint32 addr;
uint32 next;
} viarhine_rx_desc;
/*
* TX Descriptor
*/
typedef struct
{
uint32 tx_status;
uint32 desc_length;
uint32 addr;
uint32 next;
} viarhine_tx_desc;
typedef struct
{
unsigned char ebyte[6];
} ethernet_addr;
/*
* Private Data
*/
typedef struct
{
/*
* Rings
*/
viarhine_tx_desc tx_desc[TX_BUFFERS]; /* TX Frame Descriptor */
viarhine_rx_desc rx_desc[RX_BUFFERS]; /* RX Frame Descriptor */
area_id tx_buf_area; /* Transmit Descriptor and Buffer Areas */
area_id rx_buf_area; /* Receive Descriptor and Buffer Areas */
uchar *tx_buf; /* TX Buffer */
uchar *rx_buf; /* RX Buffer */
area_id cookieID; /* Cookie Area ID */
int32 devID; /* Device ID */
uint32 addr; /* Base Address of HostRegs */
pci_info *pciInfo; /* PCI Informations */
ethernet_addr macaddr; /* Ethernet Address */
uint8 tx_thresh;
uint8 rx_thresh;
uint16 cmd;
uint8 interrupted;
unsigned char duplex_full; /* Full-Duplex Operation Requested. */
unsigned char duplex_lock;
uint8 cur_rx;
uint8 cur_tx;
int nonblocking;
/*
* Semaphores
*/
sem_id ilock;
sem_id olock;
/*
* MII Transceiver Section
*/
int mii_cnt; /* MII Device Addresses. */
uint16 mii_advertising; /* NWay Media Advertisement */
unsigned char mii_phys[8]; /* MII Device Addresses. */
} viarhine_private;
/*
* Semaphores Macros
*/
/* output_wait wakes up when the card is ready to transmit another packet */
#define output_wait(data, t) acquire_sem_etc(data->olock, 1, B_TIMEOUT, t)
#define output_unwait(data, c) release_sem_etc(data->olock, c, B_DO_NOT_RESCHEDULE)
/* input_wait wakes up when the card has at least one packet on it */
#define input_wait(data) acquire_sem_etc(data->ilock ,1, B_CAN_INTERRUPT, 0)
#define input_unwait(data, c) release_sem_etc(data->ilock, c, B_DO_NOT_RESCHEDULE)
/*
* Variables
*/
extern char *pDevNameList[MAX_CARDS+1];
extern pci_info *pDevList [MAX_CARDS+1];
extern pci_module_info *pModuleInfo;
extern device_hooks pDeviceHooks;
extern int32 nOpenMask;
extern struct viarhine_pci_id_info pci_tbl[];
extern struct viarhine_chip_info cap_tbl[];
/*
* Functions
*/
// pci.c
int32 pci_getlist (pci_info *info[], int32 maxEntries);
status_t pci_freelist(pci_info *info[]);
// res.c
status_t res_allocate(viarhine_private *device);
void res_free (viarhine_private *device);
// misc.c
uint32 mem_virt2phys(void *addr, unsigned int length);
void rx_setmode (viarhine_private *device);
void duplex_check (viarhine_private *device);
bool is_mine (viarhine_private *device, char *addr);
// ring.c
status_t ring_init(viarhine_private *device);
void ring_free(viarhine_private *device);
// cmd.c
void cmd_reset (viarhine_private *device);
void cmd_getmacaddr(viarhine_private *device);
/*
* Macro
*/
#define RNDUP(x, y) (((x) + (y) - 1) & ~((y) - 1))
//#define __VIARHINE_DEBUG__
#ifdef __VIARHINE_DEBUG__
int debug_printf(char *format, ...);
#endif