REXX CB81

Mikk Lippmaa mlippmaa@oxide.rlem.titech.ac.jp
Fri Apr 30 03:19:06 1999


I have a Ratoc Systems REX-CB81 CardBus 100Base-Tx/10Base-T card
which I am trying to get working under the 2.2.5 kernel in a Sony VAIO 505RS.
The card has a 21143-TD chip,
a serial EEPROM (8 bit address length), and a TDK PHY chip (TSC78Q2120).
I did get the card working, (at least on a 10BaseT link), but
the driver (0.90z) needed some modifications. I have a couple of
questions:

1. In parse_eeprom, at the end of the media leaf data parsing there
   is a diagnostic line:

      printk(KERN_INFO "%s:  MII interface PHY %d, setup/reset "
            "sequences %d/%d long, capabilities %2.2x %2.2x.\n",
            dev->name, bp[0], bp[1], bp[1 + bp[1]*2],
            bp[5 + bp[2 + bp[1]*2]*2], bp[4 + bp[2 + bp[1]*2]*2]);

  Shouldn't this be:

      printk(KERN_INFO "%s:  MII interface PHY %d, setup/reset "
            "sequences %d/%d long, capabilities %2.2x %2.2x.\n",
            dev->name, bp[0], bp[1], bp[2 + bp[1]*2],
            bp[4 + bp[2 + bp[1]*2]*2], bp[3 + bp[2 + bp[1]*2]*2]);

  as the relevant type 3 block in the EEPROM (at least in this card is):

      00   (PHY number)  <--- bp points here
      00   (GPR sequence length)
      03   (Reset sequence length)
      0708 (Reset sequence)
      0000       "
      0200       "
      0078 (Media capabilities)
      e001 (Nway advertisment)
      
2. This block (the reset sequence) also shows another more serious problem.
   The gep pins are programmed so that gep0, gep1, and gep2 are outputs and
   gep3 is an input. The reset sequence ends by driving gep1 high and gep0
   low. Apparently, in this card the gep0 and gep1 are used to power down
   the PHY and to reset the PHY, respectively (why, I wonder). At the moment
   the tulip driver starts to look for MII xcvrs before sending the reset sequence.
   In my case this means that the PHY is either powered down or in continuous
   reset state, and never responds.

   Sending the reset sequence by adding the lines

    outl(0x08070000, ioaddr + CSR15);
    outl(0x00000000, ioaddr + CSR15);
    outl(0x00020000, ioaddr + CSR15);

   before the MII detection loop will solve the problem. The MII is found.
   The proper(?) way would, of course, be to send the sequence from the EEPROM,
   as is done when the card is finally reset in tulip_open. 
   The sequene should also remember what the gep bits are at the end of the 
   reset sequence, i.e. something like this:

        for (i = 0; i < reset_length; i++)
            outl(get_u16(&reset_sequence[i]) << 16, ioaddr + CSR15);
   tp->gepibits = (get_u16(&reset_sequence[reset_length-1]) << 16) & 0x000f0000;

   Later, whenever CSR15 is programmed, the code could look like this

   outl(((whatever) & 0xfff0ffff) | tp->gepbits, ioaddr + CSR15);


   At the moment, problems occur in tulip_open. The chip reset in the beginning
   will reset the gep bits and the MII gets killed. I had to add the above
   sequence of outls to CSR15 just after the call to tulip_init_ring.

   outls had to be modified to include the gep bit states also later in
   tulip open where CSR13, 14, and 15 get reprogrammed. 

   After these modifications the card senses a 10BaseT link and appears to
   work correctly. However, the driver has several places where CSR15 is
   potentially clobbered. I haven't tried to force link negotiation, for example.


   So, the question really is: can the gep bit state memory be added to the driver
   or will this break something else? Is it possible to put in if()s for a
   specific card, or am I destined to patch the driver whenever I want to
   upgrade?

Mikk Lippmaa (mlippmaa@oxide.rlem.titech.ac.jp)