From owner-p4-projects@FreeBSD.ORG Thu Nov 16 03:20:40 2006 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 57DF816A416; Thu, 16 Nov 2006 03:20:40 +0000 (UTC) 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 29EA616A412 for ; Thu, 16 Nov 2006 03:20:40 +0000 (UTC) (envelope-from marcel@freebsd.org) Received: from repoman.freebsd.org (repoman.freebsd.org [216.136.204.115]) by mx1.FreeBSD.org (Postfix) with ESMTP id EB18D43D49 for ; Thu, 16 Nov 2006 03:20:39 +0000 (GMT) (envelope-from marcel@freebsd.org) Received: from repoman.freebsd.org (localhost [127.0.0.1]) by repoman.freebsd.org (8.13.6/8.13.6) with ESMTP id kAG3KdAb058150 for ; Thu, 16 Nov 2006 03:20:39 GMT (envelope-from marcel@freebsd.org) Received: (from perforce@localhost) by repoman.freebsd.org (8.13.6/8.13.4/Submit) id kAG3Kdlg058147 for perforce@freebsd.org; Thu, 16 Nov 2006 03:20:39 GMT (envelope-from marcel@freebsd.org) Date: Thu, 16 Nov 2006 03:20:39 GMT Message-Id: <200611160320.kAG3Kdlg058147@repoman.freebsd.org> X-Authentication-Warning: repoman.freebsd.org: perforce set sender to marcel@freebsd.org using -f From: Marcel Moolenaar To: Perforce Change Reviews Cc: Subject: PERFORCE change 110092 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: Thu, 16 Nov 2006 03:20:40 -0000 http://perforce.freebsd.org/chv.cgi?CH=110092 Change 110092 by marcel@marcel_nfs on 2006/11/16 03:19:58 Declare the classes as weak. This allows device driver classes to be compiled-out without causing unresolved symbols. Implement the DT tag fully. Affected files ... .. //depot/projects/uart/dev/uart/uart.h#12 edit .. //depot/projects/uart/dev/uart/uart_core.c#56 edit .. //depot/projects/uart/dev/uart/uart_cpu.h#21 edit .. //depot/projects/uart/dev/uart/uart_cpu_amd64.c#12 edit .. //depot/projects/uart/dev/uart/uart_cpu_i386.c#13 edit .. //depot/projects/uart/dev/uart/uart_cpu_ia64.c#14 edit .. //depot/projects/uart/dev/uart/uart_cpu_pc98.c#14 edit .. //depot/projects/uart/dev/uart/uart_cpu_powerpc.c#3 edit .. //depot/projects/uart/dev/uart/uart_subr.c#8 edit Differences ... ==== //depot/projects/uart/dev/uart/uart.h#12 (text+ko) ==== @@ -64,10 +64,9 @@ */ struct uart_class; -extern struct uart_class uart_ns8250_class; -extern struct uart_class uart_quicc_class; -extern struct uart_class uart_sab82532_class; -extern struct uart_class uart_z8530_class; +extern struct uart_class uart_ns8250_class __attribute__((weak)); +extern struct uart_class uart_sab82532_class __attribute__((weak)); +extern struct uart_class uart_z8530_class __attribute__((weak)); /* * Device flags. ==== //depot/projects/uart/dev/uart/uart_core.c#56 (text+ko) ==== @@ -70,16 +70,22 @@ SLIST_INSERT_HEAD(&uart_sysdevs, di, next); } +const char * +uart_getname(struct uart_class *uc) +{ + return ((uc != NULL) ? uc->name : NULL); +} + struct uart_ops * uart_getops(struct uart_class *uc) { - return (uc->uc_ops); + return ((uc != NULL) ? uc->uc_ops : NULL); } int uart_getrange(struct uart_class *uc) { - return (uc->uc_range); + return ((uc != NULL) ? uc->uc_range : 0); } /* @@ -303,18 +309,26 @@ struct uart_devinfo *sysdev; int error; + sc = device_get_softc(dev); + /* + * All uart_class references are weak. Check that the needed + * class has been compiled-in. Fail if not. + */ + if (sc->sc_class == NULL) + return (ENXIO); + + /* * Initialize the instance. Note that the instance (=softc) does * not necessarily match the hardware specific softc. We can't do * anything about it now, because we may not attach to the device. * Hardware drivers cannot use any of the class specific fields * while probing. */ - sc = device_get_softc(dev); kobj_init((kobj_t)sc, (kobj_class_t)sc->sc_class); sc->sc_dev = dev; if (device_get_desc(dev) == NULL) - device_set_desc(dev, sc->sc_class->name); + device_set_desc(dev, uart_getname(sc->sc_class)); /* * Allocate the register resource. We assume that all UARTs have @@ -326,12 +340,13 @@ sc->sc_rrid = rid; sc->sc_rtype = SYS_RES_IOPORT; sc->sc_rres = bus_alloc_resource(dev, sc->sc_rtype, &sc->sc_rrid, - 0, ~0, sc->sc_class->uc_range, RF_ACTIVE); + 0, ~0, uart_getrange(sc->sc_class), RF_ACTIVE); if (sc->sc_rres == NULL) { sc->sc_rrid = rid; sc->sc_rtype = SYS_RES_MEMORY; sc->sc_rres = bus_alloc_resource(dev, sc->sc_rtype, - &sc->sc_rrid, 0, ~0, sc->sc_class->uc_range, RF_ACTIVE); + &sc->sc_rrid, 0, ~0, uart_getrange(sc->sc_class), + RF_ACTIVE); if (sc->sc_rres == NULL) return (ENXIO); } @@ -400,7 +415,7 @@ * collected by uart_bus_probe() intact. */ sc->sc_rres = bus_alloc_resource(dev, sc->sc_rtype, &sc->sc_rrid, - 0, ~0, sc->sc_class->uc_range, RF_ACTIVE); + 0, ~0, uart_getrange(sc->sc_class), RF_ACTIVE); if (sc->sc_rres == NULL) { mtx_destroy(&sc->sc_hwmtx_s); return (ENXIO); ==== //depot/projects/uart/dev/uart/uart_cpu.h#21 (text+ko) ==== @@ -74,6 +74,7 @@ int uart_cpu_getdev(int, struct uart_devinfo *); int uart_getenv(int, struct uart_devinfo *, struct uart_class *); +const char *uart_getname(struct uart_class *); struct uart_ops *uart_getops(struct uart_class *); int uart_getrange(struct uart_class *); ==== //depot/projects/uart/dev/uart/uart_cpu_amd64.c#12 (text+ko) ==== @@ -53,6 +53,8 @@ unsigned int i, ivar; class = &uart_ns8250_class; + if (class == NULL) + return (ENXIO); /* Check the environment. */ if (uart_getenv(devtype, di, class) == 0) ==== //depot/projects/uart/dev/uart/uart_cpu_i386.c#13 (text+ko) ==== @@ -53,6 +53,8 @@ unsigned int i, ivar; class = &uart_ns8250_class; + if (class == NULL) + return (ENXIO); /* Check the environment. */ if (uart_getenv(devtype, di, class) == 0) ==== //depot/projects/uart/dev/uart/uart_cpu_ia64.c#14 (text+ko) ==== @@ -65,6 +65,8 @@ unsigned int i; class = &uart_ns8250_class; + if (class == NULL) + return (ENXIO); /* * Use the DIG64 HCDP table if present. ==== //depot/projects/uart/dev/uart/uart_cpu_pc98.c#14 (text+ko) ==== @@ -53,6 +53,8 @@ unsigned int i, ivar, flags; class = &uart_ns8250_class; + if (class == NULL) + return (ENXIO); /* Check the environment. */ if (uart_getenv(devtype, di, class) == 0) ==== //depot/projects/uart/dev/uart/uart_cpu_powerpc.c#3 (text) ==== @@ -52,9 +52,14 @@ uart_cpu_getdev(int devtype, struct uart_devinfo *di) { char buf[64]; + struct uart_class *class; phandle_t input, opts; int error; + class = &uart_z8530_class; + if (class == NULL) + return (ENXIO); + if ((opts = OF_finddevice("/options")) == -1) return (ENXIO); switch (devtype) { @@ -93,7 +98,7 @@ if (error) return (error); - di->ops = uart_z8530_ops; + di->ops = uart_getops(class); di->bas.rclk = 230400; di->bas.chan = 1; ==== //depot/projects/uart/dev/uart/uart_subr.c#8 (text+ko) ==== @@ -48,6 +48,13 @@ #define UART_TAG_SB 8 #define UART_TAG_XO 9 +static struct uart_class *uart_classes[] = { + &uart_ns8250_class, + &uart_sab82532_class, + &uart_z8530_class, +}; +static size_t uart_nclasses = sizeof(uart_classes) / sizeof(uart_classes[0]); + static bus_addr_t uart_parse_addr(__const char **p) { @@ -57,6 +64,22 @@ static struct uart_class * uart_parse_class(struct uart_class *class, __const char **p) { + struct uart_class *uc; + const char *nm; + size_t len; + u_int i; + + for (i = 0; i < uart_nclasses; i++) { + uc = uart_classes[i]; + nm = uart_getname(uc); + if (nm == NULL || *nm == '\0') + continue; + len = strlen(nm); + if (strncmp(nm, *p, len) == 0) { + *p += len; + return (uc); + } + } return (class); } @@ -173,9 +196,12 @@ bus_addr_t addr = ~0U; int error; - /* We must get a valid default device class. */ + /* + * All uart_class references are weak. Make sure the default + * device class has been compiled-in. + */ if (class == NULL) - return (EDOOFUS); + return (ENXIO); /* * Check the environment variables "hw.uart.console" and