From owner-svn-src-head@FreeBSD.ORG Wed Aug 15 03:49:11 2012 Return-Path: Delivered-To: svn-src-head@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [69.147.83.52]) by hub.freebsd.org (Postfix) with ESMTP id ABF37106566B; Wed, 15 Aug 2012 03:49:11 +0000 (UTC) (envelope-from gonzo@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id 94E518FC0C; Wed, 15 Aug 2012 03:49:11 +0000 (UTC) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.4/8.14.4) with ESMTP id q7F3nBxr095927; Wed, 15 Aug 2012 03:49:11 GMT (envelope-from gonzo@svn.freebsd.org) Received: (from gonzo@localhost) by svn.freebsd.org (8.14.4/8.14.4/Submit) id q7F3nBGi095921; Wed, 15 Aug 2012 03:49:11 GMT (envelope-from gonzo@svn.freebsd.org) Message-Id: <201208150349.q7F3nBGi095921@svn.freebsd.org> From: Oleksandr Tymoshenko Date: Wed, 15 Aug 2012 03:49:11 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r239274 - in head/sys/dev: fdt uart X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 15 Aug 2012 03:49:11 -0000 Author: gonzo Date: Wed Aug 15 03:49:10 2012 New Revision: 239274 URL: http://svn.freebsd.org/changeset/base/239274 Log: Merging of projects/armv6, part 4 r233822: Remove useless and wrong piece of code in fdt_get_range() which i overwrites passed phandle_t node. Modify debug printf in fdt_reg_to_rl() to be consistent (that is, print start and end *virtual* addresses). r230560: Handle "ranges;" Make fdt_reg_to_rl() responsible for mapping the device memory, instead on just hoping that there's only one simplebus, and using fdt_immr_va as the base VA. r230315 Add a function to get the PA from range, instead of (ab)using fdt_immr_pa, and use it for the UART driver Modified: head/sys/dev/fdt/fdt_common.c head/sys/dev/fdt/fdt_common.h head/sys/dev/fdt/fdtbus.c head/sys/dev/fdt/simplebus.c head/sys/dev/uart/uart_bus_fdt.c Modified: head/sys/dev/fdt/fdt_common.c ============================================================================== --- head/sys/dev/fdt/fdt_common.c Wed Aug 15 03:33:57 2012 (r239273) +++ head/sys/dev/fdt/fdt_common.c Wed Aug 15 03:49:10 2012 (r239274) @@ -35,6 +35,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include @@ -63,30 +64,12 @@ vm_offset_t fdt_immr_va; vm_offset_t fdt_immr_size; int -fdt_immr_addr(vm_offset_t immr_va) +fdt_get_range(phandle_t node, int range_id, u_long *base, u_long *size) { pcell_t ranges[6], *rangesptr; - phandle_t node; - u_long base, size; pcell_t addr_cells, size_cells, par_addr_cells; int len, tuple_size, tuples; - /* - * Try to access the SOC node directly i.e. through /aliases/. - */ - if ((node = OF_finddevice("soc")) != -1) - if (fdt_is_compatible_strict(node, "simple-bus")) - goto moveon; - /* - * Find the node the long way. - */ - if ((node = OF_finddevice("/")) == -1) - return (ENXIO); - - if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0) - return (ENXIO); - -moveon: if ((fdt_addrsize_cells(node, &addr_cells, &size_cells)) != 0) return (ENXIO); /* @@ -99,6 +82,14 @@ moveon: len = OF_getproplen(node, "ranges"); if (len > sizeof(ranges)) return (ENOMEM); + if (len == 0) { + *base = 0; + *size = ULONG_MAX; + return (0); + } + + if (!(range_id < len)) + return (ERANGE); if (OF_getprop(node, "ranges", ranges, sizeof(ranges)) <= 0) return (EINVAL); @@ -111,21 +102,48 @@ moveon: addr_cells, size_cells)) { return (ERANGE); } - base = 0; - size = 0; - rangesptr = &ranges[0]; + *base = 0; + *size = 0; + rangesptr = &ranges[range_id]; - base = fdt_data_get((void *)rangesptr, addr_cells); + *base = fdt_data_get((void *)rangesptr, addr_cells); rangesptr += addr_cells; - base += fdt_data_get((void *)rangesptr, par_addr_cells); + *base += fdt_data_get((void *)rangesptr, par_addr_cells); rangesptr += par_addr_cells; - size = fdt_data_get((void *)rangesptr, size_cells); + *size = fdt_data_get((void *)rangesptr, size_cells); + return (0); +} - fdt_immr_pa = base; - fdt_immr_va = immr_va; - fdt_immr_size = size; +int +fdt_immr_addr(vm_offset_t immr_va) +{ + phandle_t node; + u_long base, size; + int r; - return (0); + /* + * Try to access the SOC node directly i.e. through /aliases/. + */ + if ((node = OF_finddevice("soc")) != 0) + if (fdt_is_compatible_strict(node, "simple-bus")) + goto moveon; + /* + * Find the node the long way. + */ + if ((node = OF_finddevice("/")) == 0) + return (ENXIO); + + if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0) + return (ENXIO); + +moveon: + if ((r = fdt_get_range(node, 0, &base, &size)) == 0) { + fdt_immr_pa = base; + fdt_immr_va = immr_va; + fdt_immr_size = size; + } + + return (r); } /* @@ -401,16 +419,19 @@ fdt_regsize(phandle_t node, u_long *base } int -fdt_reg_to_rl(phandle_t node, struct resource_list *rl, u_long base) +fdt_reg_to_rl(phandle_t node, struct resource_list *rl) { u_long start, end, count; pcell_t *reg, *regptr; pcell_t addr_cells, size_cells; int tuple_size, tuples; int i, rv; + long vaddr; + long busaddr, bussize; if (fdt_addrsize_cells(OF_parent(node), &addr_cells, &size_cells) != 0) return (ENXIO); + fdt_get_range(OF_parent(node), 0, &busaddr, &bussize); tuple_size = sizeof(pcell_t) * (addr_cells + size_cells); tuples = OF_getprop_alloc(node, "reg", tuple_size, (void **)®); @@ -432,14 +453,15 @@ fdt_reg_to_rl(phandle_t node, struct res reg += addr_cells + size_cells; /* Calculate address range relative to base. */ - start &= 0x000ffffful; - start = base + start; - end = start + count - 1; + start += busaddr; + if (bus_space_map(fdtbus_bs_tag, start, count, 0, &vaddr) != 0) + panic("Couldn't map the device memory"); + end = vaddr + count - 1; - debugf("reg addr start = %lx, end = %lx, count = %lx\n", start, + debugf("reg addr start = %lx, end = %lx, count = %lx\n", vaddr, end, count); - resource_list_add(rl, SYS_RES_MEMORY, i, start, end, + resource_list_add(rl, SYS_RES_MEMORY, i, vaddr, end, count); } rv = 0; Modified: head/sys/dev/fdt/fdt_common.h ============================================================================== --- head/sys/dev/fdt/fdt_common.h Wed Aug 15 03:33:57 2012 (r239273) +++ head/sys/dev/fdt/fdt_common.h Wed Aug 15 03:49:10 2012 (r239274) @@ -91,6 +91,7 @@ int fdt_data_verify(void *, int); phandle_t fdt_find_compatible(phandle_t, const char *, int); int fdt_get_mem_regions(struct mem_region *, int *, uint32_t *); int fdt_get_phyaddr(phandle_t, device_t, int *, void **); +int fdt_get_range(phandle_t, int, u_long *, u_long *); int fdt_immr_addr(vm_offset_t); int fdt_regsize(phandle_t, u_long *, u_long *); int fdt_intr_decode(phandle_t, pcell_t *, int *, int *, int *); @@ -107,7 +108,7 @@ int fdt_pci_ranges_decode(phandle_t, str struct fdt_pci_range *); int fdt_pci_route_intr(int, int, int, int, struct fdt_pci_intr *, int *); int fdt_ranges_verify(pcell_t *, int, int, int, int); -int fdt_reg_to_rl(phandle_t, struct resource_list *, u_long); +int fdt_reg_to_rl(phandle_t, struct resource_list *); int fdt_pm(phandle_t); #endif /* _FDT_COMMON_H_ */ Modified: head/sys/dev/fdt/fdtbus.c ============================================================================== --- head/sys/dev/fdt/fdtbus.c Wed Aug 15 03:33:57 2012 (r239273) +++ head/sys/dev/fdt/fdtbus.c Wed Aug 15 03:49:10 2012 (r239274) @@ -289,7 +289,7 @@ newbus_device_create(device_t dev_par, p resource_list_init(&di->di_res); - if (fdt_reg_to_rl(node, &di->di_res, fdt_immr_va)) { + if (fdt_reg_to_rl(node, &di->di_res)) { device_printf(child, "could not process 'reg' property\n"); newbus_device_destroy(child); child = NULL; Modified: head/sys/dev/fdt/simplebus.c ============================================================================== --- head/sys/dev/fdt/simplebus.c Wed Aug 15 03:33:57 2012 (r239273) +++ head/sys/dev/fdt/simplebus.c Wed Aug 15 03:49:10 2012 (r239274) @@ -61,9 +61,6 @@ static MALLOC_DEFINE(M_SIMPLEBUS, "simpl struct simplebus_softc { int sc_addr_cells; int sc_size_cells; - u_long sc_start_pa; - u_long sc_start_va; - u_long sc_size; }; struct simplebus_devinfo { @@ -155,10 +152,6 @@ simplebus_attach(device_t dev) sc = device_get_softc(dev); - sc->sc_start_pa = fdt_immr_pa; - sc->sc_start_va = fdt_immr_va; - sc->sc_size = fdt_immr_size; - /* * Walk simple-bus and add direct subordinates as our children. */ @@ -182,10 +175,11 @@ simplebus_attach(device_t dev) } resource_list_init(&di->di_res); - - if (fdt_reg_to_rl(dt_child, &di->di_res, sc->sc_start_va)) { - device_printf(dev, "%s: could not process 'reg' " + if (fdt_reg_to_rl(dt_child, &di->di_res)) { + device_printf(dev, + "%s: could not process 'reg' " "property\n", di->di_ofw.obd_name); + /* XXX should unmap */ ofw_bus_gen_destroy_devinfo(&di->di_ofw); free(di, M_SIMPLEBUS); continue; @@ -195,6 +189,7 @@ simplebus_attach(device_t dev) device_printf(dev, "%s: could not process " "'interrupts' property\n", di->di_ofw.obd_name); resource_list_free(&di->di_res); + /* XXX should unmap */ ofw_bus_gen_destroy_devinfo(&di->di_ofw); free(di, M_SIMPLEBUS); continue; @@ -206,6 +201,7 @@ simplebus_attach(device_t dev) device_printf(dev, "could not add child: %s\n", di->di_ofw.obd_name); resource_list_free(&di->di_res); + /* XXX should unmap */ ofw_bus_gen_destroy_devinfo(&di->di_ofw); free(di, M_SIMPLEBUS); continue; Modified: head/sys/dev/uart/uart_bus_fdt.c ============================================================================== --- head/sys/dev/uart/uart_bus_fdt.c Wed Aug 15 03:33:57 2012 (r239273) +++ head/sys/dev/uart/uart_bus_fdt.c Wed Aug 15 03:49:10 2012 (r239274) @@ -137,7 +137,7 @@ uart_cpu_getdev(int devtype, struct uart struct uart_class *class; phandle_t node, chosen; pcell_t shift, br, rclk; - u_long start, size; + u_long start, size, pbase, psize; int err; uart_bus_space_mem = fdtbus_bs_tag; @@ -197,7 +197,9 @@ uart_cpu_getdev(int devtype, struct uart err = fdt_regsize(node, &start, &size); if (err) return (ENXIO); - start += fdt_immr_va; + + fdt_get_range(OF_parent(node), 0, &pbase, &psize); + start += pbase; return (bus_space_map(di->bas.bst, start, size, 0, &di->bas.bsh)); }