The original vendor's driver programmed the dma controller's
AHB HPROT values to enable bufferable, privileged mode. This
along with the "same priorty for both channels" fixes the
freezes according to @takimata, @And.short, that have been
reported on the forum by @ticerex.

Furtheremore, @takimata reported that the patch also improved
the performance of the HDDs considerably:
|<https://forum.lede-project.org/t/wd-mybook-live-duo-two-disks/16195/55>
|It seems your patch unleashed the full power of the SATA port.
|Where I was previously hitting a really hard limit at around
|82 MB/s for reading and 27 MB/s for writing, I am now getting this:
|
|root@OpenWrt:/mnt# time dd if=/dev/zero of=tempfile bs=1M count=1024
|1024+0 records in
|1024+0 records out
|real    0m 13.65s
|user    0m 0.01s
|sys     0m 11.89s
|
|root@OpenWrt:/mnt# time dd if=tempfile of=/dev/null bs=1M count=1024
|1024+0 records in
|1024+0 records out
|real    0m 8.41s
|user    0m 0.01s
|sys     0m 4.70s
|
|This means: 121 MB/s reading and 75 MB/s writing!
|
|[...]
|
|The drive is a WD Green WD10EARX taken from an older MBL Single.
|I repeated the test a few times with even larger files to rule out
|any caching, I'm still seeing the same great performance. OpenWrt is
|now completely on par with the original MBL firmware's performance.

Signed-off-by: Christian Lamparter <[email protected]>
---
 ...-dw-dma-hprot-fix-and-equal-priortiy.patch | 25 +++++++++++++++++++
 1 file changed, 25 insertions(+)
 create mode 100644 
target/linux/apm821xx/patches-4.14/302-dw-dma-hprot-fix-and-equal-priortiy.patch

diff --git 
a/target/linux/apm821xx/patches-4.14/302-dw-dma-hprot-fix-and-equal-priortiy.patch
 
b/target/linux/apm821xx/patches-4.14/302-dw-dma-hprot-fix-and-equal-priortiy.patch
new file mode 100644
index 0000000000..c6e4331aa9
--- /dev/null
+++ 
b/target/linux/apm821xx/patches-4.14/302-dw-dma-hprot-fix-and-equal-priortiy.patch
@@ -0,0 +1,25 @@
+--- a/drivers/dma/dw/core.c
++++ b/drivers/dma/dw/core.c
+@@ -167,6 +167,8 @@ static void dwc_initialize_chan_dw(struc
+       cfghi |= DWC_CFGH_DST_PER(dwc->dws.dst_id);
+       cfghi |= DWC_CFGH_SRC_PER(dwc->dws.src_id);
+ 
++      cfghi |= DWC_CFGH_PROTCTL(3); /* bufferable + privileged access */
++
+       /* Set polarity of handshake interface */
+       cfglo |= hs_polarity ? DWC_CFGL_HS_DST_POL | DWC_CFGL_HS_SRC_POL : 0;
+ 
+@@ -1293,11 +1295,8 @@ int dw_dma_probe(struct dw_dma_chip *chi
+               else
+                       list_add(&dwc->chan.device_node, &dw->dma.channels);
+ 
+-              /* 7 is highest priority & 0 is lowest. */
+-              if (pdata->chan_priority == CHAN_PRIORITY_ASCENDING)
+-                      dwc->priority = pdata->nr_channels - i - 1;
+-              else
+-                      dwc->priority = i;
++              /* set all channels to the same priority */
++              dwc->priority = pdata->nr_channels - 1;
+ 
+               dwc->ch_regs = &__dw_regs(dw)->CHAN[i];
+               spin_lock_init(&dwc->lock);
-- 
2.18.0


_______________________________________________
openwrt-devel mailing list
[email protected]
https://lists.openwrt.org/mailman/listinfo/openwrt-devel

Reply via email to