On 13/11/15 13:36, Siarhei Siamashka wrote:
> On Wed, 11 Nov 2015 18:26:54 +0100
> Jens Kuske <[email protected]> wrote:
>
>> Based on some guessing and comparing with the parts I initially started
>> disassembling (before this SDK appeared), I think it's I20. The I20 dram
>> init code matched the disassembled parts exactly, except the ZQ
>> calibration part...
>> So, looks like it might not be correct to assume I20 == H3.
>
> The magic constants in mctl_set_master_priority() seem to be a bit
> different too. This explains why I could not find the matching code
> in the SDK.
Indeed, didn't remember that.
>
>> This is the ZQ calibration function I got by disassembling, but I dropped
>> it since the SDK version worked well too. Maybe I should have done the
>> opposite and drop the SDK...
>
> Agreed, it's safer to prefer the variant of code that is actually
> used in production on real devices.
>
>> It looks a bit strange, like if they are always calibrating the
>> first channel and then copying to the others, maybe there is some
>> hardware bug they work around.
>>
>> static void mctl_zq_calibration(struct dram_para *para)
>> {
>> struct sunxi_mctl_ctl_reg * const mctl_ctl =
>> (struct sunxi_mctl_ctl_reg *)SUNXI_DRAM_CTL0_BASE;
>>
>> int i;
>> u16 zq_val[6];
>> u32 reg_val, val;
>>
>> mctl_dbg("ZQ calibration... ");
>>
>> writel(0x0a0a0a0a, &mctl_ctl->zqdr[2]);
>>
>> for (i = 0; i < 6; i++)
>> {
>> u8 zq = (CONFIG_DRAM_ZQ >> (i * 4)) & 0xf;
>>
>> writel((zq << 20) | (zq << 16) | (zq << 12) |
>> (zq << 8) | (zq << 4) | (zq << 0),
>> &mctl_ctl->zqcr);
>>
>> writel(PIR_CLRSR, &mctl_ctl->pir);
>> mctl_phy_init(PIR_ZCAL);
>>
>> val = readl(&mctl_ctl->zqdr[0]) & 0xff;
>> writel((val << 24) | (val << 16) | (val << 8) | (val << 0),
>> &mctl_ctl->zqdr[2]);
>>
>> writel(PIR_CLRSR, &mctl_ctl->pir);
>> mctl_phy_init(PIR_ZCAL);
>>
>> zq_val[i] = val |
>> (bin_to_mgray(mgray_to_bin(readl(&mctl_ctl->zqdr[0]) >> 24) - 1) << 8);
>> }
>>
>> writel((zq_val[1] << 16) | zq_val[0], &mctl_ctl->zqdr[0]);
>> writel((zq_val[3] << 16) | zq_val[2], &mctl_ctl->zqdr[1]);
>> writel((zq_val[5] << 16) | zq_val[4], &mctl_ctl->zqdr[2]);
>>
>> mctl_dbg((mctl_ctl->zqsr & (1 << 30)) ? "ERROR\n" : "DONE\n");
>> }
>
> Thanks, using this implementation fixes the reliability problems at
> 672MHz on my Orange Pi PC board.
Ok, I'll replace the SDK version then.
>
>> And while trying to figure out what's the reason for this I used the
>> following debug function, it might help you if you want to debug ZQ cal:
>>
>> static void dump_zq(void)
>> {
>> struct sunxi_mctl_ctl_reg * const mctl_ctl =
>> (struct sunxi_mctl_ctl_reg *)SUNXI_DRAM_CTL0_BASE;
>>
>> int i;
>> static const char *mod[3] = { "control", "DX0/DX1", "DX2/DX3" };
>> static const char *error[4] = { "\t", "overflow",
>> "underflow", "in progress" };
>>
>> printf("== ZQ calibration %s %s ==\n",
>> (mctl_ctl->zqsr & (1 << 31)) ? "DONE" : "",
>> (mctl_ctl->zqsr & (1 << 30)) ? "ERROR" : "");
>>
>> printf("\tODT pull-up\tODT pull-down\tDRV pull-up\tDRV pull-down\n");
>>
>> for (i = 0; i < 3; i++)
>> printf("%s\t%2u %s\t%2u %s\t%2u %s\t%2u %s\n", mod[i],
>> mgray_to_bin((mctl_ctl->zqdr[i] >> 24) & 0x1f),
>> error[(mctl_ctl->zqsr >> (i * 8 + 6)) & 0x3],
>> mgray_to_bin((mctl_ctl->zqdr[i] >> 16) & 0x1f),
>> error[(mctl_ctl->zqsr >> (i * 8 + 4)) & 0x3],
>> mgray_to_bin((mctl_ctl->zqdr[i] >> 8) & 0x1f),
>> error[(mctl_ctl->zqsr >> (i * 8 + 2)) & 0x3],
>> mgray_to_bin((mctl_ctl->zqdr[i] >> 0) & 0x1f),
>> error[(mctl_ctl->zqsr >> (i * 8 + 0)) & 0x3]);
>> }
>
> With your original code from github I get:
>
> == ZQ calibration DONE ERROR ==
> ODT pull-up ODT pull-down DRV pull-up DRV pull-down
> control 16 underflow 16 12 underflow 12
> DX0/DX1 12 underflow 12 12 underflow 12
> DX2/DX3 12 12 12 underflow 12
>
> With the implementation from your e-mail I get:
>
> == ZQ calibration DONE ==
> ODT pull-up ODT pull-down DRV pull-up DRV pull-down
> control 20 17 15 13
> DX0/DX1 6 5 15 13
> DX2/DX3 6 5 15 13
>
That looks *much* better :)
>
> I'm going to try running lima-memtester on the device and also will
> do a detailed review of your code by the end of the weekend. BTW, which
> boot0 binary did you use as a reference? It might help to make sure
> that we are actually looking at exactly the same thing.
If I remember correctly the libdram came from the SDK offered at the
orange pi downloads. I roughly compared it to the preinstalled android
boot0, it looked the same but had some symbols.
But I dropped most unused codepaths and tried to cleaned up a lot of magic.
>
> And regarding the patchset itself. There are no conflicts when rebasing
> it to v2015.10 and this newer version of U-Boot is preferable because
> it has better FEL boot support (automatic 'boot.scr' handling). Also it
> would be great to have these H3 patches posted to the U-Boot mailing
> list, preferably a week ago while the merge window was still open :-)
I have some more fixes waiting, but I think I can send them this weekend
(without regulator support).
Jens
--
You received this message because you are subscribed to the Google Groups
"linux-sunxi" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.