NetBSD/sys/arch/acorn26/iobus/iobus.c
bjh21 e9030bd381 Move over to using the standard ARM bus_space implementation on acorn26.
This is more flexible than the old acorn26 bus_space, which means that single
read/write operations are slower, but multi and region operations have the
potential to be faster, and particularly insane podules might be supportable.
In theory the acorn32 mainbus and podulebus code ought to be shareable, but
acorn26 needs the extra overhead of saving R14_svc on some operations so
I've made my own version for now.  Also the acorn32 bus_spaces are a mess.
2006-09-30 16:30:10 +00:00

129 lines
3.9 KiB
C

/* $NetBSD: iobus.c,v 1.14 2006/09/30 16:30:10 bjh21 Exp $ */
/*-
* Copyright (c) 1998 Ben Harris
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/*
* iobus.c - when the IORQ* calls...
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: iobus.c,v 1.14 2006/09/30 16:30:10 bjh21 Exp $");
#include <sys/param.h>
#include <sys/device.h>
#include <sys/systm.h>
#include <machine/bus.h>
#include <machine/memcreg.h>
#include <arch/acorn26/iobus/iobusvar.h>
#include "locators.h"
static int iobus_match(struct device *parent, struct cfdata *cf, void *aux);
static void iobus_attach(struct device *parent, struct device *self, void *aux);
static int iobus_search_ioc(struct device *parent, struct cfdata *cf,
const int *ldesc, void *aux);
static int iobus_search(struct device *parent, struct cfdata *cf,
const int *ldesc, void *aux);
static int iobus_print(void *aux, const char *pnp);
struct iobus_softc {
struct device sc_dev;
};
CFATTACH_DECL(iobus, sizeof(struct iobus_softc),
iobus_match, iobus_attach, NULL, NULL);
struct iobus_softc *the_iobus;
static int
iobus_match(struct device *parent, struct cfdata *cf, void *aux)
{
/* There can be only one! */
if (the_iobus == NULL)
return 1;
return 0;
}
static void
iobus_attach(struct device *parent, struct device *self, void *aux)
{
the_iobus = (struct iobus_softc *)self;
printf("\n");
/*
* Always look for the IOC first, since stuff under there determines
* what else is present.
*/
config_search_ia(iobus_search_ioc, self, "iobus", NULL);
config_search_ia(iobus_search, self, "iobus", NULL);
}
extern struct bus_space iobus_bs_tag;
static int
iobus_search_ioc(struct device *parent, struct cfdata *cf,
const int *ldesc, void *aux)
{
struct iobus_attach_args ioa;
ioa.ioa_tag = &iobus_bs_tag;
ioa.ioa_base = (bus_addr_t)MEMC_IO_BASE + cf->cf_loc[IOBUSCF_BASE];
if (strcmp(cf->cf_name, "ioc") == 0 &&
config_match(parent, cf, &ioa) > 0)
config_attach(parent, cf, &ioa, iobus_print);
return 0;
}
static int
iobus_search(struct device *parent, struct cfdata *cf,
const int *ldesc, void *aux)
{
struct iobus_attach_args ioa;
ioa.ioa_tag = &iobus_bs_tag;
ioa.ioa_base = (bus_addr_t)MEMC_IO_BASE + cf->cf_loc[IOBUSCF_BASE];
if (config_match(parent, cf, &ioa) > 0)
config_attach(parent, cf, &ioa, iobus_print);
return 0;
}
static int
iobus_print(void *aux, const char *pnp)
{
struct iobus_attach_args *ioa = aux;
if (ioa->ioa_base != IOBUSCF_BASE_DEFAULT)
aprint_normal(" base 0x%06lx",
ioa->ioa_base - (bus_addr_t)MEMC_IO_BASE);
return UNCONF;
}