Miniport.c
上传用户:qiulin1960
上传日期:2013-10-16
资源大小:2844k
文件大小:39k
源码类别:

Windows CE

开发平台:

Windows_Unix

  1. /*++
  2. THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
  3. ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
  4. THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
  5. PARTICULAR PURPOSE.
  6. Copyright (c) 1995-1998  Microsoft Corporation
  7. Module Name:
  8.     miniport.c
  9. Abstract:
  10.     This is the main file for the CS8900 Ethernet controller.
  11.     This driver conforms to the NDIS 3.0 miniport interface.
  12. --*/
  13. #include "precomp.h"
  14. //
  15. // On debug builds tell the compiler to keep the symbols for
  16. // internal functions, otw throw them out.
  17. //
  18. #if DBG
  19. #define STATIC
  20. #else
  21. #define STATIC static
  22. #endif
  23. extern int resetCS(void);
  24. extern int initCS();
  25. //
  26. // Debugging definitions
  27. //
  28. #if DBG
  29. //
  30. // Default debug mode
  31. //
  32. ULONG Cs8900DebugFlag =
  33.        CS8900_DEBUG_LOUD
  34.        | CS8900_DEBUG_VERY_LOUD
  35.        // | CS8900_DEBUG_LOG
  36.        // | CS8900_DEBUG_CHECK_DUP_SENDS
  37.        // | CS8900_DEBUG_TRACK_PACKET_LENS
  38.        // | CS8900_DEBUG_WORKAROUND1
  39.        // | CS8900_DEBUG_CARD_BAD
  40.        // | CS8900_DEBUG_CARD_TESTS 
  41.        ;
  42. //
  43. // Debug tracing defintions
  44. //
  45. #define CS8900_LOG_SIZE 256
  46. UCHAR Cs8900LogBuffer[CS8900_LOG_SIZE]={0};
  47. UINT Cs8900LogLoc = 0;
  48. extern
  49. VOID
  50. Cs8900Log(UCHAR c) {
  51.     Cs8900LogBuffer[Cs8900LogLoc++] = c;
  52. Cs8900LogBuffer[(Cs8900LogLoc + 4) % CS8900_LOG_SIZE] = '';
  53. if (Cs8900LogLoc >= CS8900_LOG_SIZE)
  54. Cs8900LogLoc = 0;
  55. }
  56. #endif
  57. volatile unsigned char* ioPacketPage;
  58. volatile struct gpioreg *gpioRegs;
  59. volatile unsigned long *v_pBlank, *v_pPort2;
  60. volatile PLONG v_pGpioRegs, v_pIcRegs;
  61. //
  62. // This constant is used for places where NdisAllocateMemory
  63. // needs to be called and the HighestAcceptableAddress does
  64. // not matter.
  65. //
  66. NDIS_PHYSICAL_ADDRESS HighestAcceptableMax =
  67.     NDIS_PHYSICAL_ADDRESS_CONST(-1,-1);
  68. //
  69. // The global Miniport driver block.
  70. //
  71. DRIVER_BLOCK CS8900MiniportBlock={0};
  72. //
  73. // List of supported OID for this driver.
  74. //
  75. STATIC UINT CS8900SupportedOids[] = {
  76.     OID_GEN_SUPPORTED_LIST,
  77.     OID_GEN_HARDWARE_STATUS,
  78.     OID_GEN_MEDIA_SUPPORTED,
  79.     OID_GEN_MEDIA_IN_USE,
  80.     OID_GEN_MAXIMUM_LOOKAHEAD,
  81.     OID_GEN_MAXIMUM_FRAME_SIZE,
  82.     OID_GEN_MAXIMUM_TOTAL_SIZE,
  83.     OID_GEN_MAC_OPTIONS,
  84.     OID_GEN_PROTOCOL_OPTIONS,
  85.     OID_GEN_LINK_SPEED,
  86.     OID_GEN_TRANSMIT_BUFFER_SPACE,
  87.     OID_GEN_RECEIVE_BUFFER_SPACE,
  88.     OID_GEN_TRANSMIT_BLOCK_SIZE,
  89.     OID_GEN_RECEIVE_BLOCK_SIZE,
  90.     OID_GEN_VENDOR_DESCRIPTION,
  91.     OID_GEN_VENDOR_ID,
  92.     OID_GEN_DRIVER_VERSION,
  93.     OID_GEN_CURRENT_PACKET_FILTER,
  94.     OID_GEN_CURRENT_LOOKAHEAD,
  95.     OID_GEN_XMIT_OK,
  96.     OID_GEN_RCV_OK,
  97.     OID_GEN_XMIT_ERROR,
  98.     OID_GEN_RCV_ERROR,
  99.     OID_GEN_RCV_NO_BUFFER,
  100.     OID_802_3_PERMANENT_ADDRESS,
  101.     OID_802_3_CURRENT_ADDRESS,
  102.     OID_802_3_MULTICAST_LIST,
  103.     OID_802_3_MAXIMUM_LIST_SIZE,
  104.     OID_802_3_RCV_ERROR_ALIGNMENT,
  105.     OID_802_3_XMIT_ONE_COLLISION,
  106.     OID_802_3_XMIT_MORE_COLLISIONS,
  107.     
  108.     OID_GEN_MEDIA_CONNECT_STATUS,
  109.     OID_GEN_MAXIMUM_SEND_PACKETS,
  110.     OID_GEN_VENDOR_DRIVER_VERSION,
  111.     };
  112. //
  113. // Determines whether failing the initial card test will prevent
  114. // the adapter from being registered.
  115. //
  116. #ifdef CARD_TEST
  117. BOOLEAN InitialCardTest = TRUE;
  118. #else  // CARD_TEST
  119. BOOLEAN InitialCardTest = FALSE;
  120. #endif // CARD_TEST
  121. NTSTATUS
  122. DriverEntry(
  123.     IN PDRIVER_OBJECT DriverObject,
  124.     IN PUNICODE_STRING RegistryPath
  125.     );
  126. #pragma NDIS_INIT_FUNCTION(DriverEntry)
  127. NTSTATUS
  128. DriverEntry(
  129.     IN PDRIVER_OBJECT DriverObject,
  130.     IN PUNICODE_STRING RegistryPath
  131.     )
  132. /*++
  133. Routine Description:
  134.     This is the primary initialization routine for the CS8900 driver.
  135.     It is simply responsible for the intializing the wrapper and registering
  136.     the Miniport driver.  It then calls a system and architecture specific
  137.     routine that will initialize and register each adapter.
  138. Arguments:
  139.     DriverObject - Pointer to driver object created by the system.
  140.     RegistryPath - Path to the parameters for this driver in the registry.
  141. Return Value:
  142.     The status of the operation.
  143. --*/
  144. {
  145.     //
  146.     // Receives the status of the NdisMRegisterMiniport operation.
  147.     //
  148.     NDIS_STATUS Status;
  149.     //
  150.     // Characteristics table for this driver.
  151.     //
  152.     // NDIS_MINIPORT_CHARACTERISTICS CS8900Char;
  153. NDIS51_MINIPORT_CHARACTERISTICS CS8900Char;
  154.     //
  155.     // Pointer to the global information for this driver
  156.     //
  157.     PDRIVER_BLOCK NewDriver = &CS8900MiniportBlock;
  158.     //
  159.     // Handle for referring to the wrapper about this driver.
  160.     //
  161.     NDIS_HANDLE NdisWrapperHandle;
  162.     DEBUGMSG(0, (TEXT("+CS8900:DriverEntryrn")));
  163.     
  164.     RETAILMSG(0, (TEXT("+CS8900:DriverEntryrn")));
  165.     
  166.     //
  167.     // Initialize the wrapper.
  168.     //
  169.     NdisMInitializeWrapper(
  170. &NdisWrapperHandle,
  171. DriverObject,
  172. RegistryPath,
  173. NULL
  174. );
  175.     //
  176.     // Save the global information about this driver.
  177.     //
  178.     NewDriver->NdisWrapperHandle = NdisWrapperHandle;
  179.     NewDriver->AdapterQueue = (PCS8900_ADAPTER)NULL;
  180.     //
  181.     // Initialize the Miniport characteristics for the call to
  182.     // NdisMRegisterMiniport.
  183.     //
  184.     memset(&CS8900Char,0,sizeof(CS8900Char));
  185.     CS8900Char.MajorNdisVersion = CS8900_NDIS_MAJOR_VERSION;
  186.     CS8900Char.MinorNdisVersion = CS8900_NDIS_MINOR_VERSION;
  187.     CS8900Char.CheckForHangHandler = NULL;
  188.     //CS8900Char.DisableInterruptHandler = CS8900DisableInterrupt;
  189.     //CS8900Char.EnableInterruptHandler = CS8900EnableInterrupt;
  190. CS8900Char.DisableInterruptHandler = NULL;
  191.     CS8900Char.EnableInterruptHandler = NULL;
  192.     CS8900Char.HaltHandler = CS8900Halt;
  193.     CS8900Char.HandleInterruptHandler = CS8900HandleInterrupt;
  194.     CS8900Char.InitializeHandler = MiniportInitialize;
  195.     CS8900Char.ISRHandler = CS8900Isr;
  196.     CS8900Char.QueryInformationHandler = CS8900QueryInformation;
  197.     CS8900Char.ReconfigureHandler = NULL;
  198.     CS8900Char.ResetHandler = CS8900Reset;
  199.     CS8900Char.SendHandler = CS8900Send;
  200.     CS8900Char.SetInformationHandler = CS8900SetInformation;
  201.     CS8900Char.TransferDataHandler = CS8900TransferData;
  202. CS8900Char.ReturnPacketHandler     = NULL;
  203. CS8900Char.SendPacketsHandler      = NULL;
  204. CS8900Char.AllocateCompleteHandler = NULL;
  205. CS8900Char.CancelSendPacketsHandler = CS8900CancelSendPackets;
  206. CS8900Char.AdapterShutdownHandler = CS8900AdapterShutdown;
  207. CS8900Char.PnPEventNotifyHandler = CS8900DevicePnPEvent;
  208.     DEBUGMSG(0, (TEXT("CS8900: -> NdisMRegisterMiniportrn")));
  209.     Status = NdisMRegisterMiniport(
  210.  NdisWrapperHandle,
  211.  &CS8900Char,
  212.  sizeof(CS8900Char)
  213.  );
  214.     if (Status == NDIS_STATUS_SUCCESS)
  215.     {
  216. DEBUGMSG(0,
  217.  (TEXT("-CS8900:DriverEntry: Success!rn")));
  218. return STATUS_SUCCESS;
  219.     }
  220. // Terminate the wrapper.
  221. NdisTerminateWrapper (CS8900MiniportBlock.NdisWrapperHandle, NULL);
  222. CS8900MiniportBlock.NdisWrapperHandle = NULL;
  223.     DEBUGMSG(0, (TEXT("-CS8900:DriverEntry: Fail!rn")));
  224.     return STATUS_UNSUCCESSFUL;
  225. }
  226. #pragma NDIS_PAGEABLE_FUNCTION(MiniportInitialize)
  227. extern
  228. NDIS_STATUS
  229. MiniportInitialize(
  230.     OUT PNDIS_STATUS OpenErrorStatus,
  231.     OUT PUINT SelectedMediumIndex,
  232.     IN PNDIS_MEDIUM MediumArray,
  233.     IN UINT MediumArraySize,
  234.     IN NDIS_HANDLE MiniportAdapterHandle,
  235.     IN NDIS_HANDLE ConfigurationHandle
  236.     )
  237. /*++
  238. Routine Description:
  239.     CS8900Initialize starts an adapter and registers resources with the
  240.     wrapper.
  241. Arguments:
  242.     OpenErrorStatus - Extra status bytes for opening token ring adapters.
  243.     SelectedMediumIndex - Index of the media type chosen by the driver.
  244.     MediumArray - Array of media types for the driver to chose from.
  245.     MediumArraySize - Number of entries in the array.
  246.     MiniportAdapterHandle - Handle for passing to the wrapper when
  247.        referring to this adapter.
  248.     ConfigurationHandle - A handle to pass to NdisOpenConfiguration.
  249. Return Value:
  250.     NDIS_STATUS_SUCCESS
  251.     NDIS_STATUS_PENDING
  252. --*/
  253. {
  254.     //
  255.     // Pointer to our newly allocated adapter.
  256.     //
  257.     PCS8900_ADAPTER Adapter;
  258.     //
  259.     // The handle for reading from the registry.
  260.     //
  261.     NDIS_HANDLE ConfigHandle;
  262.     //
  263.     // The value read from the registry.
  264.     //
  265.     PNDIS_CONFIGURATION_PARAMETER ReturnedValue;
  266.     //
  267.     // String names of all the parameters that will be read.
  268.     //
  269.     NDIS_STRING IOAddressStr = IOADDRESS;
  270.     NDIS_STRING InterruptStr = INTERRUPT;
  271.     NDIS_STRING MaxMulticastListStr = MAX_MULTICAST_LIST;
  272.     NDIS_STRING NetworkAddressStr = NETWORK_ADDRESS;
  273.     NDIS_STRING BusTypeStr = NDIS_STRING_CONST("BusType");
  274.     NDIS_STRING CardTypeStr = NDIS_STRING_CONST("CardType");
  275.     //
  276.     // TRUE if there is a configuration error.
  277.     //
  278.     BOOLEAN ConfigError = FALSE;
  279.     //
  280.     // A special value to log concerning the error.
  281.     //
  282.     ULONG ConfigErrorValue = 0;
  283.     //
  284.     // The slot number the adapter is located in, used for
  285.     // Microchannel adapters.
  286.     //
  287.     UINT SlotNumber = 0;
  288.     //
  289.     // TRUE if it is unnecessary to read the Io Base Address
  290.     // and Interrupt from the registry.  Used for Microchannel
  291.     // adapters, which get this information from the slot
  292.     // information.
  293.     //
  294.     BOOLEAN SkipIobaseAndInterrupt = FALSE;
  295.     //
  296.     // The network address the adapter should use instead of the
  297.     // the default burned in address.
  298.     //
  299.     PVOID NetAddress;
  300.     //
  301.     // The number of bytes in the address.  It should be
  302.     // CS8900_LENGTH_OF_ADDRESS
  303.     //
  304.     ULONG Length;
  305.     //
  306.     // These are used when calling CS8900RegisterAdapter.
  307.     //
  308.     //
  309.     // The physical address of the base I/O port.
  310.     //
  311.     PVOID IoBaseAddr;
  312.     //
  313.     // The interrupt number to use.
  314.     //
  315.     CCHAR InterruptNumber;
  316.     //
  317.     // The number of multicast address to be supported.
  318.     //
  319.     UINT MaxMulticastList;
  320.     //
  321.     // Temporary looping variable.
  322.     //
  323.     ULONG i;
  324.     //
  325.     // Status of Ndis calls.
  326.     //
  327.     NDIS_STATUS Status;
  328. //    NDIS_MCA_POS_DATA McaData;
  329. DEBUGMSG(0, (TEXT("+CS8900:CS8900Initializern")));
  330.     //
  331.     // Search for the medium type (802.3) in the given array.
  332.     //
  333.     for (i = 0; i < MediumArraySize; i++)
  334.     {
  335. if (MediumArray[i] == NdisMedium802_3)
  336. {
  337.     break;
  338. }
  339.     }
  340.     if (i == MediumArraySize)
  341.     {
  342. DEBUGMSG(0, (TEXT("CS8900: No Supported Media!rn")));
  343. return( NDIS_STATUS_UNSUPPORTED_MEDIA );
  344.     }
  345.     *SelectedMediumIndex = i;
  346.     //
  347.     // Set default values.
  348.     //
  349.     IoBaseAddr = DEFAULT_IOBASEADDR;
  350.     InterruptNumber = DEFAULT_INTERRUPTNUMBER;
  351.     MaxMulticastList = DEFAULT_MULTICASTLISTMAX;
  352.     //
  353.     // Allocate memory for the adapter block now.
  354.     //
  355.     Status = NdisAllocateMemory( (PVOID *)&Adapter,
  356.    sizeof(CS8900_ADAPTER),
  357.    0,
  358.    HighestAcceptableMax
  359.    );
  360.     if (Status != NDIS_STATUS_SUCCESS)
  361.     {
  362. DEBUGMSG(0,
  363.      (TEXT("CS8900: NdisAllocateMemory(CS8900_ADAPTER) Fail!rn")));
  364. return Status;
  365.     }
  366.     //
  367.     // Clear out the adapter block, which sets all default values to FALSE,
  368.     // or NULL.
  369.     //
  370.     NdisZeroMemory (Adapter, sizeof(CS8900_ADAPTER));
  371.     //
  372.     // Open the configuration space.
  373.     //
  374.     NdisOpenConfiguration(
  375.     &Status,
  376.     &ConfigHandle,
  377.     ConfigurationHandle
  378.     );
  379.     if (Status != NDIS_STATUS_SUCCESS)
  380.     {
  381. NdisFreeMemory(Adapter, sizeof(CS8900_ADAPTER), 0);
  382. DEBUGMSG(0,
  383.      (TEXT("CS8900: NdisOpenconfiguration Fail! - 0x%xn"),
  384.      Status));
  385. return Status;
  386.     }
  387.     //
  388.     // Read in the card type.
  389.     //
  390.     NdisReadConfiguration(
  391.     &Status,
  392.     &ReturnedValue,
  393.     ConfigHandle,
  394.     &CardTypeStr,
  395.     NdisParameterHexInteger
  396.     );
  397.     
  398.     if (Status == NDIS_STATUS_SUCCESS)
  399. Adapter->CardType = (UINT)ReturnedValue->ParameterData.IntegerData;
  400. //
  401. // Read net address
  402. //
  403.     NdisReadNetworkAddress(
  404. &Status,
  405. &NetAddress,
  406. &Length,
  407. ConfigHandle
  408. );
  409.     if ((Length == CS8900_LENGTH_OF_ADDRESS) &&
  410. (Status == NDIS_STATUS_SUCCESS)) {
  411. //
  412. // Save the address that should be used.
  413. //
  414. NdisMoveMemory(
  415. Adapter->StationAddress,
  416. NetAddress,
  417. CS8900_LENGTH_OF_ADDRESS
  418. );
  419.     }
  420.     //
  421.     // Read Bus Type (for NE2/AE2 support)
  422.     //
  423.     NdisReadConfiguration(
  424.     &Status,
  425.     &ReturnedValue,
  426.     ConfigHandle,
  427. &BusTypeStr,
  428. NdisParameterHexInteger
  429. );
  430. if (Status == NDIS_STATUS_SUCCESS) {
  431. Adapter->BusType = (UCHAR)ReturnedValue->ParameterData.IntegerData;
  432. }
  433. if (!SkipIobaseAndInterrupt)
  434. {
  435. //
  436. // Read I/O Address
  437. //
  438. NdisReadConfiguration(
  439. &Status,
  440. &ReturnedValue,
  441. ConfigHandle,
  442. &IOAddressStr,
  443. NdisParameterHexInteger
  444. );
  445. if (Status == NDIS_STATUS_SUCCESS) {
  446.      IoBaseAddr = (PVOID)(ReturnedValue->ParameterData.IntegerData);
  447. }
  448. //
  449. // Read interrupt number
  450. //
  451. NdisReadConfiguration(
  452. &Status,
  453. &ReturnedValue,
  454. ConfigHandle,
  455. &InterruptStr,
  456. NdisParameterInteger
  457. );
  458. if (Status == NDIS_STATUS_SUCCESS) {
  459.      InterruptNumber = (CCHAR)(ReturnedValue->ParameterData.IntegerData);
  460. }
  461.     }
  462.     //
  463.     // Read MaxMulticastList
  464. //
  465.     NdisReadConfiguration(
  466. &Status,
  467.     &ReturnedValue,
  468.     ConfigHandle,
  469.     &MaxMulticastListStr,
  470.     NdisParameterInteger
  471.     );
  472.     if (Status == NDIS_STATUS_SUCCESS) {
  473. MaxMulticastList = ReturnedValue->ParameterData.IntegerData;
  474. if (ReturnedValue->ParameterData.IntegerData <= DEFAULT_MULTICASTLISTMAX)
  475. MaxMulticastList = ReturnedValue->ParameterData.IntegerData;
  476.     }
  477. // RegisterAdapter:
  478.     //
  479.     // Now to use this information and register with the wrapper
  480.     // and initialize the adapter.
  481.     //
  482.     //
  483.     // First close the configuration space.
  484.     //
  485.     NdisCloseConfiguration(ConfigHandle);
  486.     DEBUGMSG(0, (TEXT("CS8900:Card type: 0x%xrn"), Adapter->CardType));
  487.     DEBUGMSG(0, (TEXT("CS8900:I/O base addr 0x%lxrn"), IoBaseAddr));
  488.     DEBUGMSG(0, (TEXT("CS8900:interrupt number %ldrn"),
  489. InterruptNumber));
  490.     DEBUGMSG(0, (TEXT("CS8900:max multicast %ldrn"),
  491. DEFAULT_MULTICASTLISTMAX));
  492.     DEBUGMSG(0, (TEXT("CS8900:attribute memory address 0x%Xrn"),
  493. Adapter->AttributeMemoryAddress));
  494.     DEBUGMSG(0, (TEXT("CS8900:attribute memory size 0x%Xrn"),
  495. Adapter->AttributeMemorySize));
  496.     DEBUGMSG(0, (TEXT("CS8900:Bus type: %drn"), Adapter->BusType));
  497.     //
  498.     // Set up the parameters.
  499.     //
  500.     Adapter->IoBaseAddr = IoBaseAddr;
  501. Adapter->InterruptNumber = InterruptNumber;
  502.     Adapter->MulticastListMax = MaxMulticastList;
  503.     Adapter->MiniportAdapterHandle = MiniportAdapterHandle;
  504.     Adapter->MaxLookAhead = CS8900_MAX_LOOKAHEAD;
  505.     //
  506.     // Now do the work.
  507.     //
  508.     if (CS8900RegisterAdapter(Adapter,
  509. ConfigurationHandle,
  510. ConfigError,
  511. ConfigErrorValue
  512. ) != NDIS_STATUS_SUCCESS) {
  513. //
  514. // CS8900RegisterAdapter failed.
  515. //
  516. NdisFreeMemory(Adapter, sizeof(CS8900_ADAPTER), 0);
  517. return NDIS_STATUS_FAILURE;
  518. }
  519.     DEBUGMSG(0, (TEXT("-CS8900:CS8900Initialize Success!rn")));
  520.     return NDIS_STATUS_SUCCESS;
  521. }
  522. #pragma NDIS_PAGEABLE_FUNCTION(CS8900RegisterAdapter)
  523. NDIS_STATUS
  524. CS8900RegisterAdapter(
  525.     IN PCS8900_ADAPTER Adapter,
  526.     IN NDIS_HANDLE ConfigurationHandle,
  527.     IN BOOLEAN ConfigError,
  528.     IN ULONG ConfigErrorValue
  529.     )
  530. /*++
  531. Routine Description:
  532.     Called when a new adapter should be registered. It allocates space for
  533.     the adapter, initializes the adapter's block, registers resources
  534.     with the wrapper and initializes the physical adapter.
  535. Arguments:
  536.     Adapter - The adapter structure.
  537.     ConfigurationHandle - Handle passed to CS8900Initialize.
  538.     ConfigError - Was there an error during configuration reading.
  539.     ConfigErrorValue - Value to log if there is an error.
  540. Return Value:
  541.     Indicates the success or failure of the registration.
  542. --*/
  543. {
  544.     //
  545.     // Temporary looping variable.
  546.     //
  547.     unsigned char *m_pCS8900IoPort;
  548.     //
  549.     // General purpose return from NDIS calls
  550.     //
  551.     NDIS_STATUS status;
  552. DEBUGMSG(0, (TEXT("+CS8900:CS8900RegisterAdapterrn")));
  553.     //
  554.     // Check for a configuration error
  555.     //
  556.     if (ConfigError)
  557.     {
  558. //
  559. // Log Error and exit.
  560. //
  561. NdisWriteErrorLogEntry(
  562. Adapter->MiniportAdapterHandle,
  563. NDIS_ERROR_CODE_UNSUPPORTED_CONFIGURATION,
  564. 1,
  565. ConfigErrorValue
  566. );
  567. DEBUGMSG(0,
  568. (TEXT("CS8900:RegisterAdapter: CS8900Initialize had a config error %drn"),
  569. ConfigErrorValue));
  570. return(NDIS_STATUS_FAILURE);
  571. }
  572.     //
  573.     // Inform the wrapper of the physical attributes of this adapter.
  574.     //
  575. DEBUGMSG(0, (TEXT("CS8900: -> NdisMSetAttributesrn")));
  576.     NdisMSetAttributes(
  577. Adapter->MiniportAdapterHandle,
  578. (NDIS_HANDLE)Adapter,
  579. FALSE,
  580. Adapter->BusType
  581. );
  582. m_pCS8900IoPort = VirtualAlloc(0, 0x1000, MEM_RESERVE, PAGE_NOACCESS);
  583. DEBUGMSG(0,
  584. (TEXT("[CS8900] VirtualAlloc of m_pCS8900IoPort returns %xrn"), m_pCS8900IoPort));
  585. if (!VirtualCopy(m_pCS8900IoPort, (LPVOID)((IO_PACKET_PAGE_BASE_ADDR) & 0xFFFFF000),
  586. 0x1000, PAGE_READWRITE|PAGE_NOCACHE) )
  587. DEBUGMSG(0, (TEXT("[CS8900] m_pCS8900IoPort Virtual Copy failedrn")));
  588. else
  589. DEBUGMSG(0, (TEXT("[CS8900] m_pCS8900IoPort Virtual Copy OK!rn")));
  590. ioPacketPage = (volatile unsigned char *)(m_pCS8900IoPort + 
  591. (IO_PACKET_PAGE_BASE_ADDR - ((IO_PACKET_PAGE_BASE_ADDR) & 0xFFFFF000)) );
  592. Adapter->IoPAddr = (unsigned long)ioPacketPage;
  593. DEBUGMSG(0, (TEXT("[CS8900] m_pCS8900IoPort= %xrn"), Adapter->IoPAddr));
  594. /*    
  595.     //
  596.     // Register the port addresses.
  597.     //
  598. DEBUGMSG(0,
  599. (TEXT("CS8900: -> NdisMRegisterIoPortRangern")));
  600.     status = NdisMRegisterIoPortRange(
  601.  (PVOID *)(&(Adapter->IoPAddr)),
  602.  Adapter->MiniportAdapterHandle,
  603.  (ULONG)Adapter->IoBaseAddr,
  604.  0x20
  605.      );
  606.     if (status != NDIS_STATUS_SUCCESS)
  607.     {
  608. DEBUGMSG(0,
  609. (TEXT("CS8900:NdisMRegisterIoPortRange unsuccessful!rn")));
  610. return(status);
  611. }     
  612. */
  613.     if (Adapter->IoPAddr == 0)
  614.     {
  615. DEBUGMSG(0, (TEXT("CS8900:Invalid IoPAddr!rn")));
  616. return NDIS_STATUS_FAILURE;
  617.     }
  618.     //
  619.     // Initialize the card.
  620.     //
  621.     DEBUGMSG(0, (TEXT("+CS8900:CS8900Initializern")));
  622.     if (!CS8900Initialize(Adapter))
  623.     {
  624. DEBUGMSG(0, (TEXT("-CS8900:CS8900Initialize - Fail!rn")));
  625. NdisWriteErrorLogEntry(
  626.      Adapter->MiniportAdapterHandle,
  627.      NDIS_ERROR_CODE_ADAPTER_NOT_FOUND,
  628.      0
  629. );
  630. status = NDIS_STATUS_ADAPTER_NOT_FOUND;
  631. goto fail2;
  632.     }
  633.     DEBUGMSG(0, (TEXT("-CS8900:CS8900Initialize - Success!rn")));
  634.     //
  635.     // Read the Ethernet address off of the PROM.
  636.     //
  637.     if (!CS8900ReadEthernetAddress(Adapter))
  638.     {
  639. DEBUGMSG(0, (TEXT("CS8900:RegisterAdapter Could not read the ethernet addressn")));
  640. NdisWriteErrorLogEntry(
  641. Adapter->MiniportAdapterHandle,
  642.      NDIS_ERROR_CODE_ADAPTER_NOT_FOUND,
  643. 0
  644.      );
  645. status = NDIS_STATUS_ADAPTER_NOT_FOUND;
  646. goto fail2;
  647.     }
  648.     //
  649.     // Initialize the interrupt.
  650.     //
  651. #if 0
  652.     status = NdisMRegisterInterrupt(
  653.  &Adapter->Interrupt,
  654.  Adapter->MiniportAdapterHandle,
  655.  Adapter->InterruptNumber,
  656.  Adapter->InterruptNumber,
  657.  FALSE,
  658.  FALSE,
  659.  NdisInterruptLatched
  660.      );
  661. #else
  662.     status = NdisMRegisterInterrupt(
  663.  &Adapter->Interrupt,
  664.  Adapter->MiniportAdapterHandle,
  665.  Adapter->InterruptNumber,
  666.  Adapter->InterruptNumber,
  667.  TRUE,
  668.  FALSE,
  669.  NdisInterruptLatched
  670.      );
  671. #endif
  672.     if (status != NDIS_STATUS_SUCCESS)
  673.     {
  674. DEBUGMSG(0, (TEXT("CS8900:RegisterAdapter -> NdisMRegisterInterrupt failed 0x%xrn"), status));
  675. NdisWriteErrorLogEntry(
  676.      Adapter->MiniportAdapterHandle,
  677.      NDIS_ERROR_CODE_INTERRUPT_CONNECT,
  678.      0
  679. );
  680. goto fail3;
  681.     }
  682.     DEBUGMSG(0,
  683. (TEXT("CS8900:RegisterAdapter Interrupt Connectedrn")));
  684.     // register a shutdown handler for this card
  685. NdisMRegisterAdapterShutdownHandler(
  686. Adapter->MiniportAdapterHandle, // miniport handle.
  687. Adapter, // shutdown context.
  688. CS8900Shutdown // shutdown handler.
  689. );
  690.     
  691. /* Initialize The Interrupt */
  692. DEBUGMSG(0, (TEXT("CS8900RegisterAdapter:Initialize the Interrupt!rn")));
  693.     //
  694.     // Initialization completed successfully.
  695.     //
  696.     DEBUGMSG(0, (TEXT("CS8900:RegisterAdapter OKrn")));
  697.     return(NDIS_STATUS_SUCCESS);
  698.     //
  699.     // Code to unwind what has already been set up when a part of
  700.     // initialization fails, which is jumped into at various
  701.     // points based on where the failure occured. Jumping to
  702.     // a higher-numbered failure point will execute the code
  703.     // for that block and all lower-numbered ones.
  704.     //
  705. fail3:
  706.     //
  707.     // Take us out of the AdapterQueue.
  708.     //
  709.     if (CS8900MiniportBlock.AdapterQueue == Adapter)
  710.     {
  711. CS8900MiniportBlock.AdapterQueue = Adapter->NextAdapter;
  712.     }
  713.     else
  714.     {
  715. PCS8900_ADAPTER TmpAdapter = CS8900MiniportBlock.AdapterQueue;
  716. while (TmpAdapter->NextAdapter != Adapter)
  717. {
  718. TmpAdapter = TmpAdapter->NextAdapter;
  719. }
  720. TmpAdapter->NextAdapter = TmpAdapter->NextAdapter->NextAdapter;
  721.     }
  722. fail2:
  723.     NdisMDeregisterIoPortRange(
  724. Adapter->MiniportAdapterHandle,
  725. (ULONG)Adapter->IoBaseAddr,
  726. 0x20,
  727. (PVOID)Adapter->IoPAddr
  728.      );
  729.     return(status);
  730. }
  731. extern
  732. VOID
  733. CS8900Shutdown(
  734.     IN NDIS_HANDLE MiniportAdapterContext
  735.     )
  736. /*++
  737. Routine Description:
  738.     CS8900Shutdown is called to shut down the adapter. We need to unblock any
  739.     threads which may be called in, and terminate any loops.  This function is
  740.     called by the WinCE NDIS.DLL when a PCMCIA card removal is detected.  At that
  741.     point, any access to the CS8900 registers may return random data, as the bus
  742.     is floating.
  743. Arguments:
  744.     MiniportAdapterContext - The context value that the Miniport returned
  745. from CS8900Initialize; actually as pointer to an CS8900_ADAPTER.
  746. Return Value:
  747.     None.
  748. --*/
  749. {
  750.     PCS8900_ADAPTER Adapter;
  751.     Adapter = PCS8900_ADAPTER_FROM_CONTEXT_HANDLE(MiniportAdapterContext);
  752.     Adapter->ShuttingDown = TRUE;
  753. DEBUGMSG(0, (TEXT("+CS8900:CS8900Shutdown - Not Implemented!rn")));
  754. }
  755. extern
  756. VOID
  757. CS8900Halt(
  758.     IN NDIS_HANDLE MiniportAdapterContext
  759.     )
  760. /*++
  761. Routine Description:
  762.     CS8900Halt removes an adapter that was previously initialized.
  763. Arguments:
  764.     MiniportAdapterContext - The context value that the Miniport returned
  765. from CS8900Initialize; actually as pointer to an CS8900_ADAPTER.
  766. Return Value:
  767.     None.
  768. --*/
  769. {
  770.     PCS8900_ADAPTER Adapter;
  771.     Adapter = PCS8900_ADAPTER_FROM_CONTEXT_HANDLE(MiniportAdapterContext);
  772. DEBUGMSG(0, (TEXT("+CS8900:CS8900Haltrn")));
  773. // while(1);
  774.     return;
  775. }
  776. NDIS_STATUS
  777. CS8900Reset(
  778.     OUT PBOOLEAN AddressingReset,
  779.     IN NDIS_HANDLE MiniportAdapterContext
  780.     )
  781. /*++
  782. Routine Description:
  783.     The CS8900Reset request instructs the Miniport to issue a hardware reset
  784.     to the network adapter.  The driver also resets its software state.  See
  785.     the description of NdisMReset for a detailed description of this request.
  786. Arguments:
  787.     AddressingReset - Does the adapter need the addressing information reloaded.
  788.     MiniportAdapterContext - Pointer to the adapter structure.
  789. Return Value:
  790.     The function value is the status of the operation.
  791. --*/
  792. {
  793.     //
  794.     // Pointer to the adapter structure.
  795.     //
  796.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  797. DEBUGMSG(0, (TEXT("+CS8900:CS8900Resetrn")));
  798. RETAILMSG(1, (TEXT("----- !!!!!!!! reset !!!!!!!!!!! ------rn")));
  799. // while (1);
  800. resetCS();
  801. initCS();
  802. return NDIS_STATUS_SUCCESS;
  803. }
  804. NDIS_STATUS
  805. CS8900QueryInformation(
  806.     IN NDIS_HANDLE MiniportAdapterContext,
  807.     IN NDIS_OID Oid,
  808.     IN PVOID InformationBuffer,
  809.     IN ULONG InformationBufferLength,
  810.     OUT PULONG BytesWritten,
  811.     OUT PULONG BytesNeeded
  812. )
  813. /*++
  814. Routine Description:
  815.     The CS8900QueryInformation process a Query request for
  816.     NDIS_OIDs that are specific about the Driver.
  817. Arguments:
  818.     MiniportAdapterContext - a pointer to the adapter.
  819.     Oid - the NDIS_OID to process.
  820.     InformationBuffer -  a pointer into the
  821.     NdisRequest->InformationBuffer into which store the result of the query.
  822.     InformationBufferLength - a pointer to the number of bytes left in the
  823.     InformationBuffer.
  824.     BytesWritten - a pointer to the number of bytes written into the
  825.     InformationBuffer.
  826.     BytesNeeded - If there is not enough room in the information buffer
  827.     then this will contain the number of bytes needed to complete the
  828.     request.
  829. Return Value:
  830.     The function value is the status of the operation.
  831. --*/
  832. {
  833.     //
  834.     // Pointer to the adapter structure.
  835.     //
  836.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  837.     //
  838.     //  General Algorithm:
  839.     //
  840.     //     Switch(Request)
  841.     //        Get requested information
  842.     //        Store results in a common variable.
  843.     //     default:
  844.     //        Try protocol query information
  845.     //        If that fails, fail query.
  846.     //
  847.     //     Copy result in common variable to result buffer.
  848.     //  Finish processing
  849.     UINT BytesLeft = InformationBufferLength;
  850.     PUCHAR InfoBuffer = (PUCHAR)(InformationBuffer);
  851.     NDIS_STATUS StatusToReturn = NDIS_STATUS_SUCCESS;
  852.     NDIS_HARDWARE_STATUS HardwareStatus = NdisHardwareStatusReady;
  853.     NDIS_MEDIUM Medium = NdisMedium802_3;
  854.     //
  855.     // This variable holds result of query
  856.     //
  857.     ULONG GenericULong;
  858.     USHORT GenericUShort;
  859.     UCHAR GenericArray[6];
  860.     UINT MoveBytes = sizeof(ULONG);
  861.     PVOID MoveSource = (PVOID)(&GenericULong);
  862. DEBUGMSG(0, (TEXT("+CS8900:CS8900QueryInformationrn")));
  863.     //
  864.     // Make sure that int is 4 bytes.  Else GenericULong must change
  865.     // to something of size 4.
  866.     //
  867.     ASSERT(sizeof(ULONG) == 4);
  868.     //
  869.     // Switch on request type
  870.     //
  871.     switch (Oid) {
  872.     case OID_GEN_MAC_OPTIONS:
  873. GenericULong = (ULONG)(NDIS_MAC_OPTION_TRANSFERS_NOT_PEND  |
  874.        NDIS_MAC_OPTION_RECEIVE_SERIALIZED  |
  875.        NDIS_MAC_OPTION_COPY_LOOKAHEAD_DATA |
  876.        NDIS_MAC_OPTION_NO_LOOPBACK
  877.        );
  878.        
  879. DEBUGMSG(0, (TEXT("----> OID_GEN_MAC_OPTIONSrn")));
  880. break;
  881.     case OID_GEN_SUPPORTED_LIST:
  882. MoveSource = (PVOID)(CS8900SupportedOids);
  883. MoveBytes = sizeof(CS8900SupportedOids);
  884. DEBUGMSG(0, (TEXT("----> OID_GEN_SUPPORTED_LISTrn")));
  885. break;
  886.     case OID_GEN_HARDWARE_STATUS:
  887. HardwareStatus = NdisHardwareStatusReady;
  888. MoveSource = (PVOID)(&HardwareStatus);
  889. MoveBytes = sizeof(NDIS_HARDWARE_STATUS);
  890. DEBUGMSG(0, (TEXT("----> OID_GEN_HARDWARE_STATUSrn")));
  891. break;
  892.     case OID_GEN_MEDIA_SUPPORTED:
  893.     case OID_GEN_MEDIA_IN_USE:
  894. MoveSource = (PVOID) (&Medium);
  895. MoveBytes = sizeof(NDIS_MEDIUM);
  896. DEBUGMSG(0, (TEXT("----> OID_GEN_MEDIArn")));
  897. break;
  898.     case OID_GEN_MAXIMUM_LOOKAHEAD:
  899. GenericULong = CS8900_MAX_LOOKAHEAD;
  900. DEBUGMSG(0, (TEXT("----> OID_GEN_MAXIMUM_LOOKAHEADrn")));
  901. break;
  902.     case OID_GEN_MAXIMUM_FRAME_SIZE:
  903. GenericULong = (ULONG)(1518 - CS8900_HEADER_SIZE);
  904. DEBUGMSG(0, (TEXT("----> OID_GEN_MAXIMUM_FRAME_SIZErn")));
  905. break;
  906.     case OID_GEN_MAXIMUM_TOTAL_SIZE:
  907. GenericULong = (ULONG)(1518);
  908. DEBUGMSG(0, (TEXT("----> OID_GEN_TOTAL_SIZErn")));
  909. break;
  910.     case OID_GEN_LINK_SPEED:
  911. GenericULong = (ULONG)(100000);
  912. DEBUGMSG(0, (TEXT("----> OID_GEN_LINK_SPEEDrn")));
  913. break;
  914.     case OID_GEN_TRANSMIT_BUFFER_SPACE:
  915. GenericULong = (ULONG)(1518);
  916. DEBUGMSG(0, (TEXT("----> OID_GEN_TRANSMIT_BUFFER_SPACErn")));
  917. // while(1);
  918. break;
  919.     case OID_GEN_RECEIVE_BUFFER_SPACE:
  920. GenericULong = (ULONG)(1518);
  921. DEBUGMSG(0, (TEXT("----> OID_GEN_RECEIVE_BUFFER_SPACErn")));
  922. // while(1);
  923. break;
  924.     case OID_GEN_TRANSMIT_BLOCK_SIZE:
  925. GenericULong = (ULONG)(1518);
  926. DEBUGMSG(0, (TEXT("----> OID_GEN_TRANSMIT_BLOCK_SIZErn")));
  927. // while(1);
  928. break;
  929.     case OID_GEN_RECEIVE_BLOCK_SIZE:
  930. GenericULong = (ULONG)(1518);
  931. DEBUGMSG(0, (TEXT("----> OID_GEN_RECEIVE_BLOCK_SIZErn")));
  932. // while(1);
  933. break;
  934. #ifdef CS8900
  935.     case OID_GEN_VENDOR_ID:
  936. NdisMoveMemory(
  937.      (PVOID)&GenericULong,
  938.      Adapter->PermanentAddress,
  939.      3
  940.      );
  941. GenericULong &= 0xFFFFFF00;
  942. MoveSource = (PVOID)(&GenericULong);
  943. MoveBytes = sizeof(GenericULong);
  944. DEBUGMSG(0, (TEXT("----> OID_GEN_VENDER_IDrn")));
  945. break;
  946.     case OID_GEN_VENDOR_DESCRIPTION:
  947. MoveSource = (PVOID)"CS8900A Adapter";
  948. MoveBytes = 21;
  949. DEBUGMSG(0, (TEXT("----> OID_GEN_VENDOR_DESCRIPTIONrn")));
  950. break;
  951. #else
  952.     case OID_GEN_VENDOR_ID:
  953. NdisMoveMemory(
  954.      (PVOID)&GenericULong,
  955.      Adapter->PermanentAddress,
  956.      3
  957.      );
  958. GenericULong &= 0xFFFFFF00;
  959. GenericULong |= 0x01;
  960. MoveSource = (PVOID)(&GenericULong);
  961. MoveBytes = sizeof(GenericULong);
  962. break;
  963.     case OID_GEN_VENDOR_DESCRIPTION:
  964. MoveSource = (PVOID)"Novell 1000 Adapter.";
  965. MoveBytes = 21;
  966. break;
  967. #endif
  968.     case OID_GEN_DRIVER_VERSION:
  969. GenericUShort = ((USHORT)CS8900_NDIS_MAJOR_VERSION << 8) |
  970. CS8900_NDIS_MINOR_VERSION;
  971. MoveSource = (PVOID)(&GenericUShort);
  972. MoveBytes = sizeof(GenericUShort);
  973. break;
  974.     case OID_GEN_CURRENT_LOOKAHEAD:
  975. GenericULong = (ULONG)(Adapter->MaxLookAhead);
  976. DEBUGMSG(0, (TEXT("----> OID_GEN_CURRENT_LOOKAHEADrn")));
  977. break;
  978.     case OID_802_3_PERMANENT_ADDRESS:
  979. CS8900_MOVE_MEM((PCHAR)GenericArray,
  980.     Adapter->PermanentAddress,
  981.     CS8900_LENGTH_OF_ADDRESS);
  982. MoveSource = (PVOID)(GenericArray);
  983. MoveBytes = sizeof(Adapter->PermanentAddress);
  984. DEBUGMSG(0, (TEXT("----> OID_802_3_PERMANENT_ADDRESSrn")));
  985. break;
  986.     case OID_802_3_CURRENT_ADDRESS:
  987. CS8900_MOVE_MEM((PCHAR)GenericArray,
  988.     Adapter->StationAddress,
  989.     CS8900_LENGTH_OF_ADDRESS);
  990. MoveSource = (PVOID)(GenericArray);
  991. MoveBytes = sizeof(Adapter->StationAddress);
  992. DEBUGMSG(0, (TEXT("----> OID_802_3_CURRENT_ADDRESSrn")));
  993. break;
  994.     case OID_802_3_MAXIMUM_LIST_SIZE:
  995. GenericULong = (ULONG) (Adapter->MulticastListMax);
  996. DEBUGMSG(0, (TEXT("----> OID_802_3_MAXIMUM_LIST_SIZErn")));
  997. break;
  998.     case OID_GEN_XMIT_OK:
  999. GenericULong = (UINT)(Adapter->FramesXmitGood);
  1000. DEBUGMSG(0, (TEXT("----> OID_GEN_XMIT_OKrn")));
  1001. break;
  1002.     case OID_GEN_RCV_OK:
  1003. GenericULong = (UINT)(Adapter->FramesRcvGood);
  1004. DEBUGMSG(0, (TEXT("----> OID_GEN_RCV_OKrn")));
  1005. break;
  1006.     case OID_GEN_XMIT_ERROR:
  1007. GenericULong = (UINT)(Adapter->FramesXmitBad);
  1008. DEBUGMSG(0, (TEXT("----> OID_GEN_XMIT_ERRORrn")));
  1009. break;
  1010.     case OID_GEN_RCV_ERROR:
  1011. GenericULong = (UINT)(Adapter->CrcErrors);
  1012. DEBUGMSG(0, (TEXT("----> OID_GEN_RCV_ERRORrn")));
  1013. break;
  1014.     case OID_GEN_RCV_NO_BUFFER:
  1015. GenericULong = (UINT)(Adapter->MissedPackets);
  1016. DEBUGMSG(0, (TEXT("----> OID_GEN_RCV_NO_BUFFERrn")));
  1017. break;
  1018.     case OID_802_3_RCV_ERROR_ALIGNMENT:
  1019. GenericULong = (UINT)(Adapter->FrameAlignmentErrors);
  1020. DEBUGMSG(0, (TEXT("----> OID_802_3_RCV_ERROR_ALIGNMENTrn")));
  1021. break;
  1022.     case OID_802_3_XMIT_ONE_COLLISION:
  1023. GenericULong = (UINT)(Adapter->FramesXmitOneCollision);
  1024. DEBUGMSG(0, (TEXT("----> OID_802_3_XMIT_ONE_COLLISIONrn")));
  1025. break;
  1026.     case OID_802_3_XMIT_MORE_COLLISIONS:
  1027. GenericULong = (UINT)(Adapter->FramesXmitManyCollisions);
  1028. break;
  1029.     case OID_GEN_MEDIA_CONNECT_STATUS:
  1030. GenericULong = NdisMediaStateConnected;                 
  1031. break;
  1032.     case OID_GEN_MAXIMUM_SEND_PACKETS:
  1033.          GenericULong = 1;
  1034.          break;
  1035.     case OID_GEN_VENDOR_DRIVER_VERSION:
  1036. GenericULong = (DRIVER_MAJOR_VERSION << 16) | DRIVER_MINOR_VERSION;
  1037. break;
  1038.     default:
  1039. StatusToReturn = NDIS_STATUS_INVALID_OID;
  1040. break;
  1041.     }
  1042.     if (StatusToReturn == NDIS_STATUS_SUCCESS) {
  1043. if (MoveBytes > BytesLeft) {
  1044. //
  1045.      // Not enough room in InformationBuffer. Punt
  1046.      //
  1047.      *BytesNeeded = MoveBytes;
  1048.      StatusToReturn = NDIS_STATUS_INVALID_LENGTH;
  1049. } else {
  1050.      //
  1051.      // Store result.
  1052.      //
  1053.      CS8900_MOVE_MEM(InfoBuffer, MoveSource, MoveBytes);
  1054.      (*BytesWritten) += MoveBytes;
  1055. }
  1056.     }
  1057. DEBUGMSG(0, (TEXT("-CS8900:CS8900QueryInformationrn")));
  1058.     return StatusToReturn;
  1059. }
  1060. extern
  1061. NDIS_STATUS
  1062. CS8900SetInformation(
  1063.     IN NDIS_HANDLE MiniportAdapterContext,
  1064.     IN NDIS_OID Oid,
  1065.     IN PVOID InformationBuffer,
  1066.     IN ULONG InformationBufferLength,
  1067.     OUT PULONG BytesRead,
  1068.     OUT PULONG BytesNeeded
  1069.     )
  1070. /*++
  1071. Routine Description:
  1072.     CS8900SetInformation handles a set operation for a
  1073.     single OID.
  1074. Arguments:
  1075.     MiniportAdapterContext - Context registered with the wrapper, really
  1076. a pointer to the adapter.
  1077.     Oid - The OID of the set.
  1078.     InformationBuffer - Holds the data to be set.
  1079.     InformationBufferLength - The length of InformationBuffer.
  1080.     BytesRead - If the call is successful, returns the number
  1081. of bytes read from InformationBuffer.
  1082.     BytesNeeded - If there is not enough data in InformationBuffer
  1083. to satisfy the OID, returns the amount of storage needed.
  1084. Return Value:
  1085.     NDIS_STATUS_SUCCESS
  1086.     NDIS_STATUS_PENDING
  1087.     NDIS_STATUS_INVALID_LENGTH
  1088.     NDIS_STATUS_INVALID_OID
  1089. --*/
  1090. {
  1091.     //
  1092.     // Pointer to the adapter structure.
  1093.     //
  1094.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  1095.     //
  1096.     // General Algorithm:
  1097.     //
  1098.     //    Verify length
  1099.     //    Switch(Request)
  1100.     //       Process Request
  1101.     //
  1102.     UINT BytesLeft = InformationBufferLength;
  1103.     PUCHAR InfoBuffer = (PUCHAR)(InformationBuffer);
  1104.     //
  1105.     // Variables for a particular request
  1106.     //
  1107.     UINT OidLength;
  1108.     //
  1109.     // Variables for holding the new values to be used.
  1110.     //
  1111.     ULONG LookAhead;
  1112.     ULONG Filter;
  1113.     //
  1114.     // Status of the operation.
  1115.     //
  1116.     NDIS_STATUS StatusToReturn = NDIS_STATUS_SUCCESS;
  1117.     DEBUGMSG(0,
  1118. (TEXT("+CS8900:CS8900SetInformationrn")));
  1119.     //
  1120.     // Get Oid and Length of request
  1121.     //
  1122.     OidLength = BytesLeft;
  1123.     switch (Oid) {
  1124.     case OID_802_3_MULTICAST_LIST:
  1125. DEBUGMSG(0, (TEXT("OID_802_3_MULTICAST_LISTrn")));
  1126. //
  1127. // Verify length
  1128. //
  1129. if ((OidLength % CS8900_LENGTH_OF_ADDRESS) != 0)
  1130. {
  1131. StatusToReturn = NDIS_STATUS_INVALID_LENGTH;
  1132.      *BytesRead = 0;
  1133.      *BytesNeeded = 0;
  1134.     break;
  1135. }
  1136. //
  1137. // Set the new list on the adapter.
  1138. //
  1139. NdisMoveMemory(Adapter->Addresses, InfoBuffer, OidLength);
  1140. break;
  1141.     case OID_GEN_CURRENT_PACKET_FILTER:
  1142. DEBUGMSG(0, (TEXT("OID_GEN_CURRENT_PACKET_FILTERrn")));
  1143. //
  1144. // Verify length
  1145. //
  1146. if (OidLength != 4 ) {
  1147.      StatusToReturn = NDIS_STATUS_INVALID_LENGTH;
  1148.      *BytesRead = 0;
  1149.      *BytesNeeded = 0;
  1150. break;
  1151. }
  1152. CS8900_MOVE_MEM(&Filter, InfoBuffer, 4);
  1153. //
  1154. // Verify bits
  1155. //
  1156. if (Filter & (NDIS_PACKET_TYPE_SOURCE_ROUTING |
  1157.        NDIS_PACKET_TYPE_SMT |
  1158.        NDIS_PACKET_TYPE_MAC_FRAME |
  1159.        NDIS_PACKET_TYPE_FUNCTIONAL |
  1160.        NDIS_PACKET_TYPE_ALL_FUNCTIONAL |
  1161.        NDIS_PACKET_TYPE_GROUP
  1162.       )) {
  1163.      StatusToReturn = NDIS_STATUS_NOT_SUPPORTED;
  1164.      *BytesRead = 4;
  1165.      *BytesNeeded = 0;
  1166.      break;
  1167. }
  1168. break;
  1169.     case OID_GEN_CURRENT_LOOKAHEAD:
  1170. DEBUGMSG(0, (TEXT("OID_GEN_CURRENT_LOOKAHEADrn")));
  1171. //
  1172. // Verify length
  1173. //
  1174. if (OidLength != 4) {
  1175. StatusToReturn = NDIS_STATUS_INVALID_LENGTH;
  1176.      *BytesRead = 0;
  1177.      *BytesNeeded = 0;
  1178.      break;
  1179. }
  1180. //
  1181. // Store the new value.
  1182. //
  1183. CS8900_MOVE_MEM(&LookAhead, InfoBuffer, 4);
  1184. if (LookAhead <= CS8900_MAX_LOOKAHEAD) {
  1185. Adapter->MaxLookAhead = LookAhead;
  1186. } else {
  1187. StatusToReturn = NDIS_STATUS_INVALID_LENGTH;
  1188. }
  1189. break;
  1190.     default:
  1191. StatusToReturn = NDIS_STATUS_INVALID_OID;
  1192. *BytesRead = 0;
  1193. *BytesNeeded = 0;
  1194. break;
  1195.     }
  1196.     if (StatusToReturn == NDIS_STATUS_SUCCESS) {
  1197. *BytesRead = BytesLeft;
  1198. *BytesNeeded = 0;
  1199.     }
  1200.     DEBUGMSG(0, (TEXT("-CS8900:CS8900SetInformationrn")));
  1201.     return(StatusToReturn);
  1202. }
  1203. VOID
  1204. CS8900CancelSendPackets(
  1205.    IN NDIS_HANDLE MiniportAdapterContext,
  1206.    IN PVOID pvCancelId
  1207. )
  1208. /*++
  1209. Routine Description:
  1210.    The miniport entry point to handle cancellation of all send packets
  1211.    that match the given CancelId. If we have queued any packets that match
  1212.    this, then we should dequeue them and call NdisMSendComplete for all
  1213.    such packets, with a status of NDIS_STATUS_REQUEST_ABORTED.
  1214.    We should also call NdisCancelSendPackets in turn, on each lower binding
  1215.    that this adapter corresponds to. This is to let miniports below cancel
  1216.    any matching packets.
  1217. Arguments:
  1218.    hMiniportAdapterContext - pointer to the binding structure
  1219.    pvCancelId - ID of packets to be cancelled.
  1220. Return Value:
  1221.    None
  1222. --*/
  1223. {
  1224.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  1225.    //
  1226.    // If we queue packets on our adapter structure, this would be 
  1227.    // the place to acquire a spinlock to it, unlink any packets whose
  1228.    // Id matches CancelId, release the spinlock and call NdisMSendComplete
  1229.    // with NDIS_STATUS_REQUEST_ABORTED for all unlinked packets.
  1230.    //
  1231.    //
  1232.    // Next, pass this down so that we let the miniport(s) below cancel
  1233.    // any packets that they might have queued.
  1234.    //
  1235. //   NdisCancelSendPackets(Adapter->hPTBinding, pvCancelId);
  1236. //   DEBUGMSG(ETHDBG, (TEXT("CS8900CancelSendPacketsn")));
  1237.    return;
  1238. }
  1239. VOID
  1240. CS8900DevicePnPEvent(
  1241.    IN NDIS_HANDLE MiniportAdapterContext,
  1242.    IN NDIS_DEVICE_PNP_EVENT  devicePnPEvent,
  1243.    IN PVOID pvInformationBuffer,
  1244.    IN ULONG ulInformationBufferLength
  1245. )
  1246. /*++
  1247. Routine Description:
  1248.    This handler is called to notify us of PnP events directed to
  1249.    our miniport device object.
  1250. Arguments:
  1251.    hMiniportAdapterContext  - pointer to the binding structure
  1252.    devicePnPEvent - the event
  1253.    pvInformationBuffer - points to additional event-specific information
  1254.    ulInformationBufferLength - length of above
  1255. Return Value:
  1256.    None
  1257. --*/
  1258. {
  1259.    // TBD - add code/comments about processing this.
  1260.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  1261. //   DEBUGMSG(ETHDBG, (TEXT("MiniportDevicePnPEventn")));
  1262.    return ;
  1263. }
  1264. VOID
  1265. CS8900AdapterShutdown(
  1266.    IN NDIS_HANDLE MiniportAdapterContext
  1267. )
  1268. /*++
  1269. Routine Description:
  1270.    This handler is called to notify us of an impending system shutdown.
  1271. Arguments:
  1272.    MiniportAdapterContext  - pointer to the binding structure
  1273. Return Value:
  1274.    None
  1275. --*/
  1276. {
  1277.     PCS8900_ADAPTER Adapter = (PCS8900_ADAPTER)MiniportAdapterContext;
  1278. //   DEBUGMSG(ETHDBG, (TEXT("MiniportAdapterShutdown:rn")));
  1279.    return;
  1280. }