1
\$\begingroup\$

I'm using an ATxmega64A3U, I've connected a 4MHz external crystal and two 18pF load caps. I'm using the ASF module for clock configuration, however when starting up I can see that the code hangs in the following spot:

static inline void osc_wait_ready(uint8_t id)
{
    while (!osc_is_ready(id)) {
        /* Do nothing */
    }
}

The while waits for the clock source to stabilize but that never happens. Does anyone have any suggestions why this could be?

Addition

The code I've posted above is from the ASF, to make sure I know what I'm executing I wrote the following code and could see that the code gets stuck in the while loop that waits for the oscillator to stabilize.

OSC_CTRL |= OSC_XOSCEN_bm;
while(!(OSC_STATUS & OSC_XOSCRDY_bm));
CCP = CCP_IOREG_gc;
CLK_CTRL = (CLK_CTRL & ~CLK_SCLKSEL_gm) | CLK_SCLKSEL_XOSC_gc;
OSC_CTRL &= ~OSC_RC2MEN_bm;

I enable the external oscillator, wait for it to get stable, disable lock on register, switch over to external oscillator, disable internal 2MHz oscillator.

\$\endgroup\$
  • \$\begingroup\$ How do you call the function? Is "id" valid? \$\endgroup\$ – Kevin White Feb 20 '17 at 0:53
  • \$\begingroup\$ @KevinWhite Code is form ASF, should be fine. I added my own code to the original question. It gets gets stuck in the same place. \$\endgroup\$ – user34920 Feb 20 '17 at 13:04
  • \$\begingroup\$ Not that its really relevant, but wasn't there some kind of internal RC oscillator fallback mode in case the external crystal won't start properly? I am just wondering that it "just hangs". But its been w while since I used that. \$\endgroup\$ – Rev1.0 Feb 20 '17 at 13:14
  • \$\begingroup\$ @Rev1.0 well there is a safety fall-back, however you need to enable it at the XOSCFAIL register. I did not. \$\endgroup\$ – user34920 Feb 20 '17 at 13:24
1
\$\begingroup\$

Note that 18pF load capacitance from the data sheet does not mean to put two 18pF capacitors on the board.

Its the total capacitance the crystal should "see". Assuming a stray capacitance of 5pF, you would have

Cl = (18pF*18pF)/(36pF) + 5pF = 14pF

You may want to try something like 24pF for the load capacitors.

Furthermore, the ESR of the crystal you choose it pretty high. This may become an issue if the oscillator circuit cannot adequately drive the crystal.

Higher frequency crystal tend to have lower ESR, so try a crystal with 8 or 16MHz from that series.

\$\endgroup\$
  • \$\begingroup\$ I actually know that you have added capacitance from the tracks, however being off by a bit should affect the operation freq. of the oscillator not the stability AFAIK. However you did say something that I've missed, the fact that higher freq. crystals have lower ESR which might explain why the board is having a hard time driving this one! I think I can unlock the xmega to supply more current to the circuit and perhaps that might help here. Thanks! \$\endgroup\$ – user34920 Feb 20 '17 at 14:13
0
\$\begingroup\$

Place the scope probe, insulated by a dollar bill (thickness is 3 mils, or 1/11mm), against oscillator's Output Node (biggest but distorted voltage). This implements a voltage divider scope-probe, with little additional C on the XTAL+PI capacitors, so any amplitude should be unchanged. The capacitance through the bill's paper is $$C = E0*Er*Area/Distance$$ $$C = 9*10^-12 * 2 (cotton paper) * (1mm * 1mm scope tip area)/0.075mm$$ $$C ~ 2*10^-11 * 0.013 = 0.26pF$$

If your scope probe, in 10X mode, is 13pF, you have a 50:1 divider.

Put the scope on 20mV/division, and your real sensitivity is 1volt/division. With only 0.26pF Cload onto the oscillator.

Examine the two XTAL pins. Find healthy 1vpp, 2vpp, 3vpp signals? at 4.000MHz?

For fun, check out other MCU oscillators, for amplitude and sin-ness and distortion?

Barkhausen gives us 2 requirements for successful oscillation:

(1) voltage gain > 1

(2) EXACTLY ------- exactly ------- N*360 degrees phaseshift.

Some crystal oscillators only achieve EXACTLY N*360 degrees, with some resistance from Vout pin to the PI_network capacitor. Try 100_ohm or 1,000_ohm.

\$\endgroup\$
0
\$\begingroup\$

So it turned out to be a software issue! Turned out that there is also need to set the amount of cycles the AVR waits for the oscillator to become stable. I did not set this which obviously caused some kind of trouble. Here is the updated code which waits 16k cycles because I don't need a fast wake-up and that's about 4ms.

OSC_XOSCCTRL = ((OSC_XOSCCTRL & ~OSC_FRQRANGE_gm) | OSC_FRQRANGE_2TO9_gc) |
               ((OSC_XOSCCTRL & ~OSC_XOSCSEL_gm) | OSC_XOSCSEL3_bm | OSC_XOSCSEL1_bm | OSC_XOSCSEL0_bm);
OSC_CTRL |= OSC_XOSCEN_bm;
while(!(OSC_STATUS & OSC_XOSCRDY_bm));
CCP = CCP_IOREG_gc;
CLK_CTRL = (CLK_CTRL & ~CLK_SCLKSEL_gm) | CLK_SCLKSEL_XOSC_gc;
OSC_CTRL &= ~OSC_RC2MEN_bm;
\$\endgroup\$
  • \$\begingroup\$ If available, you should use a scope to check start-up time and waveform anyway. If it stabilizes only after say 15k cycles, the "next" crystal might not work properly due to slightly different characteristics. \$\endgroup\$ – Rev1.0 Feb 20 '17 at 16:04
  • \$\begingroup\$ @Rev1.0 That is true. For the next build I will be using a higher freq. Xtal and divide it down. \$\endgroup\$ – user34920 Feb 20 '17 at 16:34

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.