1ae36cccdSWarner Losh /*- 24d846d26SWarner Losh * SPDX-License-Identifier: BSD-2-Clause 3718cf2ccSPedro F. Giffuni * 4ae36cccdSWarner Losh * Copyright (c) 2007 Bruce M. Simpson. 5ae36cccdSWarner Losh * All rights reserved. 6ae36cccdSWarner Losh * 7ae36cccdSWarner Losh * Redistribution and use in source and binary forms, with or without 8ae36cccdSWarner Losh * modification, are permitted provided that the following conditions 9ae36cccdSWarner Losh * are met: 10ae36cccdSWarner Losh * 1. Redistributions of source code must retain the above copyright 11ae36cccdSWarner Losh * notice, this list of conditions and the following disclaimer. 12ae36cccdSWarner Losh * 2. Redistributions in binary form must reproduce the above copyright 13ae36cccdSWarner Losh * notice, this list of conditions and the following disclaimer in the 14ae36cccdSWarner Losh * documentation and/or other materials provided with the distribution. 15ae36cccdSWarner Losh * 16ae36cccdSWarner Losh * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17ae36cccdSWarner Losh * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18ae36cccdSWarner Losh * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19ae36cccdSWarner Losh * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20ae36cccdSWarner Losh * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21ae36cccdSWarner Losh * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22ae36cccdSWarner Losh * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23ae36cccdSWarner Losh * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24ae36cccdSWarner Losh * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25ae36cccdSWarner Losh * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26ae36cccdSWarner Losh * SUCH DAMAGE. 27ae36cccdSWarner Losh */ 28ae36cccdSWarner Losh 29ae36cccdSWarner Losh /* 30ae36cccdSWarner Losh * Driver to swallow up memory ranges reserved by CFE platform firmware. 31ae36cccdSWarner Losh * CFE on Sentry5 doesn't specify reserved ranges, so this is not useful 32ae36cccdSWarner Losh * at the present time. 33ae36cccdSWarner Losh * TODO: Don't attach this off nexus. 34ae36cccdSWarner Losh */ 35ae36cccdSWarner Losh 36ae36cccdSWarner Losh #include <sys/param.h> 37ae36cccdSWarner Losh #include <sys/systm.h> 38ae36cccdSWarner Losh #include <sys/kernel.h> 39ae36cccdSWarner Losh #include <sys/socket.h> 40ae36cccdSWarner Losh 41ae36cccdSWarner Losh #include <sys/module.h> 42ae36cccdSWarner Losh #include <sys/bus.h> 43ae36cccdSWarner Losh 44ae36cccdSWarner Losh #include <machine/bus.h> 45ae36cccdSWarner Losh #include <machine/resource.h> 46ae36cccdSWarner Losh #include <sys/rman.h> 47ae36cccdSWarner Losh 48ae36cccdSWarner Losh #include <dev/cfe/cfe_api.h> 49ae36cccdSWarner Losh #include <dev/cfe/cfe_error.h> 50ae36cccdSWarner Losh 51ae36cccdSWarner Losh #define MAX_CFE_RESERVATIONS 16 52ae36cccdSWarner Losh 53ae36cccdSWarner Losh struct cferes_softc { 54ae36cccdSWarner Losh int rnum; 55ae36cccdSWarner Losh int rid[MAX_CFE_RESERVATIONS]; 56ae36cccdSWarner Losh struct resource *res[MAX_CFE_RESERVATIONS]; 57ae36cccdSWarner Losh }; 58ae36cccdSWarner Losh 59ae36cccdSWarner Losh static int 60ae36cccdSWarner Losh cferes_probe(device_t dev) 61ae36cccdSWarner Losh { 62ae36cccdSWarner Losh 63feeec74dSNathan Whitehorn return (BUS_PROBE_NOWILDCARD); 64ae36cccdSWarner Losh } 65ae36cccdSWarner Losh 66ae36cccdSWarner Losh static int 67ae36cccdSWarner Losh cferes_attach(device_t dev) 68ae36cccdSWarner Losh { 69ae36cccdSWarner Losh 70ae36cccdSWarner Losh return (0); 71ae36cccdSWarner Losh } 72ae36cccdSWarner Losh 73ae36cccdSWarner Losh static void 74ae36cccdSWarner Losh cferes_identify(driver_t* driver, device_t parent) 75ae36cccdSWarner Losh { 76ae36cccdSWarner Losh device_t child; 77ae36cccdSWarner Losh int i; 78ae36cccdSWarner Losh struct resource *res; 79ae36cccdSWarner Losh int result; 80ae36cccdSWarner Losh int rid; 81ae36cccdSWarner Losh struct cferes_softc *sc; 82ae36cccdSWarner Losh uint64_t addr, len, type; 83ae36cccdSWarner Losh 84*a05a6804SWarner Losh child = BUS_ADD_CHILD(parent, 100, "cferes", DEVICE_UNIT_ANY); 85ae36cccdSWarner Losh device_set_driver(child, driver); 86ae36cccdSWarner Losh sc = device_get_softc(child); 87ae36cccdSWarner Losh 88ae36cccdSWarner Losh sc->rnum = 0; 89ae36cccdSWarner Losh for (i = 0; i < ~0U; i++) { 90ae36cccdSWarner Losh result = cfe_enummem(i, CFE_FLG_FULL_ARENA, &addr, &len, &type); 91ae36cccdSWarner Losh if (result < 0) 92ae36cccdSWarner Losh break; 93ae36cccdSWarner Losh if (type != CFE_MI_RESERVED) { 94ae36cccdSWarner Losh if (bootverbose) 95ae36cccdSWarner Losh printf("%s: skipping non reserved range 0x%0jx(%jd)\n", 96ae36cccdSWarner Losh device_getnameunit(child), 97ae36cccdSWarner Losh (uintmax_t)addr, (uintmax_t)len); 98ae36cccdSWarner Losh continue; 99ae36cccdSWarner Losh } 100ae36cccdSWarner Losh 101ae36cccdSWarner Losh bus_set_resource(child, SYS_RES_MEMORY, sc->rnum, addr, len); 102ae36cccdSWarner Losh rid = sc->rnum; 103ae36cccdSWarner Losh res = bus_alloc_resource_any(child, SYS_RES_MEMORY, &rid, 0); 104ae36cccdSWarner Losh if (res == NULL) { 105ae36cccdSWarner Losh bus_delete_resource(child, SYS_RES_MEMORY, sc->rnum); 106ae36cccdSWarner Losh continue; 107ae36cccdSWarner Losh } 108ae36cccdSWarner Losh sc->rid[sc->rnum] = rid; 109ae36cccdSWarner Losh sc->res[sc->rnum] = res; 110ae36cccdSWarner Losh 111ae36cccdSWarner Losh sc->rnum++; 112ae36cccdSWarner Losh if (sc->rnum == MAX_CFE_RESERVATIONS) 113ae36cccdSWarner Losh break; 114ae36cccdSWarner Losh } 115ae36cccdSWarner Losh 116ae36cccdSWarner Losh if (sc->rnum == 0) { 117ae36cccdSWarner Losh device_delete_child(parent, child); 118ae36cccdSWarner Losh return; 119ae36cccdSWarner Losh } 120ae36cccdSWarner Losh 121ae36cccdSWarner Losh device_set_desc(child, "CFE reserved memory"); 122ae36cccdSWarner Losh } 123ae36cccdSWarner Losh 124ae36cccdSWarner Losh static int 125ae36cccdSWarner Losh cferes_detach(device_t dev) 126ae36cccdSWarner Losh { 127ae36cccdSWarner Losh int i; 128ae36cccdSWarner Losh struct cferes_softc *sc = device_get_softc(dev); 129ae36cccdSWarner Losh 130ae36cccdSWarner Losh for (i = 0; i < sc->rnum; i++) { 131ae36cccdSWarner Losh bus_release_resource(dev, SYS_RES_MEMORY, sc->rid[i], 132ae36cccdSWarner Losh sc->res[i]); 133ae36cccdSWarner Losh } 134ae36cccdSWarner Losh 135ae36cccdSWarner Losh return (0); 136ae36cccdSWarner Losh } 137ae36cccdSWarner Losh 138ae36cccdSWarner Losh static device_method_t cferes_methods[] = { 139ae36cccdSWarner Losh /* Device interface */ 140ae36cccdSWarner Losh DEVMETHOD(device_identify, cferes_identify), 141ae36cccdSWarner Losh DEVMETHOD(device_probe, cferes_probe), 142ae36cccdSWarner Losh DEVMETHOD(device_attach, cferes_attach), 143ae36cccdSWarner Losh DEVMETHOD(device_detach, cferes_detach), 144ae36cccdSWarner Losh DEVMETHOD(device_shutdown, bus_generic_shutdown), 145ae36cccdSWarner Losh DEVMETHOD(device_suspend, bus_generic_suspend), 146ae36cccdSWarner Losh DEVMETHOD(device_resume, bus_generic_resume), 147ae36cccdSWarner Losh { 0, 0 } 148ae36cccdSWarner Losh }; 149ae36cccdSWarner Losh 150ae36cccdSWarner Losh static driver_t cferes_driver = { 151ae36cccdSWarner Losh "cferes", 152ae36cccdSWarner Losh cferes_methods, 153ae36cccdSWarner Losh sizeof (struct cferes_softc) 154ae36cccdSWarner Losh }; 155ae36cccdSWarner Losh 156ae36cccdSWarner Losh static devclass_t cferes_devclass; 157ae36cccdSWarner Losh 158ae36cccdSWarner Losh DRIVER_MODULE(cfe, nexus, cferes_driver, cferes_devclass, 0, 0); 159