Path: blob/main/sys/arm/annapurna/alpine/alpine_machdep.c
39536 views
/*-1* Copyright (c) 2013 Ruslan Bukin <[email protected]>2* Copyright (c) 2015 Semihalf3* All rights reserved.4*5* Redistribution and use in source and binary forms, with or without6* modification, are permitted provided that the following conditions7* are met:8* 1. Redistributions of source code must retain the above copyright9* notice, this list of conditions and the following disclaimer.10* 2. Redistributions in binary form must reproduce the above copyright11* notice, this list of conditions and the following disclaimer in the12* documentation and/or other materials provided with the distribution.13*14* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND15* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE16* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE17* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE18* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL19* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS20* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)21* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT22* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY23* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF24* SUCH DAMAGE.25*26*/2728#include "opt_ddb.h"29#include "opt_platform.h"3031#include <sys/param.h>32#include <sys/systm.h>33#include <sys/bus.h>34#include <sys/devmap.h>3536#include <vm/vm.h>37#include <vm/pmap.h>3839#include <machine/bus.h>40#include <machine/fdt.h>41#include <machine/platformvar.h>4243#include <dev/fdt/fdt_common.h>44#include <dev/ofw/openfirm.h>4546#include <arm/annapurna/alpine/alpine_mp.h>4748#include "platform_if.h"4950#define WDTLOAD 0x00051#define LOAD_MIN 0x0000000152#define LOAD_MAX 0xFFFFFFFF53#define WDTVALUE 0x00454#define WDTCONTROL 0x00855/* control register masks */56#define INT_ENABLE (1 << 0)57#define RESET_ENABLE (1 << 1)58#define WDTLOCK 0xC0059#define UNLOCK 0x1ACCE55160#define LOCK 0x000000016162bus_addr_t al_devmap_pa;63bus_addr_t al_devmap_size;6465static int66alpine_get_devmap_base(bus_addr_t *pa, bus_addr_t *size)67{68phandle_t node;6970if ((node = OF_finddevice("/")) == -1)71return (ENXIO);7273if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0)74return (ENXIO);7576return fdt_get_range(node, 0, pa, size);77}7879static int80alpine_get_wdt_base(uint32_t *pbase, uint32_t *psize)81{82phandle_t node;83u_long base = 0;84u_long size = 0;8586if (pbase == NULL || psize == NULL)87return (EINVAL);8889if ((node = OF_finddevice("/")) == -1)90return (EFAULT);9192if ((node = fdt_find_compatible(node, "simple-bus", 1)) == 0)93return (EFAULT);9495if ((node =96fdt_find_compatible(node, "arm,sp805", 1)) == 0)97return (EFAULT);9899if (fdt_regsize(node, &base, &size))100return (EFAULT);101102*pbase = base;103*psize = size;104105return (0);106}107108/*109* Construct devmap table with DT-derived config data.110*/111static int112alpine_devmap_init(platform_t plat)113{114alpine_get_devmap_base(&al_devmap_pa, &al_devmap_size);115devmap_add_entry(al_devmap_pa, al_devmap_size);116return (0);117}118119static void120alpine_cpu_reset(platform_t plat)121{122uint32_t wdbase, wdsize;123bus_addr_t wdbaddr;124int ret;125126ret = alpine_get_wdt_base(&wdbase, &wdsize);127if (ret) {128printf("Unable to get WDT base, do power down manually...");129goto infinite;130}131132ret = bus_space_map(fdtbus_bs_tag, al_devmap_pa + wdbase,133wdsize, 0, &wdbaddr);134if (ret) {135printf("Unable to map WDT base, do power down manually...");136goto infinite;137}138139bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTLOCK, UNLOCK);140bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTLOAD, LOAD_MIN);141bus_space_write_4(fdtbus_bs_tag, wdbaddr, WDTCONTROL,142INT_ENABLE | RESET_ENABLE);143144infinite:145while (1) {}146}147148static platform_method_t alpine_methods[] = {149PLATFORMMETHOD(platform_devmap_init, alpine_devmap_init),150PLATFORMMETHOD(platform_cpu_reset, alpine_cpu_reset),151152#ifdef SMP153PLATFORMMETHOD(platform_mp_start_ap, alpine_mp_start_ap),154PLATFORMMETHOD(platform_mp_setmaxid, alpine_mp_setmaxid),155#endif156PLATFORMMETHOD_END,157};158FDT_PLATFORM_DEF(alpine, "alpine", 0, "annapurna,alpine", 200);159160161