From owner-p4-projects@FreeBSD.ORG Wed Dec 14 18:24:17 2005 Return-Path: X-Original-To: p4-projects@freebsd.org Delivered-To: p4-projects@freebsd.org Received: by hub.freebsd.org (Postfix, from userid 32767) id 666A916A478; Wed, 14 Dec 2005 18:24:17 +0000 (GMT) X-Original-To: perforce@freebsd.org Delivered-To: perforce@freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id B2A8216A444 for ; Wed, 14 Dec 2005 18:24:16 +0000 (GMT) (envelope-from imp@freebsd.org) Received: from repoman.freebsd.org (repoman.freebsd.org [216.136.204.115]) by mx1.FreeBSD.org (Postfix) with ESMTP id 5FC1943D45 for ; Wed, 14 Dec 2005 18:24:16 +0000 (GMT) (envelope-from imp@freebsd.org) Received: from repoman.freebsd.org (localhost [127.0.0.1]) by repoman.freebsd.org (8.13.1/8.13.1) with ESMTP id jBEIOGbN082505 for ; Wed, 14 Dec 2005 18:24:16 GMT (envelope-from imp@freebsd.org) Received: (from perforce@localhost) by repoman.freebsd.org (8.13.1/8.13.1/Submit) id jBEIOFc6082501 for perforce@freebsd.org; Wed, 14 Dec 2005 18:24:15 GMT (envelope-from imp@freebsd.org) Date: Wed, 14 Dec 2005 18:24:15 GMT Message-Id: <200512141824.jBEIOFc6082501@repoman.freebsd.org> X-Authentication-Warning: repoman.freebsd.org: perforce set sender to imp@freebsd.org using -f From: Warner Losh To: Perforce Change Reviews Cc: Subject: PERFORCE change 88185 for review X-BeenThere: p4-projects@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: p4 projects tree changes List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 14 Dec 2005 18:24:18 -0000 http://perforce.freebsd.org/chv.cgi?CH=88185 Change 88185 by imp@imp_Speedy on 2005/12/14 18:23:48 attempt to make the atmelarm bus do real resource allocation. Affected files ... .. //depot/projects/arm/src/sys/arm/at91/at91rm92.c#6 edit .. //depot/projects/arm/src/sys/arm/at91/at91rm92var.h#3 edit Differences ... ==== //depot/projects/arm/src/sys/arm/at91/at91rm92.c#6 (text+ko) ==== @@ -29,6 +29,7 @@ #include #include #include +#include #include #include @@ -160,7 +161,7 @@ static int at91rm92_probe(device_t dev) { - device_set_desc(dev, "AT91RM9200"); + device_set_desc(dev, "AT91 CPU"); return (0); } @@ -186,6 +187,30 @@ extern void irq_entry(void); +static void +at91rm92_add_child(device_t dev, int prio, const char *name, int unit, + bus_addr_t addr, bus_size_t size, int irq) +{ + device_t kid; + struct at91rm92_ivar *ivar; + + kid = device_add_child_ordered(dev, prio, name, unit); + if (kid == NULL) + return; + ivar = malloc(sizeof(*ivar), M_DEVBUF, M_WAITOK | M_ZERO); + if (ivar == NULL) { + device_delete_child(dev, kid); + return; + } + device_set_ivars(kid, ivar); + resource_list_init(&ivar->resources); + if (irq != -1) + bus_set_resource(kid, SYS_RES_IRQ, 0, irq, 1); + if (addr != 0) + bus_set_resource(kid, SYS_RES_MEMORY, 0, addr, size); +} + + static int at91rm92_attach(device_t dev) { @@ -196,14 +221,20 @@ sc->sc_st = &at91rm92_bs_tag; sc->sc_sh = AT91RM92_BASE; sc->dev = dev; - sc->sc_irq_rman.rm_type = RMAN_ARRAY; - sc->sc_irq_rman.rm_descr = "AT91RM92 IRQs"; if (bus_space_subregion(sc->sc_st, sc->sc_sh, AT91RM92_SYS_BASE, AT91RM92_SYS_SIZE, &sc->sc_sys_sh) != 0) panic("Enable to map IRQ registers"); + sc->sc_irq_rman.rm_type = RMAN_ARRAY; + sc->sc_irq_rman.rm_descr = "AT91RM92 IRQs"; + sc->sc_mem_rman.rm_type = RMAN_ARRAY; + sc->sc_mem_rman.rm_descr = "AT91RM92 Memory"; if (rman_init(&sc->sc_irq_rman) != 0 || rman_manage_region(&sc->sc_irq_rman, 1, 31) != 0) panic("at91rm92_attach: failed to set up IRQ rman"); + if (rman_init(&sc->sc_mem_rman) != 0 || + rman_manage_region(&sc->sc_mem_rman, 0xfff00000ul, + 0xfffffffful) != 0) + panic("at91rm92_attach: failed to set up memory rman"); for (i = 0; i < 32; i++) { bus_space_write_4(sc->sc_st, sc->sc_sys_sh, IC_SVR + @@ -223,7 +254,18 @@ /* Disable and clear all interrupts. */ bus_space_write_4(sc->sc_st, sc->sc_sys_sh, IC_IDCR, 0xffffffff); bus_space_write_4(sc->sc_st, sc->sc_sys_sh, IC_ICCR, 0xffffffff); - device_add_child(dev, "at91rm92_timer", 0); + + at91rm92_add_child(dev, 0, "at91rm92_timer", 0, 0, 0, 1); + at91rm92_add_child(dev, 10, "uart", 0, AT91RM92_BASE + + AT91RM92_SYS_BASE + DBGU, DBGU_SIZE, 1); // DBGU + at91rm92_add_child(dev, 10, "uart", 1, AT91RM92_BASE + + AT91RM92_USART0_BASE, AT91RM92_USART_SIZE, 6); // USART0 + at91rm92_add_child(dev, 10, "uart", 2, AT91RM92_BASE + + AT91RM92_USART1_BASE, AT91RM92_USART_SIZE, 7); // USART1 + at91rm92_add_child(dev, 10, "uart", 3, AT91RM92_BASE + + AT91RM92_USART2_BASE, AT91RM92_USART_SIZE, 8); // USART2 + at91rm92_add_child(dev, 10, "uart", 4, AT91RM92_BASE + + AT91RM92_USART3_BASE, AT91RM92_USART_SIZE, 9); // USART3 bus_generic_probe(dev); bus_generic_attach(dev); enable_interrupts(I32_bit | F32_bit); @@ -251,11 +293,67 @@ u_long start, u_long end, u_long count, u_int flags) { struct at91rm92_softc *sc = device_get_softc(dev); + struct resource_list_entry *rle; + struct at91rm92_ivar *ivar = device_get_ivars(child); + struct resource_list *rl = &ivar->resources; + + if (device_get_parent(child) != dev) + return (BUS_ALLOC_RESOURCE(device_get_parent(dev), child, + type, rid, start, end, count, flags)); - if (type == SYS_RES_IRQ) - return (rman_reserve_resource(&sc->sc_irq_rman, - start, end, count, flags, child)); - return (NULL); + rle = resource_list_find(rl, type, *rid); + if (rle == NULL) + return (NULL); + if (rle->res) + panic("Resource rid %d type %d already in use", *rid, type); + if (start == 0UL && end == ~0UL) { + start = rle->start; + count = ulmax(count, rle->count); + end = ulmax(rle->end, start + count - 1); + } + switch (type) + { + case SYS_RES_IRQ: + rle->res = rman_reserve_resource(&sc->sc_irq_rman, + start, end, count, flags, child); + break; + case SYS_RES_MEMORY: + rle->res = rman_reserve_resource(&sc->sc_mem_rman, + start, end, count, flags, child); + } + if (rle->res) { + rle->start = rman_get_start(rle->res); + rle->end = rman_get_end(rle->res); + rle->count = count; + } + return (rle->res); +} + +static struct resource_list * +at91rm92_get_resource_list(device_t dev, device_t child) +{ + struct at91rm92_ivar *ivar; + + ivar = device_get_ivars(child); + return (&(ivar->resources)); +} + +static int +at91rm92_release_resource(device_t dev, device_t child, int type, + int rid, struct resource *r) +{ + struct resource_list *rl; + struct resource_list_entry *rle; + + rl = at91rm92_get_resource_list(dev, child); + if (rl == NULL) + return (EINVAL); + rle = resource_list_find(rl, type, rid); + if (rle == NULL) + return (EINVAL); + rman_release_resource(r); + rle->res = NULL; + return (0); } static int @@ -287,6 +385,7 @@ at91rm92_activate_resource(device_t bus, device_t child, int type, int rid, struct resource *r) { +#if 0 u_long p; int error; @@ -296,11 +395,34 @@ if (error) return (error); rman_set_bushandle(r, p); - } +#endif return (rman_activate_resource(r)); } +static int +at91rm92_print_child(device_t dev, device_t child) +{ + struct at91rm92_ivar *ivars; + struct resource_list *rl; + int retval = 0; + + ivars = device_get_ivars(child); + rl = &ivars->resources; + + retval += bus_print_child_header(dev, child); + + retval += resource_list_print_type(rl, "port", SYS_RES_IOPORT, "%#lx"); + retval += resource_list_print_type(rl, "mem", SYS_RES_MEMORY, "%#lx"); + retval += resource_list_print_type(rl, "irq", SYS_RES_IRQ, "%ld"); + if (device_get_flags(dev)) + retval += printf(" flags %#x", device_get_flags(dev)); + + retval += bus_print_child_footer(dev, child); + + return (retval); +} + void arm_mask_irq(uintptr_t nb) { @@ -342,12 +464,17 @@ DEVMETHOD(device_probe, at91rm92_probe), DEVMETHOD(device_attach, at91rm92_attach), DEVMETHOD(device_identify, at91rm92_identify), + DEVMETHOD(bus_alloc_resource, at91rm92_alloc_resource), DEVMETHOD(bus_setup_intr, at91rm92_setup_intr), DEVMETHOD(bus_teardown_intr, at91rm92_teardown_intr), - DEVMETHOD(bus_release_resource, bus_generic_release_resource), DEVMETHOD(bus_activate_resource, at91rm92_activate_resource), DEVMETHOD(bus_deactivate_resource, bus_generic_deactivate_resource), + DEVMETHOD(bus_get_resource_list,at91rm92_get_resource_list), + DEVMETHOD(bus_set_resource, bus_generic_rl_set_resource), + DEVMETHOD(bus_get_resource, bus_generic_rl_get_resource), + DEVMETHOD(bus_release_resource, at91rm92_release_resource), + DEVMETHOD(bus_print_child, at91rm92_print_child), {0, 0}, }; ==== //depot/projects/arm/src/sys/arm/at91/at91rm92var.h#3 (text+ko) ==== @@ -35,6 +35,12 @@ bus_space_handle_t sc_sh; bus_space_handle_t sc_sys_sh; struct rman sc_irq_rman; + struct rman sc_mem_rman; +}; + +struct at91rm92_ivar { + struct resource_list resources; }; + #endif /* _AT91RM92VAR_H_ */