Subject: Re: com rumblings...
To: None <garrett_damore@tadpole.com>
From: Izumi Tsutsui <tsutsui@ceres.dti.ne.jp>
List: tech-kern
Date: 06/16/2006 21:25:40
Sorry for a bit late response, but I'd appreciate if I could have
more time for review before merge. Thanks,
garrett_damore@tadpole.com wrote:
> > - Why don't you put map[] member to struct com_softc?
> Because lots of com routines don't actually have/use the softc.
> Particularly stuff that might be used with console/kgdb support. This
> common structure lives in the softc, and can also live outside the softc
> for use in code that doesn't have the softc.
IMHO, it looks a bit inconsistent to have both functions,
ones take com_softc and the others do com_regs.
(of course current implementation which passes only iot, ioh
and iobase is also ugly though)
Actually you have changed such functions (which don't take com_softc)
into wrapper ones to prepare struct com_regs and create other real
functions which take struct com_regs.
Why don't you make them wrapper functions which prepare struct softc?
How about structures like this?
---
struct com_regs {
bus_space_tag_t cr_iot;
bus_space_handle_t cr_ioh;
bus_addr_t cr_iobase;
bus_size_t cr_nports;
bus_size_t cr_regmap[16];
};
struct com_softc {
struct device sc_dev;
void *sc_si;
struct tty *sc_tty;
struct callout sc_diag_callout;
int sc_frequency;
struct com_regs sc_regs;
#define sc_iot sc_regs.cr_iot
#define sc_ioh sc_regs.cr_ioh
#define sc_iobase sc_regs.cr_iobase
#define sc_nports sc_regs.cr_nports
#define sc_regmap sc_regs.cr_regmap
bus_space_handle_t sc_hayespioh;
:
---
:
#define CSR_WRITE_1(sc, o, v) \
bus_space_write_1((sc)->sc_iot, (sc)->sc_ioh, (sc)->sc_regmap[o], v)
#define CSR_READ_1(sc, o) \
bus_space_read_1((sc)->sc_iot, (sc)->cr_ioh, (sc)->cr_map[o])
:
int
cominit(struct com_softc *sc, int rate, int frequency, int type,
tcflag_t cflag)
{
if (bus_space_map(sc->sc_iot, sc->sc_iobase, sc->sc_nports, 0,
&sc->sc_ioh))
return (ENOMEM); /* ??? */
rate = comspeed(rate, frequency, type);
if (type != COM_TYPE_AU1x00) {
/* no EFR on alchemy */
CSR_WRITE_1(sc, COM_REG_LCR, LCR_EERS);
:
}
:
int
comcnattach1(struct com_softc *sc, int rate, int frequency, int type,
tcflag_t cflag)
{
int res;
comconsregs = sc->sc_reg;
res = cominit(sc, rate, frequency, type, cflag);
:
}
int
comcnattach(bus_space_tag_t iot, bus_addr_t iobase, int rate, int frequency,
int type, tcflag_t cflag)
{
struct com_softc sc_store;
struct com_softc *sc = &sc_store;
sc->sc_iot = iot;
sc->sc_iobase = iobase;
sc->sc_nports = COM_NPORTS;
#ifdef COM_REGMAP
memcpy(sc->sc_regmap, com_std_map, sizeof(sc->sc_regmap));
#endif
return comcnattach1(sc, rate, frequency, type, cflag);
}
---
In this implementation, you have to copy struct com_regs
from comconsregs to com_softc for com_common_{put,get}c().
If you don't like the copy, we could have some hacked
struct com_regs which can be passed as struct softc:
---
struct com_regs {
/* these members should be sync'ed with ones in struct com_softc */
struct device cr_dev; /* dummy */
bus_space_tag_t cr_iot;
bus_space_handle_t cr_ioh;
bus_addr_t cr_iobase;
bus_size_t cr_nports;
bus_size_t cr_regmap[16];
};
struct com_softc {
struct device sc_dev;
bus_space_tag_t sc_iot;
bus_space_handle_t sc_ioh;
bus_addr_t sc_iobase;
bus_size_t sc_nports;
bus_size_t sc_regmap[16];
bus_space_handle_t sc_hayespioh;
void *sc_si;
struct tty *sc_tty;
struct callout sc_diag_callout;
int sc_frequency;
:
---
I'm not sure if these implementations are good idea
(because I'm not a programmer but just a dumb reader),
but I think it could reduce changes from -current common style.
(note I don't test these changes at all though)
> > - Where is "COM_REGSMAP" defined in your code?
>
> In conf/files (or rather, opt_com.h)
>
> > Is it possible to define it only if a particular MD
> > attachment which requires special layout is configured?
>
> Yes. Stick it in MD config file (e.g. I have it in files.alchemy and
> files.atheros, but not in i386.)
Hmm. What happens if we have to support another com variant which
is attached to MI bus but also has odd regster mapping?
> > - Do all MD attachments have to initialize map[] array
> > if COM_REGSMAP is defined?
>
> No, there is a default "COM_INIT_REGS" that initializes this for
> standard 16550 layout.
Well, you are adding COM_INIT_REGS() macro in _all_ MD attachments.
That was my concern. Some people may complain about it if they have
their own private drivers, or if you miss some attachments on the merge.
I wonder if we can initialize the regmap array in com_attach_subr()
according to some proper quirk flag in softc:
---
if ((sc->sc_flags & COM_F_HAVE_OWN_REGMAP) == 0)
COM_INIT_REGMAP(sc->sc_regmap);
---
Then I guess we could use most current MD attachments without
extra changes.
---
Izumi Tsutsui