This is the mail archive of the ecos-discuss@sourceware.org mailing list for the eCos project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Ever learning, setting individual bits


So my driver still isn't working. But there are two clues that I have and I'm working from that angle.

First, a person who has gotten VIA ethernet drivers to work in the past warned me about programming bits that VIA's data sheets said not to program. In particular he encouraged me to read the old value, just change the bits I want, and write the new value. In looking at the if_vr.c code in FreeBSD I see that the author of that code has done something similar. I coded up a few macros to do that on 8 and 16 bit registers (they are included below). They could be useful in the HAL layer if there isn't something like them already there.

Second, on closer inspection I've ascertained that my driver is never actually getting packets out on the wire. This makes me suspect that there is some setup between the PHY and the switch that haven't correctly negotiated their setup. Again in the if_vr.c code there is extensive MAC/PHY setup but in the old Rhine driver there was very little (the D-link card is pretty simple I guess).

I'd love to be compliant with the emerging drv_eth_phy architecture but there doesn't seem to be a parameter in the calls to phy_reg_read and phy_reg_write that would allow me to identify the base address of the MAC (which is the only way to talk to the phy, by telling the mac to send it messages). If I squirrel away a local copy then my driver won't work if there are multiple MAC/PHY pairs present. What to do?

--Chuck

------------BIT set/clear macros for I/O registers
/*
 * A bit of syntactic sugar around setting and resetting bits in
 * 8 and 16 bit IO registers. A number of registers have reserved
 * bits that are marked "do not program" which means don't ever
 * change them if you expect your driver to work. So these macros
 * automate the process of reading the old value, oring in or anding
 * out the bits that are set in the pattern 'bits' and then writing
 * the result back to the register.
 */
#define IO_BIT_SET_8(base, offset, bits)                   \
CYG_MACRO_START                                            \
        cyg_uint8       datum;                             \
        HAL_PCI_IO_READ_UINT8((base) + (offset), datum);   \
        datum |= (cyg_uint8)(bits);                        \
        HAL_PCI_IO_wRITE_UINT8((base) + (offset), datum);  \
CYG_MACRO_END

#define IO_BIT_CLR_8(base, offset, bits)                   \
CYG_MACRO_START                                            \
        cyg_uint8       datum;                             \
        HAL_PCI_IO_READ_UINT8((base) + (offset), datum);   \
        datum &= ~((cyg_uint8)(bits));                     \
        HAL_PCI_IO_wRITE_UINT8((base) + (offset), datum);  \
CYG_MACRO_END

#define IO_BIT_SET_16(base, offset, bits)                  \
CYG_MACRO_START                                            \
        cyg_uint16      datum;                             \
        HAL_PCI_IO_READ_UINT16((base) + (offset), datum);  \
        datum |= (cyg_uint16)(bits);                       \
        HAL_PCI_IO_wRITE_UINT16((base) + (offset), datum); \
CYG_MACRO_END

#define IO_BIT_CLR_16(base, offset, bits)                  \
CYG_MACRO_START                                            \
        cyg_uint16      datum;                             \
        HAL_PCI_IO_READ_UINT16((base) + (offset), datum);  \
        datum &= ~((cyg_uint16)(bits));                    \
        HAL_PCI_IO_wRITE_UINT16((base) + (offset), datum); \
CYG_MACRO_END


-- Before posting, please read the FAQ: http://ecos.sourceware.org/fom/ecos and search the list archive: http://ecos.sourceware.org/ml/ecos-discuss


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]