Message ID | 200909072238.19736.sshtylyov@ru.mvista.com (mailing list archive) |
---|---|
State | Changes Requested |
Headers | show |
Sergei Shtylyov <sshtylyov@ru.mvista.com> writes: > Add the function to initialize the CPPI 4.1 subsystem along with the data > describing CPPI 4.1 queue manager and DMA block found in DA8xx chips. > > Modify USB 2.0 clock entry to have the clock enabled early if we have > CPPI 4.1 subsystem enabled. > > Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com> > > --- > The patch is against the recent DaVinci tree. > > arch/arm/mach-davinci/da830.c | 4 + > arch/arm/mach-davinci/devices-da8xx.c | 95 +++++++++++++++++++++++++++++ > arch/arm/mach-davinci/include/mach/da8xx.h | 6 + > 3 files changed, 105 insertions(+) > > Index: linux-davinci/arch/arm/mach-davinci/da830.c > =================================================================== > --- linux-davinci.orig/arch/arm/mach-davinci/da830.c > +++ linux-davinci/arch/arm/mach-davinci/da830.c > @@ -305,6 +305,10 @@ static struct clk usb20_clk = { > .parent = &pll0_sysclk2, > .lpsc = DA8XX_LPSC1_USB20, > .psc_ctlr = 1, > +#ifdef CONFIG_CPPI41 > + /* CPPI 4.1 is clocked by USB 2.0 clock */ > + .flags = ALWAYS_ENABLED, > +#endif Don't like this. If CPP4.1 is clocked by USB2.0 clock, it should do a clk_get()/clk_enable() on it. If you can't use clk_enable() there should be detailed description as to why. > }; > > static struct clk aemif_clk = { > Index: linux-davinci/arch/arm/mach-davinci/devices-da8xx.c > =================================================================== > --- linux-davinci.orig/arch/arm/mach-davinci/devices-da8xx.c > +++ linux-davinci/arch/arm/mach-davinci/devices-da8xx.c > @@ -20,6 +20,7 @@ > #include <mach/cputype.h> > #include <mach/common.h> > #include <mach/time.h> > +#include <mach/cppi41.h> > #include <mach/da8xx.h> > #include <video/da8xx-fb.h> > > @@ -448,3 +449,97 @@ int __init da8xx_register_mmcsd0(struct > da8xx_mmcsd0_device.dev.platform_data = config; > return platform_device_register(&da8xx_mmcsd0_device); > } > + > +#ifdef CONFIG_CPPI41 > + > +static const struct cppi41_tx_ch tx_ch_info[] = { > + [0] = { > + .port_num = 1, > + .num_tx_queue = 2, > + .tx_queue = { { 0, 16 }, { 0, 17 } } > + }, > + [1] = { > + .port_num = 2, > + .num_tx_queue = 2, > + .tx_queue = { { 0, 18 }, { 0, 19 } } > + }, > + [2] = { > + .port_num = 3, > + .num_tx_queue = 2, > + .tx_queue = { { 0, 20 }, { 0, 21 } } > + }, > + [3] = { > + .port_num = 4, > + .num_tx_queue = 2, > + .tx_queue = { { 0, 22 }, { 0, 23 } } > + } > +}; > + > +/* DMA block configuration */ > +const struct cppi41_dma_block cppi41_dma_block[1] = { > + [0] = { > + .global_ctrl_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x1000), > + .ch_ctrl_stat_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x1800), > + .sched_ctrl_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x2000), > + .sched_table_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x2800), > + .num_tx_ch = 4, > + .num_rx_ch = 4, > + .tx_ch_info = tx_ch_info > + } > +}; > +EXPORT_SYMBOL(cppi41_dma_block); > + > +/* Queues 0 to 27 are pre-assigned, others are spare */ > +static const u32 assigned_queues[] = { 0x0fffffff, 0 }; > + > +/* Queue manager information */ > +const struct cppi41_queue_mgr cppi41_queue_mgr[1] = { > + [0] = { > + .q_mgr_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x4000), > + .desc_mem_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x5000), > + .q_mgmt_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x6000), > + .q_stat_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x6800), > + > + .num_queue = 64, > + .queue_types = CPPI41_FREE_DESC_BUF_QUEUE | > + CPPI41_UNASSIGNED_QUEUE, > + .base_fdbq_num = 0, > + .assigned = assigned_queues > + } > +}; > + > +const u8 cppi41_num_queue_mgr = 1; > +const u8 cppi41_num_dma_block = 1; > + > +/* Fair DMA scheduling */ > +static const u8 dma_sched_table[] = { > + 0x00, 0x80, 0x01, 0x81, 0x02, 0x82, 0x03, 0x83 > +}; > + > +int __init da8xx_cppi41_init(void) > +{ > + int ret; > + > + ret = cppi41_queue_mgr_init(0, 0, 0); > + if (ret) { > + pr_warning("%s: queue manager initialization failed: %d\n", > + __func__, ret); > + return ret; > + } > + > + ret = cppi41_dma_ctrlr_init(0, 0, 5); > + if (ret) { > + pr_warning("%s: DMA controller initialization failed: %d\n", > + __func__, ret); > + return ret; > + } > + > + ret = cppi41_dma_sched_init(0, dma_sched_table, > + sizeof(dma_sched_table)); > + if (ret) > + printk("%s: DMA scheduler initialization failed: %d\n", > + __func__, ret); checkpatch: WARNING: printk() should include KERN_ facility level I assume you wanted pr_warning() here too. > + return ret; > +} > + > +#endif /* CONFIG_CPPI41 */ > Index: linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h > =================================================================== > --- linux-davinci.orig/arch/arm/mach-davinci/include/mach/da8xx.h > +++ linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h > @@ -68,6 +68,12 @@ > void __init da830_init(void); > void __init da850_init(void); > > +#ifdef CONFIG_CPPI41 > +int da8xx_cppi41_init(void); > +#else > +static int da8xx_cppi41_init(void) { return 0; } > +#endif > + Minor nit, but I'd rather these kinds of init function #ifdefs in the C-code and not the header. > int da8xx_register_edma(void); > int da8xx_register_i2c(int instance, struct davinci_i2c_platform_data *pdata); > int da8xx_register_watchdog(void); Kevin
Hello. Kevin Hilman wrote: >>Add the function to initialize the CPPI 4.1 subsystem along with the data >>describing CPPI 4.1 queue manager and DMA block found in DA8xx chips. >>Modify USB 2.0 clock entry to have the clock enabled early if we have >>CPPI 4.1 subsystem enabled. >>Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com> >>--- >>The patch is against the recent DaVinci tree. >> arch/arm/mach-davinci/da830.c | 4 + >> arch/arm/mach-davinci/devices-da8xx.c | 95 +++++++++++++++++++++++++++++ >> arch/arm/mach-davinci/include/mach/da8xx.h | 6 + >> 3 files changed, 105 insertions(+) >>Index: linux-davinci/arch/arm/mach-davinci/da830.c >>=================================================================== >>--- linux-davinci.orig/arch/arm/mach-davinci/da830.c >>+++ linux-davinci/arch/arm/mach-davinci/da830.c >>@@ -305,6 +305,10 @@ static struct clk usb20_clk = { >> .parent = &pll0_sysclk2, >> .lpsc = DA8XX_LPSC1_USB20, >> .psc_ctlr = 1, >>+#ifdef CONFIG_CPPI41 >>+ /* CPPI 4.1 is clocked by USB 2.0 clock */ >>+ .flags = ALWAYS_ENABLED, >>+#endif > Don't like this. If CPP4.1 is clocked by USB2.0 clock, It's a just part of the USB 2.0 module in this case. > it should do a Like it or not -- I'm doing essentially the same as what EDMA does. :-) > clk_get()/clk_enable() on it. If you can't use clk_enable() there > should be detailed description as to why. I think I can -- the same as EDMA could. :-) >>Index: linux-davinci/arch/arm/mach-davinci/devices-da8xx.c >>=================================================================== >>--- linux-davinci.orig/arch/arm/mach-davinci/devices-da8xx.c >>+++ linux-davinci/arch/arm/mach-davinci/devices-da8xx.c [...] >>+int __init da8xx_cppi41_init(void) >>+{ >>+ int ret; >>+ >>+ ret = cppi41_queue_mgr_init(0, 0, 0); >>+ if (ret) { >>+ pr_warning("%s: queue manager initialization failed: %d\n", >>+ __func__, ret); >>+ return ret; >>+ } >>+ >>+ ret = cppi41_dma_ctrlr_init(0, 0, 5); >>+ if (ret) { >>+ pr_warning("%s: DMA controller initialization failed: %d\n", >>+ __func__, ret); >>+ return ret; >>+ } >>+ >>+ ret = cppi41_dma_sched_init(0, dma_sched_table, >>+ sizeof(dma_sched_table)); >>+ if (ret) >>+ printk("%s: DMA scheduler initialization failed: %d\n", >>+ __func__, ret); > checkpatch: WARNING: printk() should include KERN_ facility level > I assume you wanted pr_warning() here too. Sure, just managed to overlook this... :-/ >>Index: linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h >>=================================================================== >>--- linux-davinci.orig/arch/arm/mach-davinci/include/mach/da8xx.h >>+++ linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h >>@@ -68,6 +68,12 @@ >> void __init da830_init(void); >> void __init da850_init(void); >> >>+#ifdef CONFIG_CPPI41 >>+int da8xx_cppi41_init(void); >>+#else >>+static int da8xx_cppi41_init(void) { return 0; } >>+#endif >>+ > Minor nit, but I'd rather these kinds of init function #ifdefs in the > C-code and not the header. OK... >> int da8xx_register_edma(void); >> int da8xx_register_i2c(int instance, struct davinci_i2c_platform_data *pdata); >> int da8xx_register_watchdog(void); > Kevin WBR, Sergei
Index: linux-davinci/arch/arm/mach-davinci/da830.c =================================================================== --- linux-davinci.orig/arch/arm/mach-davinci/da830.c +++ linux-davinci/arch/arm/mach-davinci/da830.c @@ -305,6 +305,10 @@ static struct clk usb20_clk = { .parent = &pll0_sysclk2, .lpsc = DA8XX_LPSC1_USB20, .psc_ctlr = 1, +#ifdef CONFIG_CPPI41 + /* CPPI 4.1 is clocked by USB 2.0 clock */ + .flags = ALWAYS_ENABLED, +#endif }; static struct clk aemif_clk = { Index: linux-davinci/arch/arm/mach-davinci/devices-da8xx.c =================================================================== --- linux-davinci.orig/arch/arm/mach-davinci/devices-da8xx.c +++ linux-davinci/arch/arm/mach-davinci/devices-da8xx.c @@ -20,6 +20,7 @@ #include <mach/cputype.h> #include <mach/common.h> #include <mach/time.h> +#include <mach/cppi41.h> #include <mach/da8xx.h> #include <video/da8xx-fb.h> @@ -448,3 +449,97 @@ int __init da8xx_register_mmcsd0(struct da8xx_mmcsd0_device.dev.platform_data = config; return platform_device_register(&da8xx_mmcsd0_device); } + +#ifdef CONFIG_CPPI41 + +static const struct cppi41_tx_ch tx_ch_info[] = { + [0] = { + .port_num = 1, + .num_tx_queue = 2, + .tx_queue = { { 0, 16 }, { 0, 17 } } + }, + [1] = { + .port_num = 2, + .num_tx_queue = 2, + .tx_queue = { { 0, 18 }, { 0, 19 } } + }, + [2] = { + .port_num = 3, + .num_tx_queue = 2, + .tx_queue = { { 0, 20 }, { 0, 21 } } + }, + [3] = { + .port_num = 4, + .num_tx_queue = 2, + .tx_queue = { { 0, 22 }, { 0, 23 } } + } +}; + +/* DMA block configuration */ +const struct cppi41_dma_block cppi41_dma_block[1] = { + [0] = { + .global_ctrl_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x1000), + .ch_ctrl_stat_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x1800), + .sched_ctrl_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x2000), + .sched_table_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x2800), + .num_tx_ch = 4, + .num_rx_ch = 4, + .tx_ch_info = tx_ch_info + } +}; +EXPORT_SYMBOL(cppi41_dma_block); + +/* Queues 0 to 27 are pre-assigned, others are spare */ +static const u32 assigned_queues[] = { 0x0fffffff, 0 }; + +/* Queue manager information */ +const struct cppi41_queue_mgr cppi41_queue_mgr[1] = { + [0] = { + .q_mgr_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x4000), + .desc_mem_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x5000), + .q_mgmt_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x6000), + .q_stat_rgn_base = IO_ADDRESS(DA8XX_USB0_BASE + 0x6800), + + .num_queue = 64, + .queue_types = CPPI41_FREE_DESC_BUF_QUEUE | + CPPI41_UNASSIGNED_QUEUE, + .base_fdbq_num = 0, + .assigned = assigned_queues + } +}; + +const u8 cppi41_num_queue_mgr = 1; +const u8 cppi41_num_dma_block = 1; + +/* Fair DMA scheduling */ +static const u8 dma_sched_table[] = { + 0x00, 0x80, 0x01, 0x81, 0x02, 0x82, 0x03, 0x83 +}; + +int __init da8xx_cppi41_init(void) +{ + int ret; + + ret = cppi41_queue_mgr_init(0, 0, 0); + if (ret) { + pr_warning("%s: queue manager initialization failed: %d\n", + __func__, ret); + return ret; + } + + ret = cppi41_dma_ctrlr_init(0, 0, 5); + if (ret) { + pr_warning("%s: DMA controller initialization failed: %d\n", + __func__, ret); + return ret; + } + + ret = cppi41_dma_sched_init(0, dma_sched_table, + sizeof(dma_sched_table)); + if (ret) + printk("%s: DMA scheduler initialization failed: %d\n", + __func__, ret); + return ret; +} + +#endif /* CONFIG_CPPI41 */ Index: linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h =================================================================== --- linux-davinci.orig/arch/arm/mach-davinci/include/mach/da8xx.h +++ linux-davinci/arch/arm/mach-davinci/include/mach/da8xx.h @@ -68,6 +68,12 @@ void __init da830_init(void); void __init da850_init(void); +#ifdef CONFIG_CPPI41 +int da8xx_cppi41_init(void); +#else +static int da8xx_cppi41_init(void) { return 0; } +#endif + int da8xx_register_edma(void); int da8xx_register_i2c(int instance, struct davinci_i2c_platform_data *pdata); int da8xx_register_watchdog(void);
Add the function to initialize the CPPI 4.1 subsystem along with the data describing CPPI 4.1 queue manager and DMA block found in DA8xx chips. Modify USB 2.0 clock entry to have the clock enabled early if we have CPPI 4.1 subsystem enabled. Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com> --- The patch is against the recent DaVinci tree. arch/arm/mach-davinci/da830.c | 4 + arch/arm/mach-davinci/devices-da8xx.c | 95 +++++++++++++++++++++++++++++ arch/arm/mach-davinci/include/mach/da8xx.h | 6 + 3 files changed, 105 insertions(+)