Did my crystal fail?

Go To Last Post
32 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I wrote this code

/*
 * DisplayTest.cpp
 *
 * Created: 21.1.2016. 21:17:01
 *  Author: Zvoc47
 */ 

#include <avr/io.h>
#define F_CPU 32768000
#include <util/delay.h>

int main(void)
{
	PORTQ_DIRSET=0b00001000;
    while(1)
    {
		PORTQ_OUTTGL=0b00001000;
		_delay_ms(500);
        //TODO:: Please write your application code
    }
}

for my XMEGA A1U Xplained Pro board. This time without ASF. I just wanted to check if the timing is correct.

 

The LED blinks after 8 seconds instead of half a second. If the crystal fails, the frequency of the CPU goes to 2MHz. The board has a 32Mhz crystal. If this calculation is correct: 32/2[MHz]=8000/500 ... then it seems that something has happened to my crystal! I wonder how do I fix this. Is it maybe the clock settings that are problematic?

 

* Moved to XMega forum *

 

Last Edited: Fri. Jan 22, 2016 - 04:25 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'm not an Xmega person.  [perhaps a moderator will move to that forum?]  But don't you have to select your clock source in an Xmega program?  My app has a fairly extensive "system_clocks_init()" that goes through all the clock sources per the needs of the app.

 

 

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'm trying to not use ASF because of licensing issues. I want to only use AVRlibc and copycenter licensed libraries. Do you use functions that are from ASF or AVRlibc?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Not an Xmega person (yet) but....

 

I recall that the manual (don't ask me which one) has a fairly detailed listing of the coded needed. No libraries involved, as I recall.

 

Jim

Jim Wagner Oregon Research Electronics, Consulting Div. Tangent, OR, USA http://www.orelectronics.net

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The LED blinks after 8 seconds instead of half a second.

You don't have any code to enable the 32MHz clock therefore the chip runs at the 2MHz default.

John Samperi

Ampertronics Pty. Ltd.

www.ampertronics.com.au

* Electronic Design * Custom Products * Contract Assembly

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I can't see a problem using the ASF functions to set the clock - they only work on an AVR. You wouldn't port those functions to another cpu.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I found some code for 32MHz but my board has a 8MHz crystal

// Set clock to 32 MHz with 8MHz external crystal

//	OSC_XOSCCTRL = (OSC_FRQRANGE_2TO9_gc | OSC_XOSCSEL_XTAL_16KCLK_gc);	// 2-9MHz with 16Kcycles
//	OSC_CTRL |= OSC_XOSCEN_bm | OSC_PLLEN_bm;
//	OSC_PLLCTRL = 16;	//(1<<OSC_PLLSRC1_bp | 1<<OSC_PLLSRC0_bp);	// PLL clock source EXT and mult. factor ( 8MHzx4=32MHz)

//	while (!(OSC_STATUS & (1<<OSC_XOSCRDY_bp)));	// Wait for crystal clock ready.

	OSC_PLLCTRL = 16;	// PLL clock source EXT and mult. factor ( 8MHzx4=32MHz)
	OSC_CTRL = (1<<OSC_PLLEN_bp);		// Enable PLL
	while (!(OSC_STATUS & (1<<OSC_PLLRDY_bp)));

	CPU_CCP = CCP_IOREG_gc;				// Unlock sequence to access CLK_CTRL
	CLK_CTRL = CLK_SCLKSEL_PLL_gc;			// Select PLL as system clock 

	OSC_CTRL =  OSC_PLLEN_bm;			// Leave PLL oscillator only running now

EDIT I think the bit above is using the PLL so it should work for you, the commented parts and a few more lines not shown are for the 8MHz crystal.

John Samperi

Ampertronics Pty. Ltd.

www.ampertronics.com.au

* Electronic Design * Custom Products * Contract Assembly

Last Edited: Fri. Jan 22, 2016 - 06:52 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
#define F_CPU 32768000

As others have said - this is wrong. Xmega's always power on at 2MHz. try:

#define F_CPU 2000000UL

and it will work as expected.

 

BTW even if you succeed in multiplying the clock up to 32MHz will that really be 32768000 or 32000000 ?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Isn't the max supported crystal 16MHz? For 32MHz you need to PLL that up 2x.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Setting the Xmega clock really doesn't require using a library if you just read the manuals and set a few bits.

 

Two examples, (in Basic), below, but they show the concept.

It should be easy to port it to C.

 

In one example the Xmega runs at 32 MHz from the internal 32 MHz Osc.

This routines polls the 32 MHz Osc status to see when it is powered up and stable, and it is OK to switch to it.

 

In the other example the Xmega runs at 32 MHz from an external 16 MHz Xtal, and by setting the PLL to x2.

This one doesn't bother reading the status bit for the clock of interest, it just delays a mSec and assumes that the Osc is good to go.

 

I know the real programmers hate code with numbers setting the bits.

Oh well.

The numbers are in decimal.

The comments describe what is taking place.

 

Don't forget the Configuration Change Register instructions when making changes to the clock.

 

JC

 

Clockopt5:
   'Set up the Xmega Clock. Works.
   'Run at 32 MHz from the Internal 32 MHz Osc, set by my code.
   'Xmega runs on Int 2MHz Osc on Startup.
   'This turns on the Int 32 MHz Osc, awaits it being ready, and switches to it.
   'Don't forget the Configuration Change Register Protection Trigger before
   'changing the uC's Clock Source.
   'First turn ON the 32 MHz Int Osc:
   'Then wait until the Int 32 MHz Osc is ready to be used.

   Osc_ctrl = 2                                             'Int 32 MHz Osc ON
   Rvbit = 0                                                'Clear flag
   While Rvbit = 0
      'Read the Int 32 MHz Osc Status
      Regdata = Osc_status                                  'Status of all Int Osc Sources
      Rvbit = Regdata.1                                     'Int 32 MHz Osc Status, 1 = Ready
   Wend
   Cpu_ccp = 216                                            'Config Change Protection
   Clk_ctrl = 1                                             'Use Int 32 MHz Osc
   Return

Clockopt6:
   'Set up the Xmega clock.  Works.
   'Run on External Xtal, (16 MHz), at 32 MHz, via the PLL x2.
   'This MANUALLY turns on the Xmega PLL.
   'Xmega runs at 2MHz on power up.

   Osc_xoscctrl = 203                                       'Ext Osc: 12-16MHz, 16 K Clks
   Osc_ctrl = 9                                             'PLL Off, Ext Xtal On, Int 2M OSC On
   Clk_psctrl = 0                                           'No PreScaler in use
   Osc_pllctrl = 194                                        'PLL: Ext Xtal 16 MHz, Multi x2
   Waitms 1
   Osc_ctrl = 31                                            'PLL ON, All Osc Sources On
   Waitms 1
   Cpu_ccp = 216                                            'Config Change Protection
   Clk_ctrl = 4                                             'Use PLL as Clock Source
   Return

Edit:  Typo.

Last Edited: Fri. Jan 22, 2016 - 01:12 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Too right !

There is no need to use magic numbers even with Basic.

Yes, all that you do is set the relevant control bits to enable the XTAL or PLL.
Then wait for the clock running to be verified.

Somehow, I doubt if Foxcat will want to use the official advice.

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Back in 2015 when I had a dev board from Mikroelektronika, a bootloader would set up the clock and USART for me so a 32MHz clock setting would work.

 

I think the crystal of the new Xplain board is 32.768MHz so the setting should be 32768000.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Why don't you just read the documentation that comes with your Xplain board?

It is very handy to use the PLL with the 2MHz RC oscillator. I can just run at 2, 4, ..., 32, .., 48Mhz.
Yes, this is overclocking but the chip core works fine.

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I think all you need to do is turn on the crystal oscillator and select it for the clock. Let's see:

 

	OSC.XOSCCTRL=OSC_FRQRANGE_12TO16_gc | OSC_XOSCSEL_XTAL_16KCLK_gc;
	OSC.CTRL|=OSC_XOSCEN_bm;
	uint8_t n=(CLK.PSCTRL & (~(CLK_PSADIV_gm | CLK_PSBCDIV1_bm | CLK_PSBCDIV0_bm))) | CLK_PSADIV_1_gc | CLK_PSBCDIV_1_1_gc;
	CCP=CCP_IOREG_gc;
	CLK.PSCTRL=n;

	// Wait for the external oscillator to stabilize
	while ((OSC.STATUS & OSC_XOSCRDY_bm)==0);

	// Prescaler A: 1:1, B, 1:1, C: 1:1 (all default). Unlock first.
	CCP = CCP_IOREG_gc;
	CLK.PSCTRL = CLK_PSADIV_1_gc | CLK_PSBCDIV_1_1_gc;
	// XOSC src for PLL, 2x.
	OSC.PLLCTRL = OSC_PLLSRC_XOSC_gc | (OSC_PLLFAC_gm & 2);
	// Enable PLL
	OSC.CTRL |= OSC_PLLEN_bm;
	// Wait until PLL ready
	while (!(OSC.STATUS & OSC_PLLRDY_bm)) ;
	// PLL as system clock, unlock CLK.CTRL first
	CCP = CCP_IOREG_gc;
	CLK.CTRL = CLK_SCLKSEL_gm & CLK_SCLKSEL_PLL_gc;
	// Disable the unused oscillators: 2MHz, 32MHz, internal 32kHz, PLL
	OSC.CTRL&= ~(OSC_RC2MEN_bm | OSC_RC32MEN_bm | OSC_RC32KEN_bm | OSC_PLLEN_bm);

I had a 16MHz crystal, so I set the pll to multiply by 2.

The largest known prime number: 282589933-1

In my humble opinion, I'm always right. 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The crystal is 32.768kHz not MHz!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

If it's 32.768kHz, how will I get 32.768MHz from it?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You calibrate the 2MHz RC with the 32kHz crystal. Then ùse the PLL to multiply the RC.

Why would anyone want 32.768MHz ?

But that is a mystery that only you can solve.

I do not think that you can multiply 32.768kHz by 1000 in one go.

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I have no idea what all these things are. I thought that the crystal makes 32.768MHz frequency for CPU and that's it. But I don't know what this is.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

What does ASF do?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I cannot see because Atmel Studio won't open two projects at the same time if they're not in the same solution. Can I make it be able to open multiple projects without this solution problem?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I opened it, but it's so complicated with so much code instead of directly using the I/O registers

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This works for me:

 

static inline void sysclk_init(void)
{

	// enable and switch to RC32M oscillator
	OSC.CTRL |= OSC_RC32MEN_bm;
	while (!(OSC.STATUS & OSC_RC32MRDY_bm));
	CCP = CCP_IOREG_gc;
	CLK.CTRL = CLK_SCLKSEL_RC32M_gc;
	
	// disable RC2M oscillator
	OSC.CTRL &= ~OSC_RC2MEN_bm;

}

 

Greg Muth

Portland, OR, US

Xplained/Pro/Mini Boards mostly

 

Make Xmega Great Again!

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

If you're going to be using USB later on, you'll want to use the RC2M and PLL to get your 32MHz system clock, because you'll have to tune the RC32M to run at 48MHz to clock the USB.  I'm getting ready for work so can't post code now, but will try later.

Greg Muth

Portland, OR, US

Xplained/Pro/Mini Boards mostly

 

Make Xmega Great Again!

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hey it really works!

 

/*
 * DisplayTest.cpp
 *
 * Created: 21.1.2016. 21:17:01
 *  Author: Zvoc47
 */ 

#include <avr/io.h>
#define F_CPU 32768000
#include <util/delay.h>
#include <avr/interrupt.h>

static inline void sysclk_init(void)
{

	// enable and switch to RC32M oscillator
	OSC.CTRL |= OSC_RC32MEN_bm;
	while (!(OSC.STATUS & OSC_RC32MRDY_bm));
	CCP = CCP_IOREG_gc;
	CLK.CTRL = CLK_SCLKSEL_RC32M_gc;
	
	// disable RC2M oscillator
	OSC.CTRL &= ~OSC_RC2MEN_bm;

}

int main(void)
{
	sysclk_init();
	PORTQ_DIRSET=0b00001000;
    while(1)
    {
		PORTQ_OUTTGL=0b00001000;
		_delay_ms(500);
        //TODO:: Please write your application code 
    }
}

The LED blinks half a second! Thanks. Now, is the peripheral clock set to 32MHz or is this only for the CPU?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
#define F_CPU 32768000

// it's 32MHz, not 32.768MHz.  Your delay is probably 512ms, not 500ms

#define F_CPU   32000000UL

 

The PER clock runs at the same frequency as the CPU clock.  They are in different clock domains because, depending on a particular sleep mode, one might be off while the other is running.  The PER2 and PER4 can be configured to run at 2x and 4x, respectively, of the PER/CPU clock.  A few of the peripherals can run at these faster rates, such as the EBI, AWE, HiRes, and perhaps others.

Greg Muth

Portland, OR, US

Xplained/Pro/Mini Boards mostly

 

Make Xmega Great Again!

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Foxcat385 wrote:
Can I make it be able to open multiple projects without this solution problem?

Put both projects in one solution.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
/*
 * DisplayTest.cpp
 *
 * Created: 21.1.2016. 21:17:01
 *  Author: Zvoc47
 */ 

#include <avr/io.h>
#define F_CPU 32768000
#include <util/delay.h>

static inline void sysclk_init(void)
{
	// enable and switch to RC32M oscillator
	OSC.CTRL |= OSC_RC32MEN_bm;
	while (!(OSC.STATUS & OSC_RC32MRDY_bm));
	CCP = CCP_IOREG_gc;
	CLK.CTRL = CLK_SCLKSEL_RC32M_gc;
	
	// disable RC2M oscillator
	OSC.CTRL &= ~OSC_RC2MEN_bm;
}

USART_t* TermUART = &USARTE0;

static inline void termuart_init()
{
	PORTE_OUTSET=1<<3;
	PORTE_DIRSET=1<<3;
	TermUART->BAUDCTRLA=17;
	TermUART->BAUDCTRLB=0;
	TermUART->CTRLC=USART_CMODE_ASYNCHRONOUS_gc|USART_PMODE_DISABLED_gc|USART_CHSIZE_8BIT_gc;
	TermUART->CTRLB=USART_RXEN_bm|USART_TXEN_bm;
}

int main(void)
{
	sysclk_init();
	termuart_init();
	PORTQ_DIRSET=0b00001000;
    while(1)
    {
		PORTQ_OUTTGL=0b00001000;
		_delay_ms(1000);
		TermUART->DATA='A';
    }
}

I've successfully activated USART at 115200.

 

JohanEkdahl wrote:

Foxcat385 wrote:
Can I make it be able to open multiple projects without this solution problem?

Put both projects in one solution.

I did it, but then again didn't need it.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Greg_Muth wrote:

#define F_CPU 32768000

// it's 32MHz, not 32.768MHz.  Your delay is probably 512ms, not 500ms

#define F_CPU   32000000UL

 

The PER clock runs at the same frequency as the CPU clock.  They are in different clock domains because, depending on a particular sleep mode, one might be off while the other is running.  The PER2 and PER4 can be configured to run at 2x and 4x, respectively, of the PER/CPU clock.  A few of the peripherals can run at these faster rates, such as the EBI, AWE, HiRes, and perhaps others.

 

I forgot to reply to this.

If the Xplained board has a 32.768kHz crystal, wouldn't that calibrate the internal 32MHz oscilator to 32.768MHz?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The watch crystal, 32.768 kHz, is small, low cost, and relatively accurate.

That's why it is often used in watches.

 

It serves as an accurate time base, a reference against which to measure other signals.

 

One can calibrate any signal against this one, it doesn't have to be an integer multiple of it.

 

If, for example, one used the 32 kHz signal to count for exactly 1 second, and one counted the pulses from the 32 MHz clock during that one second and counted 31,999,000 pulses then one would know that the 32 MHz clock was running a little bit slow.  One would adjust it to make it run a little bit faster and measure it again.

When one counted 32,000,000 pulses over the one second counting interval one would know that the 32 Mhz clock was exactly on frequency.

("Exactly" is a relative term, it would be "exactly" on frequency, within the tolerance of the 32 kHz reference, which itself might be a little bit of "exactly" 32.768 kHz.)

 

JC

 

 

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

So then, is the CPU on 32760000Hz or 32000000Hz?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

32.000000 MHz, provided you are not altering the DFLL.COMP register from the default value of 0x7A12.

 

From the AU Manual:

 

 

BTW, your code above is not enabling the TOSC or DFLL.

 

Greg Muth

Portland, OR, US

Xplained/Pro/Mini Boards mostly

 

Make Xmega Great Again!

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Something like this should work:

 

// enable RC32M and TOSC and wait for ready
OSC.XOSCCTRL = OSC_XOSCSEL_32KHz_gc;
OSC.CTRL |= OSC_RC32MEN_bm | OSC_XOSCEN_bm;
while (~OSC.STATUS & (OSC_RC32MRDY_bm | OSC_XOSCRDY_bm));

// select DFLL32 reference clock and enable DFLL32
OSC.DFLLCTRL = OSC_RC32MCREF_bm;
DFLLRC32M.CTRL = DFLL_ENABLE_bm;

// switch to RC32M as system clock source
CCP = CCP_IOREG_gc;
CLK.CTRL = CLK_SCLKSEL_RC32M_gc;

// turn off RC2M
OSC.CTRL &= ~OSC_RC2MEN_bm;

// select TOSC as RTC clock source
CLK.RTCCTRL = CLK_RTCSRC_TOSC_gc;

 

Greg Muth

Portland, OR, US

Xplained/Pro/Mini Boards mostly

 

Make Xmega Great Again!