Subject: Re: fsl-esdhc on P2020 weird endianess behavior

From: Elie De Brauwer <[email-masked]>
Date: Mon, 24 Jan 2011 10:36:07 +0100

On 01/24/11 10:28, tiejun.chen wrote:
> Elie De Brauwer wrote:
>> On 01/24/11 09:15, tiejun.chen wrote:
>>> Elie De Brauwer wrote:
>>>> On 01/24/11 04:26, tiejun.chen wrote:
>>>>> Elie De Brauwer wrote:
>>>>>> Hello list,
>>>>>>
>>>>>> I have a P2020 processor on a custom board which uses the embedded
>>>>>> fsl-esdhc controller. Hardware-wise this is functional and in u-boot
>>>>>> everything seems to behave (mmc part 0 gives the correct partition
>>>>>> table
>>>>>> and ext2ls/fatls are capable of reading the contents of the sd card).
>>>>>>
>>>>>> However as soon as I start Linux (2.6.36), I get all sorts of unwanted
>>>>>> behavior. Linux is unable to detect the partition layout (but if I
>>>>>> do a
>>>>>
>>>>> Can you re-partition that under Linux? i.e, you can use fdisk to do
>>>>> this. Then
>>>>> I'm a bit curious what it'll be happened.
>>>>
>>>> This was already partitioned under (x86) Linux, and when I plug it into
>>>
>>> I means you should partition the disk on the PPC Linux, not x86. As
>>> you know x86
>>> work with LE for Linux, but PPC with BE. So I think you should
>>> partition that on
>>> the same type machine. Can you try it?
>>>
>>>> my laptop it sees the MBR (but also on target, in U-boot, the mmc part 0
>>>> command shows the correct partition table). And this does not explain
>>>
>>> I didn't check this implemented codes within u-boot. Maybe u-boot can do
>>> something to swap MMC ending problem. You can try to get the
>>> conclusion. Firstly
>>> you can re-partition that on PPC Linux then check if u-boot can
>>> identify it
>>> properly. I guess u-boot still can read that successfully.
>>>
>>
>> Unfortunately two wrongs don't make a right here. When I fdisk it on
>> target, then on target the partition gets detected, in u-boot it fails
>> (Unknown partition table). To be honest this was already the behavior
>> which I expected because the endianness swap was also seen for the card
>> registers. So I think something more fundamental is wrong (which in turn
>> smells like the "BIG_ENDIAN_32BIT_BYTE_SWAPPER" but this is used in a
>> very convincing way by the fsl-esdh driver...
>
> As you said looks you can disable 'MMC_SDHCI_BIG_ENDIAN_32BIT_BYTE_SWAPPER' from
> the Kconfig to rebuild Linux since its unnecessary for your target.
>

Well no, since this gets selected by the fsl-esdhc driver

config MMC_SDHCI_OF_ESDHC
         bool "SDHCI OF support for the Freescale eSDHC controller"
         depends on MMC_SDHCI_OF
         select MMC_SDHCI_BIG_ENDIAN_32BIT_BYTE_SWAPPER
         help
           This selects the Freescale eSDHC controller support.

           If unsure, say N.

And if you look in the sdhc-of.esdhc.c 
(http://lxr.linux.no/#linux+v2.6.37/drivers/mmc/host/sdhci-of-esdhc.c#L75 ) 
you can see that this driver is very stubborn in using the sdhci_be32bs* 
variants, so it just won't compile without the BYTE_SWAPPER set. But the 
entire sdhci_esdhc struct looks odd (for example they do byteswapping 
for the read_b but nog for the write_b, and it gets only done for the 
{read|write}_l.  I'll try using the 'regular' callbacks here instead of 
the byteswapped versions.

> Tiejun
>
>>
>>>
>>>> why the card registers (such as the scr pasted below) also seem to have
>>>> their endianess swapped, which will result in other side-effects, such
>>>> as improper reading of card capabilities.
>>>>
>>>>>
>>>>>> hexdump of the MBR, I see the endianness is swapped (last 4 bytes
>>>>>> are aa
>>>>>> 55 00 00). Also when I try to obtain the card registers they show the
>>>>>> same behavior:
>>>>>> # cat ./devices/soc.0/ff72e000.sdhci/mmc_host/mmc0/mmc0:0001/scr
>>>>>> 0000b50200000000
>>>>>>
>>>>>> While for comparison the same value on my (x86) laptop gives:
>>>>>> edb@lapedb:/sys/devices/pci0000:00/0000:00:1e.0/0000:15:00.2/mmc_host/mmc0/mmc0:0001$
>>>>>>
>>>>>>
>>>>>> cat scr
>>>>>> 02b5000000000000
>>>>>>
>>>>>> In my config I have the following set:
>>>>>> CONFIG_MMC_SDHCI=y
>>>>>> CONFIG_MMC_SDHCI_IO_ACCESSORS=y
>>>>>> CONFIG_MMC_SDHCI_BIG_ENDIAN_32BIT_BYTE_SWAPPER=y
>>>>>> # CONFIG_MMC_SDHCI_PCI is not set
>>>>>> CONFIG_MMC_SDHCI_OF=y
>>>>>> CONFIG_MMC_SDHCI_OF_ESDHC=y
>>>>>
>>>>> At least looks the config is fine.
>>>>>
>>>>> Tiejun
>>>>>
>>>>
>>>>
>>>
>>
>>
>

-- 
Elie De Brauwer