Post Go back to editing

DM0 and DM1 after reset in ADAU1450

Hi all,

A while ago, I posted a question about the state of the RAM registers in the ADAU1450 after reset: DM0 and DM1 RAM content after RESET ADAU1450 

Dave responded that RAM is initialized just before the core starts running. That's what I found later also in the datasheet (i overlooked it at first...). But I don't think that both are correct.

I use a microcontroller to program the ADAU1450 via an I2C bus. I use the output xml file, generated by SigmaStudio and write all registers mentioned in that xml file. But for DM0 and DM1 I do it a little different. Because I use a lot of RAM for delay, that registers are all filled with zero's. And, according to the answers I got, I do not need to write zero's, so I skipped doing that when programming the DSP.

But after releasing the hibernate state, the DSP is giving strange signals :-) So, to test my theory, I wrote all zero's to DM0 and DM1 in the range SigmaStudio wrote in the xml outputfile and then I write the non zero values. With that sequence, the DSP is working fine.... So my conclusion is that RAM isn't initialized, or at least not at the time I expect.

Maybe someone can shine some light here? That would be appreciated :-) My program is running fine now, but I could speed up the bootprocess when omitting writing the zero's to DM0 and DM1 at startup (I2C isn't very fast...). OK, I could switch to SPI, but that isn't an option, I use more I2C chips :-)

Addition: I found the following in the datasheet under paragraph "

POWER SUPPLIES, VOLTAGE REGULATOR, AND HARDWARE RESET"

"Hardware Reset

An active low hardware reset pin (RESET) is available for externally triggering a reset of the device. When this pin is tied to ground, all functional blocks in the device are disabled, and the current consumption decreases dramatically. The amount of current drawn depends on the leakage current of the silicon, which depends greatly on the ambient temperature and the properties of the die. When the RESET pin is connected to IOVDD, all control registers are reset to their power-on default values. The state of the RAM is not guaranteed to be cleared after a reset, so the memory must be manually cleared by the DSP program. The default program generated by SigmaStudio includes code that automatically clears the memory."
Hmm, I was sure I read somewhere else in the same datasheet that RAM is cleared, but I can't find it anymore... So maybe I have to clear the RAM registers myself...

Thanks again for all your input

With kind regards,

Reini

  • Hi Reini:

    I would have to double check but there is a chance that only DMO or DM1 are initialized before the program starts running. 

    Are you simply hibernating the DSP or restarting it to run it. This might also point to the problem.

    Please comment.

    Miguel

  • Hi Miguel,

    The dsp is coming from hard reset, but during startup, the core is placed in hibernation mode. I also found that I mixed two datasheets, the one of adau1701 and the one of adau1450 ...

    Thank you for your input!

    with kind regards,

    Reini

  • All of the DSP's memories are uninitialized after power-up. Buffers are zero-filled by the DSP program generated by SigmaStudio when it starts. Parameters are not, and have to be explicitly initialized during programming even if they are zero.

    Another thing I noticed is that reading uninitialized memory (or a memory location that's immediately followed by uninitialized memory) via SPI/I²C has a high probability of triggering a spurious parity error in the panic manager. For that reason I prefer to fill all memories completely during programming (but I use SPI, which is much faster than I²C).

    If you want to save programming time, after setting up the PLL upload and run this little program to zero-fill DM0 and DM1:

    00000002
    0880dcdc
    c0002830
    8000xxxx
    0c30dcdc
    01000008
    064c0000
    064c5040
    00000005
    00000000
    00000000
    02010008
    00000000
    00000000

    where xxxx in the fourth word should be the number of words per DM divided by 4, i.e. 0400 for the ADAU1450, 0800 for the ADAU1451, and 1400 for the ADAU1452. This program zero-fills memory at a rate of 4 words per core clock cycle and then halts. You can then upload your actual program without having to write zeros in DM0/DM1.

  • Reini wrote:

    I have one question though: your program should run after pll is setup, can you help me a bit indicating where to run your program in the execution flow, output from SigmaStudio? I follow the xml file, generated by SigmaStudio and think, the RAM clearing code should be programmed before the node <Program Data> in the xml output file.

    Correct.

    But do I have to set the START_CORE, KILL_CORE and HIBERNATE registers?

    After writing the program data and making sure START_ADDRESS is initialized to zero, a rising edge (0 → 1 transition) on START_CORE is needed to start the program. There should be no need to set KILL_CORE to zero since it's edge-triggered (but no harm in doing so either). The program doesn't use interrupts so the START_PULSE and HIBERNATE registers are irrelevant to it.

    Once the program is done filling memory (which takes about 8192 words / 4 words/cycle / 147 MHz = 14 microseconds) it will terminate itself, hence there should be no need to kill it afterwards using a rising edge on KILL_CORE (but no harm in doing so either). Then continue with the rest of the programming.

    Where did you find the information to generate your code?

    Magic :-)

    Unfortunately there's no public documentation on the Sigma300 instruction set.

    Matthijs

  • Note btw that no delay should be needed after starting the program, since it completes in less time than it takes to transfer even a single byte of data via I²C at 400 kHz.

  • Hello Matthijs,

    This is a very nice solution for me. We use lots of ram just for delay and these locations are initially always zero.

    I have one question though: your program should run after pll is setup, can you help me a bit indicating where to run your program in the executionflow, output from SigmaStudio? I follow the xml file, generated by SigmaStudio and think, the RAM clearing code should be programmed before the node <Program Data> in the xml output file. But do I have to set the START_CORE, KILL_CORE and HIBERNATE registers? In the xml file, these are set after writing Program and RAM data:

            <Program>
                <Name>Program Data</Name>
                <Address>49152</Address>
                <Size>4384</Size>

                <Data>0x00, 0x00, 0x00, 0x02 </Data>

           </Program>
            <Register>
                <Name>DM0 Data</Name>
                <Address>0</Address>
                <Size>9620</Size>

                <Data>0x00, 0x00, 0x00, 0x00 </Data>

            </Register>
            <Register>
                <Name>DM1 Data</Name>
                <Address>24576</Address>
                <Size>15760</Size>

                <Data>0x00, 0x00, 0x00, 0x00 </Data>

            </Register>
            <Register>
                <Name>IC 1.KILL_CORE</Name>
                <Address>62467</Address>
                <Size>2</Size>
                <Data>0x00, 0x00, </Data>
            </Register>
            <Register>
                <Name>IC 1.START_ADDRESS</Name>
                <Address>62468</Address>
                <Size>2</Size>
                <Data>0x00, 0x00, </Data>
            </Register>
            <Register>
                <Name>IC 1.START_PULSE</Name>
                <Address>62465</Address>
                <Size>2</Size>
                <Data>0x00, 0x02, </Data>
            </Register>
            <Register>
                <Name>IC 1.START_CORE</Name>
                <Address>62466</Address>
                <Size>2</Size>
                <Data>0x00, 0x00, </Data>
            </Register>
            <Register>
                <Name>IC 1.START_CORE</Name>
                <Address>62466</Address>
                <Size>2</Size>
                <Data>0x00, 0x01, </Data>
            </Register>
            <Register>
                <Name>IC 1.Start Delay</Name>
                <Address>0</Address>
                <Size>2</Size>
                <Data>0x00, 0x01, </Data>
            </Register>
            <Register>
                <Name>IC 1.HIBERNATE</Name>
                <Address>62464</Address>
                <Size>2</Size>
                <Data>0x00, 0x00, </Data>
            </Register>

    Am I right, to write your code when programming reaches the <Program/> node and then setting the START_CORE register to "1", the HIBERNATE register to "0", waiting is few millisecs to let the clear-code execute, stop the core again, setting HIBERNATE to "1" and resume "normal" programming with the xml code I inserted above?

    Where did you find the information to generate your code? Is it from a book? If I can find it myself, I won't have to bother you guys :-)

    Thank you very much for your input!

    With kind regards,

    Reini

  • Hey Matthijs,

    Thanks again :-) It's very clear and I will give it a try. This will save me quite a bit of time starting the DSP

    Kind regards,

    Reini

  • If you read the datasheet carefully

    ... then it says literally "This register is edge triggered", so if this is not true then it's not merely a matter of unclear wording, but it's plain wrong. Good to know though, thanks for mentioning this.

  • Hello,

    Great discussion.

    I want to add one small detail. I recently identified a small detail in the datasheet that will be changed soon. The Kill_Core command is not edge triggered. When it is high the core will be killed. So you must set it low to restart the core. If you read the datasheet carefully it says that the core will be killed on the transition from low to high. The distinction was between the Hibernate command that will take a short time before the core stops executing instructions where the Kill_Core will immediately kill the core. That is why it said on the low to high transition it will stop the core. I have changed that in the next revision of the datasheet.

    Hibernate simply stops the interrupts so that execution will stop after the current frame or after the current block if there is block processing in the program.

    Dave T.