square wave at 24MHz

LaGate

New member
Hello,

I have a device that needs a square wave signal at 24MHz, for now I am using a 12MHz IC oscillator for my testing. But I would like to simplify by using one of the unused outputs of my Teensy 4.1. I've tried using interrupts, but I don't think that's the right solution (not fast enough). Doing some research, it looks like I could do this using the "hardware" to drive a pin (without using the cpu). Can someone tell me how to do it?
 
The Teensy 4 PWM can generate a square-wave (without CPU intervention). The PWM frequencies are discrete divisors of 150 mhz. so you can't get exactly 24mhz. Try this in setup()
Code:
  analogWriteFrequency(23,24000000);
  analogWrite(23,128);
Scope shows 25mhz square wave on pin 23 (50% duty), 150MHz/6. Selecting 22000000 hz yields 21.4 MHz

Ref: https://www.pjrc.com/teensy/td_pulse.html
 
Good news, you can get a 24 MHz square wave by using a special feature of the chip meant to test the clock signals. Bad news, only on one of the SD card signals, specifically pin 46 (which is pin 38 on Teensy 4.0). See the back of the Teensy 4.1 pinout card to identify which pin to connect.

Here is the code.

Code:
void setup() {
  IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B0_00 = 2;
  IOMUXC_SW_MUX_CTL_PAD_GPIO_SD_B0_05 = 6;
  CCM_CCOSR = CCM_CCOSR_CLKO2_EN | CCM_CCOSR_CLKO2_SEL(0x0E);
}

void loop() {
}

Here is a quick test I did just now to confirm.

file.png

The overshoot in this picture is due to using a small wire from the scope ground to the SD card shell. It's much worse on my 200 MHz bandwidth scope if using the long ground clip, and (probably) would be much better if I went to a lot more trouble to get a shorter ground lead, but this was just done quickly to confirm the code really does give 24 MHz output.

To understand how this works, search for those register names in the reference manual. They're documented in the CCM and IOMUX chapters.
 
Thank's for your fast answers,

manitou, I had already read the reference page you mention, I just didn't realize that we could go so high in frequency. So, if I understand correctly, using analogWriteFrequency I have the choice between 25MHz or 21.4MHz, except that 21.4MHz will not have the 50% duty cycle since the divisor is an odd number (150MHz / 7). It.s a shame, because in both cases, I'm going to be out of tolerance since the maximum frequency is 24MHz with a duty cycle between 45% and 55%. Your method is to much easy :mad:

Paul, I tried to look and understand, but as soon as I open the reference manual, my brain stops working properly. I will use your code as is in my program and in the comments I will write "no idea now it works, but it works". You can always try to explain it to me, but you have to be patient :p
 
You might also play around with different CPU frequency...

For example if you run at 450mhz it looks like the PWM is running at 25mhz with duty 50%
screenshot.jpg

Code:
void setup() {
  analogWriteFrequency(23, 24000000);
  analogWrite(23, 128);
  analogWriteFrequency(19, 24000000);
  analogWrite(19, 128);
  pinMode(13, OUTPUT);
}

void loop() {
  digitalToggleFast(13);
  delay(500);
}

Top line is the 23 (FlexPWM) second line is the pin 19 (Quad timer)
 
Looking at this again, you can probably delete the line which writes to IOMUXC_SW_MUX_CTL_PAD_GPIO_AD_B0_00. I copied this from some test code which turns on both 24 MHz and 32.768 kHz to verify both crystals work. The fixture we used to test every Teensy 4.0 & 4.1 uses this feature and compares against a crystal on the tester, with accuracy good enough to detect if the oscillator is working but running at slightly wrong frequency due to either of the crystal's capacitors missing or the wrong value.

And yeah, the reference manual is huge and disjointly organized. The short story is the chip has special peripherals built in for the purpose of testing the internal clocks. Normally people wouldn't dive into using this special clock testing hardware, but it is there with the ability to give access to most of the chip's internal clocks. All this code does is turns on that peripheral to output the crystal's frequency, and then configures the pin's mux to connect to that special peripheral.
 
Back
Top