0% found this document useful (0 votes)
210 views5 pages

Arduino PWM and Frecuencia

This code defines functions for controlling pulse-width modulation (PWM) output on an Arduino. It initializes PWM timers on startup and enters a loop where it gets input from the serial port to set the PWM frequency, duty cycle, and phase shift between two pins in real-time. It also allows direct manipulation of timer registers for debugging purposes.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
210 views5 pages

Arduino PWM and Frecuencia

This code defines functions for controlling pulse-width modulation (PWM) output on an Arduino. It initializes PWM timers on startup and enters a loop where it gets input from the serial port to set the PWM frequency, duty cycle, and phase shift between two pins in real-time. It also allows direct manipulation of timer registers for debugging purposes.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 5

#include <PWM.

h>

int outputPin = 11;

//For testing
int freqInput = 100; //10-10000 Hz (I wanted that range only)
int dutyCycleInput = 70; //1-65535

void setup()
{
InitTimersSafe();
}

void loop()
{
//Get inputs from either serial or through pot
//So we have Frequency and Duty cycle in variables 'freqInput' &
'dutyCycleInput' respectively in int
SetPinFrequencySafe(outputPin, freqInput );
pwmWriteHR(outputPin, dutyCycleInput );
}

/*

Test sketch for arduino PWM library - modified version.

CLI - command line interface:

d - debug, shift phase on regular time base interval, demo mode.


f - set frequency, "f100" - 100 Hz.
l - set duty cycle, "l2000".
p - set phase, "p90".

Direct Registers Manipulation:

1. "a80" - set address


2. "w10111" - write data, leading 0 could be ommited.
3. "r" - read current registers.

NOTE: Use direct registers programming VERY Carefully !!!

created 16 June. 2017


Anatoly Kuzmenko
[email protected]

This example code is in the public domain.


Works for Timer 1 & 3 so far:
Pin 11 12 timer1
Pin 2 3 5 timer3

Timer-1 is primery clock generator, Timer-3 secondary, phase shifted clock.


*/

#include <PWM.h>

String in_String = "";


boolean end_input = false;
uint8_t adres_reg = 0;
uint8_t debug_osm = 0;

uint8_t prime_pin = 11;


uint8_t secon_pin = 2;

uint16_t level_pwm = 32767; // 1 -/- 65535


uint16_t phase_pwm = 90; // degree 1 -/- 360
uint32_t freqn_pwm = 35; // frequency in Hz

unsigned long previousMillis = 0;


const long interval = 500;

void setup()
{
Serial.begin(115200);
in_String.reserve(200);

InitTimersSafe();
}

void loop()
{
int32_t tempr = 0;
char * pEnd;

if(debug_osm) {
uint32_t currentMillis = millis();
if (currentMillis - previousMillis >= interval) {
previousMillis = currentMillis;
phaseShift();
}
}

serialEvent();

if( end_input) {
char cmd = in_String[0];
in_String[0] = '+';

if( cmd == 'd' ) {


debug_osm = 1 - debug_osm;
if(debug_osm) Serial.print(F("\nDebug aktiv."));
else Serial.print(F("\nDebug de-aktiv."));
}

if( cmd == 'f' ) {


tempr = strtol( in_String.c_str(), &pEnd, 10);
Serial.print(F("\n\tFreq: "));
Serial.print(tempr, DEC);
freqn_pwm = tempr;

bool success1 = SetPinFrequencySafe(prime_pin, freqn_pwm);


bool success2 = SetPinFrequencySafe(secon_pin, freqn_pwm);

GTCCR |= ((1<<TSM)|(1<<PSRASY)|(1<<PSRSYNC));
GTCCR &= ~(1<<TSM);

if(success1 && success2) {


pwmWriteHR(prime_pin, level_pwm);
pwmWriteHR(secon_pin, level_pwm);

pinMode(13, OUTPUT);
digitalWrite(13, HIGH);
}
}

if( cmd == 'l' ) {


tempr = strtol( in_String.c_str(), &pEnd, 10);
Serial.print(F("\n\tLevel: "));
Serial.print(tempr, DEC);
level_pwm = tempr;
pwmWriteHR(prime_pin, level_pwm);
pwmWriteHR(secon_pin, level_pwm);
}

if( cmd == 'p' ) {


tempr = strtol( in_String.c_str(), &pEnd, 10);
Serial.print(F("\n\tPhase: "));
Serial.print(tempr, DEC);
phase_pwm = tempr;

//GTCCR |= ((1<<TSM)|(1<<PSRASY)|(1<<PSRSYNC));
GTCCR |= (1<<TSM);

tempr = ICR3 * (phase_pwm /360.0) -1;


if(tempr < 0) tempr = 0;
TCNT1 = 0;
TCNT3 = tempr;

GTCCR &= ~(1<<TSM);


}

if( cmd == 'a' ) {


adres_reg = strtol( in_String.c_str(), &pEnd, 16);
Serial.print(F("\n\tReg: "));
Serial.print(adres_reg, HEX);
Serial.print(F("\tvalue: "));
tempr = (*(uint8_t*)adres_reg);
Serial.print(tempr, BIN);
}
if( cmd == 'r' ) {
Serial.print(F("\n\tReg: "));
Serial.print(adres_reg, HEX);
Serial.print(F("\tvalue: "));
tempr = (*(uint8_t*)adres_reg);
Serial.print(tempr, BIN);
}
if( cmd == 'w' ) {
Serial.print(F("\n\tReg: "));
Serial.print(adres_reg, HEX);
Serial.print(F("\tvalue: "));
tempr = (*(uint8_t*)adres_reg);
Serial.print(tempr, BIN);
tempr = strtol( in_String.c_str(), &pEnd, 2);
(*(uint8_t*)adres_reg) = tempr;
Serial.print(F("\tnew value: "));
tempr = (*(uint8_t*)adres_reg);
Serial.print( tempr, BIN);
}

in_String = "";
end_input= false;
}
}

void serialEvent() {
while (Serial.available()) {
char inChar = (char)Serial.read();
in_String += inChar;
if (inChar == '\n') {
end_input= true;
}
}
}

void phaseShift() {
static uint16_t phase_loc = 0;
uint16_t tempr = 0;

//GTCCR |= ((1<<TSM)|(1<<PSRASY)|(1<<PSRSYNC));
GTCCR |= (1<<TSM);
// GTCCR |= _BV (TSM);

tempr = ICR3 * (phase_loc /360.0) -1;


if(tempr < 0) tempr = 0;

TCNT1 = 0;
TCNT3 = tempr;

GTCCR &= ~(1<<TSM);


// GTCCR &= ~(_BV (TSM));
phase_loc += 30;
if(phase_loc > 360) phase_loc = 0;
}

You might also like