Module Name:    src
Committed By:   dyoung
Date:           Tue Aug 18 16:52:43 UTC 2009

Modified Files:
        src/sys/dev/isa: isa.c isadma.c isadmavar.h

Log Message:
Let us safely detach the ISA bus and devices attaching to the ISA
bus:

1 Add isadetach() for detaching the ISA bus, and add some helper
  routines that release resources held for ISA DMA.

2 In isachilddetached(), forget references to child devices.

While I am here, change ISA_DMA_DRQ_ISFREE(...) == 0 to the simpler
expression, !ISA_DMA_DRQ_ISFREE(...).


To generate a diff of this commit:
cvs rdiff -u -r1.135 -r1.136 src/sys/dev/isa/isa.c
cvs rdiff -u -r1.61 -r1.62 src/sys/dev/isa/isadma.c
cvs rdiff -u -r1.24 -r1.25 src/sys/dev/isa/isadmavar.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/dev/isa/isa.c
diff -u src/sys/dev/isa/isa.c:1.135 src/sys/dev/isa/isa.c:1.136
--- src/sys/dev/isa/isa.c:1.135	Tue Apr  7 21:48:46 2009
+++ src/sys/dev/isa/isa.c	Tue Aug 18 16:52:42 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: isa.c,v 1.135 2009/04/07 21:48:46 dyoung Exp $	*/
+/*	$NetBSD: isa.c,v 1.136 2009/08/18 16:52:42 dyoung Exp $	*/
 
 /*-
  * Copyright (c) 1998, 2001, 2008 The NetBSD Foundation, Inc.
@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: isa.c,v 1.135 2009/04/07 21:48:46 dyoung Exp $");
+__KERNEL_RCSID(0, "$NetBSD: isa.c,v 1.136 2009/08/18 16:52:42 dyoung Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -56,12 +56,13 @@
 
 int	isamatch(device_t, cfdata_t, void *);
 void	isaattach(device_t, device_t, void *);
+int	isadetach(device_t, int);
 int	isarescan(device_t, const char *, const int *);
 void	isachilddetached(device_t, device_t);
 int	isaprint(void *, const char *);
 
 CFATTACH_DECL2_NEW(isa, sizeof(struct isa_softc),
-    isamatch, isaattach, NULL, NULL, isarescan, isachilddetached);
+    isamatch, isaattach, isadetach, NULL, isarescan, isachilddetached);
 
 void	isa_attach_knowndevs(struct isa_softc *);
 void	isa_free_knowndevs(struct isa_softc *);
@@ -138,6 +139,27 @@
 }
 
 int
+isadetach(device_t self, int flags)
+{
+	struct isa_softc *sc = device_private(self);
+	int rc;
+
+	if ((rc = config_detach_children(self, flags)) != 0)
+		return rc;
+
+	pmf_device_deregister(self);
+
+	isa_free_knowndevs(sc);
+
+#if NISADMA > 0
+	isa_dmadestroy(sc->sc_ic);
+#endif
+	isa_detach_hook(self);
+
+	return 0;
+}
+
+int
 isarescan(device_t self, const char *ifattr, const int *locators)
 {
 	int locs[ISACF_NLOCS];
@@ -162,7 +184,13 @@
 void
 isachilddetached(device_t self, device_t child)
 {
-	/* nothing to do */
+	struct isa_knowndev *ik;
+	struct isa_softc *sc = device_private(self);
+
+	TAILQ_FOREACH(ik, &sc->sc_knowndevs, ik_list) {
+		if (ik->ik_claimed == child)
+			ik->ik_claimed = NULL;
+	}
 }
 
 void

Index: src/sys/dev/isa/isadma.c
diff -u src/sys/dev/isa/isadma.c:1.61 src/sys/dev/isa/isadma.c:1.62
--- src/sys/dev/isa/isadma.c:1.61	Tue May 12 09:10:15 2009
+++ src/sys/dev/isa/isadma.c	Tue Aug 18 16:52:42 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: isadma.c,v 1.61 2009/05/12 09:10:15 cegger Exp $	*/
+/*	$NetBSD: isadma.c,v 1.62 2009/08/18 16:52:42 dyoung Exp $	*/
 
 /*-
  * Copyright (c) 1997, 1998, 2000 The NetBSD Foundation, Inc.
@@ -35,7 +35,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: isadma.c,v 1.61 2009/05/12 09:10:15 cegger Exp $");
+__KERNEL_RCSID(0, "$NetBSD: isadma.c,v 1.62 2009/08/18 16:52:42 dyoung Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -201,6 +201,24 @@
 	}
 }
 
+void
+_isa_dmadestroy(struct isa_dma_state *ids)
+{
+	if (!ids->ids_initialized)
+		return;
+
+	_isa_dmacascade_stop(ids, 4);
+
+	/*
+	 * Unmap the registers used by the ISA DMA controller.
+	 */
+	bus_space_unmap(ids->ids_bst, ids->ids_dmapgh, 0xf);
+	bus_space_unmap(ids->ids_bst, ids->ids_dma2h, DMA2_IOSIZE);
+	bus_space_unmap(ids->ids_bst, ids->ids_dma1h, DMA1_IOSIZE);
+
+	ids->ids_initialized = 0;
+}
+
 /*
  * _isa_dmacascade(): program 8237 DMA controller channel to accept
  * external dma control by a board.
@@ -215,7 +233,7 @@
 		return (EINVAL);
 	}
 
-	if (ISA_DMA_DRQ_ISFREE(ids, chan) == 0) {
+	if (!ISA_DMA_DRQ_ISFREE(ids, chan)) {
 		printf("%s: DRQ %d is not free\n", device_xname(ids->ids_dev),
 		    chan);
 		return (EAGAIN);
@@ -235,10 +253,32 @@
 	return (0);
 }
 
+/*
+ * _isa_dmacascade_stop(): turn off cascading on the 8237 DMA controller channel
+ * external dma control by a board.
+ */
+int
+_isa_dmacascade_stop(struct isa_dma_state *ids, int chan)
+{
+	if (chan < 0 || chan > 7) {
+		printf("%s: bogus drq %d\n", device_xname(ids->ids_dev), chan);
+		return EINVAL;
+	}
+
+	if (ISA_DMA_DRQ_ISFREE(ids, chan))
+		return 0;
+
+	_isa_dmamask(ids, chan);
+
+	ISA_DMA_DRQ_FREE(ids, chan);
+
+	return 0;
+}
+
 int
 _isa_drq_alloc(struct isa_dma_state *ids, int chan)
 {
-	if (ISA_DMA_DRQ_ISFREE(ids, chan) == 0)
+	if (!ISA_DMA_DRQ_ISFREE(ids, chan))
 		return EBUSY;
 	ISA_DMA_DRQ_ALLOC(ids, chan);
 	return 0;

Index: src/sys/dev/isa/isadmavar.h
diff -u src/sys/dev/isa/isadmavar.h:1.24 src/sys/dev/isa/isadmavar.h:1.25
--- src/sys/dev/isa/isadmavar.h:1.24	Tue May 12 09:10:15 2009
+++ src/sys/dev/isa/isadmavar.h	Tue Aug 18 16:52:42 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: isadmavar.h,v 1.24 2009/05/12 09:10:15 cegger Exp $	*/
+/*	$NetBSD: isadmavar.h,v 1.25 2009/08/18 16:52:42 dyoung Exp $	*/
 
 /*-
  * Copyright (c) 1997, 1998, 2000 The NetBSD Foundation, Inc.
@@ -97,7 +97,10 @@
 void	   _isa_dmainit(struct isa_dma_state *, bus_space_tag_t,
 	       bus_dma_tag_t, device_t);
 
+void	   _isa_dmadestroy(struct isa_dma_state *);
+
 int	   _isa_dmacascade(struct isa_dma_state *, int);
+int	   _isa_dmacascade_stop(struct isa_dma_state *, int);
 
 bus_size_t _isa_dmamaxsize(struct isa_dma_state *, int);
 

Reply via email to