Subject: Re: Support for ARM9E
To: Scott <scott_allan@picovex.com>
From: Richard Earnshaw <Richard.Earnshaw@buzzard.freeserve.co.uk>
List: port-arm
Date: 07/27/2006 23:27:25
On Thu, 27 Jul 2006 15:08:02 PDT, Scott wrote:
> Hi all,
>
> The processor on my board is an ARM926EJ-S. NetBSD didn't have support for
> it, so I've gone ahead and added code for it. My understanding is that the
> ARM9E processors are ARMv5 like the ARM10 processors, and unlike the ARM9
> processors which are ARMv4. Because of that, I've added CPU_ARM9E and am
> basically just treating it for the most part as CPU_ARM10.
That all sounds pretty reasonable.
> This seems to be
> working just fine, but in doing this, I've ended up with a couple of curiosit
> ies.
>
> 1) I was having troubles if the cache buffering on my early MMU setup did not
>
> match the "real" MMU setup. In summary, if my early translation table
> entries' Buffering bit was not the same as the "real" translation table
> entries', I would end up jumping into lala land shortly after setting the
> "real" TTB.
>
Hmm, is your 'firmware' passing control to NetBSD with the MMU enabled?
For most ports that's considered to be a no-no, and in those cases the
first thing they do is turn the MMU off. It makes the bootstrap code
slower, but it then does work reliably.
> I finally figured out it was due to the way the setttb functions were written
>
> in cpufunc_asm_*.S. Here is the ARM10 code (but other ones are written in th
> e
> same way):
>
> ENTRY(arm10_setttb)
> stmfd sp!, {r0, lr}
> bl _C_LABEL(armv5_idcache_wbinv_all)
> ldmfd sp!, {r0, lr}
>
> mcr p15, 0, r0, c2, c0, 0 /* load new TTB */
>
> mcr p15, 0, r0, c8, c7, 0 /* invalidate I+D TLBs */
> RET
>
> The call to armv5_idcache_wbinv_all is trying to get the caches into a
> quiescent state for flipping the TTB, but the ldmfd to restore the registers
> is basically undoing some of that work. I was able to get it to work if I ad
> ded:
>
> mcr p15, 0, r0, c7, c7, 0 /* Invalidate I and D caches */
>
> after the ldmfd. It also worked if I reworked the idcache_wbinv_all function
>
> to use fewer registers and just stashed r0 and lr in r1 and r2. Which leads
> us to...
>
> 2) The ARM926EJ-S provides some nifty test and clean operations. From the TR
> M:
>
> ... use the following loop to clean the entire DCache:
> tc_loop: MRC p15, 0, r15, c7, c10, 3 ; test and clean
> BNE tc_loop
>
> and:
> ... use the following loop to clean and invalidate the entire DCache:
> tci_loop: MRC p15, 0, r15, c7, c14, 3 ; test clean and invalidate
> BNE tci_loop
>
> I checked the ARM1026EJ-S TRM and it supports these same operations. The
> question is, does anyone know why NetBSD loops over all the sets/ways instead
>
> of using the nifty operations?
That would be because the ARM1020E doesn't have those cache operations :-(
I thought I'd already added some support for the operations you mention,
but I can't find it in my tree here. Maybe it was at work.
R.