--- /dev/null
+/*
+ * Acess2 PRO/100 Driver
+ * - By John Hodge (thePowersGang)
+ *
+ * main.c
+ * - Driver core
+ *
+ * Built with reference to the linux e100 driver (drivers/net/ethernet/intel/e100.c)
+ * 82559-fast-ethernet-multifunciton-pci-datasheet.pdf
+ */
+#include <acess.h>
+#include <IPStack/include/adapter_api.h>
+#include <modules.h>
+
+// === CONSTANTS ===
+const Uint16 caSupportedCards[][2] = {
+ {0x8086, 0x103D},
+ };
+const int ciNumSupportedCards = sizeof(caSupportedCards)/sizeof(caSupportedCards[0]);
+
+// === PROTOTYPES ===
+ int PRO100_Install(char **Arguments);
+ int PRO100_InitCard(tCard *Card);
+void PRO100_Cleanup(void);
+tIPStackBuffer *PRO100_WaitForPacket(void *Ptr);
+ int PRO100_SendPacket(void *Ptr, tIPStackBuffer *Buffer);
+void PRO100_IRQHandler(int Num, void *Ptr);
+
+size_t PRO100_int_ReadEEPROM(tCard *Card, size_t Ofs, size_t Len, void *Buffer);
+// === GLOBALS ===
+MODULE_DEFINE(0, PRO100, PRO100_Install, PRO100_Cleanup, "IPStack", NULL);
+tIPStack_AdapterType gPRO100_AdapterType = {
+ .Name = "PRO/100",
+ .Type = ADAPTERTYPE_ETHERNET_100M,
+ .Flags = 0,
+ .SendPacket = PRO100_SendPacket,
+ .WaitForPacket = PRO100_WaitForPacket
+
+};
+
+// === CODE ===
+int PRO100_Install(char **Arguments)
+{
+ return MODULE_ERR_OK;
+}
+
+int PRO100_InitCard(tCard *Card)
+{
+ // Card reset
+ Card->MMIO->Port = PORT_SELECTIVERESET;
+ // - Write Flush, wait 20us
+ Card->MMIO->Port = PORT_SOFTWARERESET;
+ // - Write Flush, wait 20us
+
+ // Read MAC address
+ Card->MAC.Words[0] = PRO100_int_ReadEEPROM(Card, 0);
+ Card->MAC.Words[1] = PRO100_int_ReadEEPROM(Card, 1);
+ Card->MAC.Words[2] = PRO100_int_ReadEEPROM(Card, 2);
+
+ return 0;
+}
+
+void PRO100_Cleanup(void)
+{
+ return 0;
+}
+
+tIPStackBuffer *PRO100_WaitForPacket(void *Ptr)
+{
+}
+
+int PRO100_SendPacket(void *Ptr, tIPStackBuffer *Buffer)
+{
+
+}
+
+void PRO100_IRQHandler(int Num, void *Ptr)
+{
+
+}
+
+Uint16 PRO100_int_ReadEEPROM(tCard *Card, size_t Ofs)
+{
+ Uint8 addr_len = 8;
+ Uint32 addr_data = ((EEPROM_OP_READ << addr_len) | Ofs) << 16;
+
+ Card->MMIO->EEPROMCtrl = EEPROM_CTRL_CS | EEPROM_CTRL_SK;
+ // Flush + 4us
+
+ for( int i = 32; i --; )
+ {
+ Uint8 ctrl = EEPROM_CTRL_CS | ((addr_data & (1 << i)) ? EEPROM_CTRL_DI : 0);
+ Card->MMIO->EEPROMCtrl = ctrl;
+ // Flush + 4us
+ Card->MMIO->EEPROMCtrl = ctrl | EEPROM_CTRL_SK;
+ // Flush + 4us
+
+ ctrl = Card->MMIO->EEPROMCtrl;
+ // Once the address is fully recieved, the card emits a zero bit
+ if( !(ctrl & EEPROM_CTRL_DO) && i > 16 )
+ {
+ addr_len = addr_len - (i - 16);
+ i = 17;
+ }
+
+ data = (data << 1) | (ctrl & EEPROM_CTRL_DO ? 1 : 0)
+ }
+
+ // Deslect chip
+ Card->MMIO->EEPROMCtrl = 0;
+ // Flush + 4us
+
+ return (data & 0xFFFF);
+}
--- /dev/null
+/*
+
+ */
+#ifndef _PRO100_H_
+#define _PRO100_H_
+
+struct sCSR
+{
+ Uint16 Status;
+ Uint16 Command;
+
+ Uint32 GenPtr;
+ Uint32 Port;
+
+ Uint16 FlashCtrl;
+ Uint16 EEPROMCtrl;
+
+ Uint32 MDICtrl;
+ Uint32 RXDMACount;
+};
+
+#define STATUS_RUS_MASK 0x003C // Receive Unit Status
+#define STATUS_CUS_MASK 0x00C0 // Comamnd Unit Status
+#define STATUS_FCP 0x0100 // Flow Control Pause
+#define STATUS_ER 0x0200 // Early Recieve
+#define STATUS_SWI 0x0400 // Software Interrupt
+#define STATUS_MDI 0x0800 // Management Data Interrupt
+#define STATUS_RNR 0x1000 // Receive Not Ready
+#define STATUS_CNA 0x2000 // Command Unit not active
+#define STATUS_FR 0x4000 // Frame Recieved
+#define STATUS_CX 0x8000 // Command Unit executed
+
+#define CMD_RUC 0x0007
+#define CMD_CUC 0x00F0
+#define CMD_M 0x0100 // Interrupt Mask
+#define CMD_SI 0x0200 // Software Interrupt
+
+#define MDI_IE (1 << 29)
+#define MDI_RDY (1 << 28)
+
+#define EEPROM_CTRL_SK 0x01 //
+#define EEPROM_CTRL_CS 0x02
+#define EEPROM_CTRL_DI 0x04
+#define EEPROM_CTRL_DO 0x08
+
+enum ePortCommands {
+ PORT_SOFTWARERESET = 0,
+ PORT_SELFTEST = 1,
+ PORT_SELECTIVERESET = 2,
+};
+
+struct sCommandBuffer
+{
+ Uint16 Status;
+ Uint16 Command;
+ Uint32 Link;
+
+ tIPStackBuffer *Buffer;
+ tCommandBuffer *Next;
+} __align__(4);
+
+#endif
+