Lines Matching +full:8 +full:- +full:ch
1 /*-
2 * Copyright (c) 2014-2016 Jared D. McNeill <jmcneill@invisible.ca>
52 #define NDMA_CHANNELS 8
53 #define DDMA_CHANNELS 8
83 { -1, 0 }
86 #define DMA_READ(sc, reg) bus_read_4((sc)->sc_res[0], (reg))
87 #define DMA_WRITE(sc, reg, val) bus_write_4((sc)->sc_res[0], (reg), (val))
88 #define DMACH_READ(ch, reg) \ argument
89 DMA_READ((ch)->ch_sc, (reg) + (ch)->ch_regoff)
90 #define DMACH_WRITE(ch, reg, val) \ argument
91 DMA_WRITE((ch)->ch_sc, (reg) + (ch)->ch_regoff, (val))
101 if (!ofw_bus_is_compatible(dev, "allwinner,sun4i-a10-dma")) in a10dmac_probe()
118 if (bus_alloc_resources(dev, a10dmac_spec, sc->sc_res)) { in a10dmac_attach()
123 mtx_init(&sc->sc_mtx, "a10 dmac", NULL, MTX_SPIN); in a10dmac_attach()
143 sc->sc_ndma_channels[index].ch_sc = sc; in a10dmac_attach()
144 sc->sc_ndma_channels[index].ch_index = index; in a10dmac_attach()
145 sc->sc_ndma_channels[index].ch_type = CH_NDMA; in a10dmac_attach()
146 sc->sc_ndma_channels[index].ch_callback = NULL; in a10dmac_attach()
147 sc->sc_ndma_channels[index].ch_callbackarg = NULL; in a10dmac_attach()
148 sc->sc_ndma_channels[index].ch_regoff = AWIN_NDMA_REG(index); in a10dmac_attach()
149 DMACH_WRITE(&sc->sc_ndma_channels[index], AWIN_NDMA_CTL_REG, 0); in a10dmac_attach()
152 sc->sc_ddma_channels[index].ch_sc = sc; in a10dmac_attach()
153 sc->sc_ddma_channels[index].ch_index = index; in a10dmac_attach()
154 sc->sc_ddma_channels[index].ch_type = CH_DDMA; in a10dmac_attach()
155 sc->sc_ddma_channels[index].ch_callback = NULL; in a10dmac_attach()
156 sc->sc_ddma_channels[index].ch_callbackarg = NULL; in a10dmac_attach()
157 sc->sc_ddma_channels[index].ch_regoff = AWIN_DDMA_REG(index); in a10dmac_attach()
158 DMACH_WRITE(&sc->sc_ddma_channels[index], AWIN_DDMA_CTL_REG, 0); in a10dmac_attach()
161 error = bus_setup_intr(dev, sc->sc_res[1], INTR_MPSAFE | INTR_TYPE_MISC, in a10dmac_attach()
162 NULL, a10dmac_intr, sc, &sc->sc_ih); in a10dmac_attach()
165 bus_release_resources(dev, a10dmac_spec, sc->sc_res); in a10dmac_attach()
166 mtx_destroy(&sc->sc_mtx); in a10dmac_attach()
185 mask = (1U << (bit - 1)); in a10dmac_intr()
191 * pending). The 8 normal DMA channel status are in the lower in a10dmac_intr()
192 * 16 bits and the 8 dedicated DMA channel status are in in a10dmac_intr()
193 * the upper 16 bits. The output is a channel number from 0-7. in a10dmac_intr()
195 index = ((bit - 1) / 2) & 7; in a10dmac_intr()
197 if (sc->sc_ndma_channels[index].ch_callback == NULL) in a10dmac_intr()
199 sc->sc_ndma_channels[index].ch_callback( in a10dmac_intr()
200 sc->sc_ndma_channels[index].ch_callbackarg); in a10dmac_intr()
202 if (sc->sc_ddma_channels[index].ch_callback == NULL) in a10dmac_intr()
204 sc->sc_ddma_channels[index].ch_callback( in a10dmac_intr()
205 sc->sc_ddma_channels[index].ch_callbackarg); in a10dmac_intr()
211 a10dmac_read_ctl(struct a10dmac_channel *ch) in a10dmac_read_ctl() argument
213 if (ch->ch_type == CH_NDMA) { in a10dmac_read_ctl()
214 return (DMACH_READ(ch, AWIN_NDMA_CTL_REG)); in a10dmac_read_ctl()
216 return (DMACH_READ(ch, AWIN_DDMA_CTL_REG)); in a10dmac_read_ctl()
221 a10dmac_write_ctl(struct a10dmac_channel *ch, uint32_t val) in a10dmac_write_ctl() argument
223 if (ch->ch_type == CH_NDMA) { in a10dmac_write_ctl()
224 DMACH_WRITE(ch, AWIN_NDMA_CTL_REG, val); in a10dmac_write_ctl()
226 DMACH_WRITE(ch, AWIN_DDMA_CTL_REG, val); in a10dmac_write_ctl()
233 struct a10dmac_channel *ch = priv; in a10dmac_set_config() local
238 switch (cfg->dst_width) { in a10dmac_set_config()
239 case 8: in a10dmac_set_config()
251 switch (cfg->dst_burst_len) { in a10dmac_set_config()
258 case 8: in a10dmac_set_config()
264 switch (cfg->src_width) { in a10dmac_set_config()
265 case 8: in a10dmac_set_config()
277 switch (cfg->src_burst_len) { in a10dmac_set_config()
284 case 8: in a10dmac_set_config()
293 (cfg->dst_drqtype << AWIN_DMA_CTL_DST_DRQ_TYPE_SHIFT) | in a10dmac_set_config()
296 (cfg->src_drqtype << AWIN_DMA_CTL_SRC_DRQ_TYPE_SHIFT); in a10dmac_set_config()
298 if (ch->ch_type == CH_NDMA) { in a10dmac_set_config()
299 if (cfg->dst_noincr) in a10dmac_set_config()
301 if (cfg->src_noincr) in a10dmac_set_config()
304 DMACH_WRITE(ch, AWIN_NDMA_CTL_REG, val); in a10dmac_set_config()
306 dst_am = cfg->dst_noincr ? AWIN_DDMA_CTL_DMA_ADDR_IO : in a10dmac_set_config()
308 src_am = cfg->src_noincr ? AWIN_DDMA_CTL_DMA_ADDR_IO : in a10dmac_set_config()
314 DMACH_WRITE(ch, AWIN_DDMA_CTL_REG, val); in a10dmac_set_config()
316 dst_bs = cfg->dst_blksize - 1; in a10dmac_set_config()
317 dst_wc = cfg->dst_wait_cyc - 1; in a10dmac_set_config()
318 src_bs = cfg->src_blksize - 1; in a10dmac_set_config()
319 src_wc = cfg->src_wait_cyc - 1; in a10dmac_set_config()
321 DMACH_WRITE(ch, AWIN_DDMA_PARA_REG, in a10dmac_set_config()
336 struct a10dmac_channel *ch = NULL; in a10dmac_alloc() local
341 ch_list = sc->sc_ddma_channels; in a10dmac_alloc()
344 ch_list = sc->sc_ndma_channels; in a10dmac_alloc()
348 mtx_lock_spin(&sc->sc_mtx); in a10dmac_alloc()
351 ch = &ch_list[index]; in a10dmac_alloc()
352 ch->ch_callback = cb; in a10dmac_alloc()
353 ch->ch_callbackarg = cbarg; in a10dmac_alloc()
356 if (ch->ch_type == CH_NDMA) in a10dmac_alloc()
365 mtx_unlock_spin(&sc->sc_mtx); in a10dmac_alloc()
367 return (ch); in a10dmac_alloc()
373 struct a10dmac_channel *ch = priv; in a10dmac_free() local
374 struct a10dmac_softc *sc = ch->ch_sc; in a10dmac_free()
377 mtx_lock_spin(&sc->sc_mtx); in a10dmac_free()
380 cfg = a10dmac_read_ctl(ch); in a10dmac_free()
381 if (ch->ch_type == CH_NDMA) { in a10dmac_free()
382 sta = AWIN_DMA_IRQ_NDMA_END(ch->ch_index); in a10dmac_free()
385 sta = AWIN_DMA_IRQ_DDMA_END(ch->ch_index); in a10dmac_free()
389 a10dmac_write_ctl(ch, cfg); in a10dmac_free()
393 ch->ch_callback = NULL; in a10dmac_free()
394 ch->ch_callbackarg = NULL; in a10dmac_free()
396 mtx_unlock_spin(&sc->sc_mtx); in a10dmac_free()
403 struct a10dmac_channel *ch = priv; in a10dmac_transfer() local
406 cfg = a10dmac_read_ctl(ch); in a10dmac_transfer()
407 if (ch->ch_type == CH_NDMA) { in a10dmac_transfer()
411 DMACH_WRITE(ch, AWIN_NDMA_SRC_ADDR_REG, src); in a10dmac_transfer()
412 DMACH_WRITE(ch, AWIN_NDMA_DEST_ADDR_REG, dst); in a10dmac_transfer()
413 DMACH_WRITE(ch, AWIN_NDMA_BC_REG, nbytes); in a10dmac_transfer()
416 a10dmac_write_ctl(ch, cfg); in a10dmac_transfer()
421 DMACH_WRITE(ch, AWIN_DDMA_SRC_START_ADDR_REG, src); in a10dmac_transfer()
422 DMACH_WRITE(ch, AWIN_DDMA_DEST_START_ADDR_REG, dst); in a10dmac_transfer()
423 DMACH_WRITE(ch, AWIN_DDMA_BC_REG, nbytes); in a10dmac_transfer()
426 a10dmac_write_ctl(ch, cfg); in a10dmac_transfer()
435 struct a10dmac_channel *ch = priv; in a10dmac_halt() local
438 cfg = a10dmac_read_ctl(ch); in a10dmac_halt()
439 if (ch->ch_type == CH_NDMA) { in a10dmac_halt()
444 a10dmac_write_ctl(ch, cfg); in a10dmac_halt()