xref: /netbsd-src/sys/dev/fdt/fdt_syscon.c (revision 5375fcbde97192f15f1ba8bd7484c1f1eda93a58)
1*5375fcbdSjmcneill /* $NetBSD: fdt_syscon.c,v 1.3 2018/06/30 20:16:56 jmcneill Exp $ */
25b0333ebSjmcneill 
35b0333ebSjmcneill /*-
45b0333ebSjmcneill  * Copyright (c) 2018 Jared McNeill <jmcneill@invisible.ca>
55b0333ebSjmcneill  * All rights reserved.
65b0333ebSjmcneill  *
75b0333ebSjmcneill  * Redistribution and use in source and binary forms, with or without
85b0333ebSjmcneill  * modification, are permitted provided that the following conditions
95b0333ebSjmcneill  * are met:
105b0333ebSjmcneill  * 1. Redistributions of source code must retain the above copyright
115b0333ebSjmcneill  *    notice, this list of conditions and the following disclaimer.
125b0333ebSjmcneill  * 2. Redistributions in binary form must reproduce the above copyright
135b0333ebSjmcneill  *    notice, this list of conditions and the following disclaimer in the
145b0333ebSjmcneill  *    documentation and/or other materials provided with the distribution.
155b0333ebSjmcneill  *
165b0333ebSjmcneill  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
175b0333ebSjmcneill  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
185b0333ebSjmcneill  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
195b0333ebSjmcneill  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
205b0333ebSjmcneill  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
215b0333ebSjmcneill  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
225b0333ebSjmcneill  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
235b0333ebSjmcneill  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
245b0333ebSjmcneill  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
255b0333ebSjmcneill  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
265b0333ebSjmcneill  * SUCH DAMAGE.
275b0333ebSjmcneill  */
285b0333ebSjmcneill 
295b0333ebSjmcneill #include <sys/cdefs.h>
30*5375fcbdSjmcneill __KERNEL_RCSID(0, "$NetBSD: fdt_syscon.c,v 1.3 2018/06/30 20:16:56 jmcneill Exp $");
315b0333ebSjmcneill 
325b0333ebSjmcneill #include <sys/param.h>
335b0333ebSjmcneill #include <sys/bus.h>
345b0333ebSjmcneill #include <sys/kmem.h>
355b0333ebSjmcneill #include <sys/queue.h>
365b0333ebSjmcneill 
375b0333ebSjmcneill #include <libfdt.h>
385b0333ebSjmcneill #include <dev/fdt/fdtvar.h>
395b0333ebSjmcneill 
405b0333ebSjmcneill struct syscon;
415b0333ebSjmcneill 
425b0333ebSjmcneill struct fdtbus_syscon {
435b0333ebSjmcneill 	device_t sc_dev;
445b0333ebSjmcneill 	int sc_phandle;
455b0333ebSjmcneill 	struct syscon *sc_syscon;
465b0333ebSjmcneill 
475b0333ebSjmcneill 	LIST_ENTRY(fdtbus_syscon) sc_next;
485b0333ebSjmcneill };
495b0333ebSjmcneill 
50*5375fcbdSjmcneill static LIST_HEAD(, fdtbus_syscon) fdtbus_syscons =
515b0333ebSjmcneill     LIST_HEAD_INITIALIZER(fdtbus_syscons);
525b0333ebSjmcneill 
535b0333ebSjmcneill int
fdtbus_register_syscon(device_t dev,int phandle,struct syscon * syscon)545b0333ebSjmcneill fdtbus_register_syscon(device_t dev, int phandle,
555b0333ebSjmcneill     struct syscon *syscon)
565b0333ebSjmcneill {
575b0333ebSjmcneill 	struct fdtbus_syscon *sc;
585b0333ebSjmcneill 
595b0333ebSjmcneill 	sc = kmem_alloc(sizeof(*sc), KM_SLEEP);
605b0333ebSjmcneill 	sc->sc_dev = dev;
615b0333ebSjmcneill 	sc->sc_phandle = phandle;
625b0333ebSjmcneill 	sc->sc_syscon = syscon;
635b0333ebSjmcneill 
645b0333ebSjmcneill 	LIST_INSERT_HEAD(&fdtbus_syscons, sc, sc_next);
655b0333ebSjmcneill 
665b0333ebSjmcneill 	return 0;
675b0333ebSjmcneill }
685b0333ebSjmcneill 
695b0333ebSjmcneill static struct fdtbus_syscon *
fdtbus_get_syscon(int phandle)705b0333ebSjmcneill fdtbus_get_syscon(int phandle)
715b0333ebSjmcneill {
725b0333ebSjmcneill 	struct fdtbus_syscon *sc;
735b0333ebSjmcneill 
745b0333ebSjmcneill 	LIST_FOREACH(sc, &fdtbus_syscons, sc_next) {
755b0333ebSjmcneill 		if (sc->sc_phandle == phandle)
765b0333ebSjmcneill 			return sc;
775b0333ebSjmcneill 	}
785b0333ebSjmcneill 
795b0333ebSjmcneill 	return NULL;
805b0333ebSjmcneill }
815b0333ebSjmcneill 
825b0333ebSjmcneill struct syscon *
fdtbus_syscon_acquire(int phandle,const char * prop)835b0333ebSjmcneill fdtbus_syscon_acquire(int phandle, const char *prop)
845b0333ebSjmcneill {
855b0333ebSjmcneill 	struct fdtbus_syscon *sc;
865b0333ebSjmcneill 	int sc_phandle;
875b0333ebSjmcneill 
885b0333ebSjmcneill 	sc_phandle = fdtbus_get_phandle(phandle, prop);
895b0333ebSjmcneill 	if (sc_phandle < 0)
905b0333ebSjmcneill 		return NULL;
915b0333ebSjmcneill 
925b0333ebSjmcneill 	sc = fdtbus_get_syscon(sc_phandle);
935b0333ebSjmcneill 	if (sc == NULL)
945b0333ebSjmcneill 		return NULL;
955b0333ebSjmcneill 
965b0333ebSjmcneill 	return sc->sc_syscon;
975b0333ebSjmcneill }
981ca6c5c5Sjmcneill 
991ca6c5c5Sjmcneill struct syscon *
fdtbus_syscon_lookup(int phandle)1001ca6c5c5Sjmcneill fdtbus_syscon_lookup(int phandle)
1011ca6c5c5Sjmcneill {
1021ca6c5c5Sjmcneill 	struct fdtbus_syscon *sc;
1031ca6c5c5Sjmcneill 
1041ca6c5c5Sjmcneill 	sc = fdtbus_get_syscon(phandle);
1051ca6c5c5Sjmcneill 	if (sc == NULL)
1061ca6c5c5Sjmcneill 		return NULL;
1071ca6c5c5Sjmcneill 
1081ca6c5c5Sjmcneill 	return sc->sc_syscon;
1091ca6c5c5Sjmcneill }
110