req;sample code for 5 independent pwm outputs at separate frequencies

Started by okmn, Feb 26, 2021, 12:32 PM

Previous topic - Next topic

okmn

hi guys,
I had been opened also same topic ın the last old/ex-website before it close;
and you guys shared some sample codes but i can not reach all of them now.!!

please could you support some sample code for  different time base 5 pwm (5 different timer )?

i would use pic16f1527
each pwm frequency and duty  will diffrent value,
and "2 pwm" out will run in same time together.

for example ;

pwm1 and pwm3 will run in same time but different frequency diffrent duty

i have planinng to use different pwm and different timer like that ;

ccp1(pwm1)...timer 2
ccp3(pwm3)...timer 4
ccp6(pwm6)..timer 6
ccp8(pwm8)..timer 8
ccp9(pwm9)..timer 10
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

but after the information dear Les gaved to us in here , I COULDN'T STOP MY CURIOSITY;
and I searched a little more and found the pic mcus below, which ones have lots of uart and at least 5 independent pwm outputs.

but now the question arises with which one should I go on and why?
Can you help about it ?
(Which one/ones is/are the well-established product in terms of stability, durability, reliability?

PIC18F47Q83....16BIT DUAL PWM /CCP = 4/3(are dual pwm frequency can set able different signal?)
                  8-Bit Timer with HLT/16-Bit Timers = 3/3
                  UART/ UART WITH PROTOOL SUPPORT =3/2
                  CAN
             
PIC18F47Q84...16BIT DUAL PWM /CCP = 4/3(are dual pwm frequency can set able different signal?)
                  8-Bit Timer with HLT/16-Bit Timers = 3/3
                  UART/ UART WITH PROTOCOL SUPPORT =3/2
                  CAN FD

PIC18F47K42... CCP/10 BIT PWM = 4/4
                      8-Bit Timer with HLT/16-Bit Timers = 3/4
                      UART = 2

PIC18F47Q43...16BIT DUAL PWM /CCP = 3/3(are dual pwm frequency can set able different signal?)
                      8-Bit Timer with HLT/16-Bit Timers = 3/4
                      UART/ UART WITH PROTOCOL SUPPORT = 4/1

this is scenario schematic just

okmn

The users shared more than one sample codes on the old site in the "topic" I made a request about the same topic.
I wonder if those users don't know about this new website now?

could you share any sample codes for independent 5 pwm out (different time based pwm) and "any 2 pwm out" will run together in  same time in different frequencies

via using "HPWM"command (Generate PWM signals using the device's CCP peripherals)
or via with a new command (that exists but I do not know) for the new pics which one has their "dedicated timer" to use for pwm signal genarete.

For any or more of those PIC MCUs
pic16f1527 ,PIC18F47K42, PIC18F47Q43,PIC18F47Q83,PIC18F47Q84

flosigud

18fxxk22 also has 5 PWM. There was a discussion on that recently where few people posted their code including me. I don't know what the difference is between that and all the other controllers you mentioned but this might be useful.


tumbleweed

The K22 only has 3 8-bit TMR modules (TMR2/4/6), so you can't get 5 totally independent PWM's

flosigud


okmn

Quote from: flosigud on Apr 13, 2021, 06:57 PMThis is it: https://protoncompiler.com/index.php/topic,168.msg908.html#msg908

thank you to your notice.
in that codes used same frequency to all pwm outputs(if i did not comment wrong) 
they are same code algorithm , like 877A has a timer2 and you can use only that for all pwm out and all pwm frequency will be same (you can change duty value but not freuency value)

i needed a sample code has 5 pwm out able in the same time( at least 2 out running in the same time) but with different frequencies
and the new model PICs q43 q83 q84 has their own pwm signal out by their own d"edicated timers"

the problem ,i did not use any other 40pin "pic" than 877A , so i don't know(at the days now) how can i use these new models "PICs"for via separated  and different frequency pwm out

dear Les shared some sample codes with his new mechanism "procedurees" in ex closed forum ;
but also he said the compiler does not support at the moment for the new series PICs

but pic16f1527 existed before these new series ,someones could write some codes for these old type pic mcu like pic1527...(i was thinking like that).

than you.

top204

The HPWM command will not support seperate timers for its frequency, and I am not going to add it because of the, many, differences between devices.

I had a quick look at the PIC16F1527 datasheet and wrote the code below. It is purely experimental and I do not have a PIC16F1527 device to test it, so it will need alterations to get it working fully, but it should give you some idea what is required for multi-timers on the CCP peripherals. It shows the flexibilty that procedures and preproccesor meta-macros give, and the reason new comamnds are not required in the compiler. Download the device's datasheet and read through the SFRs that are used for the CCPs and Timers, and you will see what each bit of them does. Then experiment with a device and tweak the code until it produces what is required.

Please note.... I cannot answer any questions concerning the code below's operation because I cannot test it and it is purely based upon a quick read of the datasheet.

'
'   /\\\\\\\\\
'  /\\\///////\\\
'  \/\\\     \/\\\                                                 /\\\          /\\\
'   \/\\\\\\\\\\\/        /\\\\\     /\\\\\\\\\\     /\\\\\\\\   /\\\\\\\\\\\  /\\\\\\\\\\\  /\\\\\\\\\
'    \/\\\//////\\\      /\\\///\\\  \/\\\//////    /\\\/////\\\ \////\\\////  \////\\\////  \////////\\\
'     \/\\\    \//\\\    /\\\  \//\\\ \/\\\\\\\\\\  /\\\\\\\\\\\     \/\\\         \/\\\        /\\\\\\\\\\
'      \/\\\     \//\\\  \//\\\  /\\\  \////////\\\ \//\\///////      \/\\\ /\\     \/\\\ /\\   /\\\/////\\\
'       \/\\\      \//\\\  \///\\\\\/    /\\\\\\\\\\  \//\\\\\\\\\\    \//\\\\\      \//\\\\\   \//\\\\\\\\/\\
'        \///        \///     \/////     \//////////    \//////////      \/////        \/////     \////////\//
'                                  Let's find out together what makes a PIC Tick!
'
' Experimental PWM using the CCP peripherals with seperate timers based upon the datasheet for a PIC16F1527 device
' The code cannot be tested by me, and will need tweaks for the timer values for a particular frequency and bit resolution
'
' Written by Les Johnson for the Positron8 BASIC compiler
'
    Device = 16F1527
    Declare Xtal = 32
'
' Setup the pins for the CCP peripherals
'
    Symbol CCP1_Pin = PORTC.2
    Symbol CCP2_Pin = PORTC.1
    Symbol CCP3_Pin = PORTG.0
    Symbol CCP5_Pin = PORTG.4
    Symbol CCP8_Pin = PORTE.4
'
' Create a variable for the demo
'
    Dim wDutyValue As Word

'-------------------------------------------------------------------------------------
' CCP1 peripheral
'-------------------------------------------------------------------------------------
' Setup CCP1
' Input     : None
' Output    : None
' Notes     : Setup to use Timer2
'
Proc PWM1_Init()
    CCP1CON = %00111100                                 ' CCP1 PWM
    CCPR1L = $00
    CCPR1H = $00
    CCPTMRS0bits_C1TSEL0 = 0                            ' \ Select Timer2
    CCPTMRS0bits_C1TSEL1 = 0                            ' /
EndProc

'-------------------------------------------------------------------------------------
' Write the duty value to CCP1
' Input     : pDuty holds the duty cycle value
' Output    : None
' Notes     : None
'
Proc PWM1_Duty(pDuty As Word)
    CCP1CON = CCP1CON & %11001111
    WREG = pDuty << 4
    WREG = WREG & %00110000
    CCP1CON = CCP1CON | WREG
    CCPR1L = pDuty >> 2
EndProc

'-------------------------------------------------------------------------------------
' CCP2 peripheral
'-------------------------------------------------------------------------------------
' Setup CCP2
' Input     : None
' Output    : None
' Notes     : Setup to use Timer4
'
Proc PWM2_Init()
    CCP2CON = %00111100                                 ' CCP2 PWM
    CCPR2L = $00
    CCPR2H = $00
    CCPTMRS0bits_C2TSEL0 = 1                            ' \ Select Timer4
    CCPTMRS0bits_C2TSEL1 = 0                            ' /
EndProc

'-------------------------------------------------------------------------------------
' Write the duty value to CCP2
' Input     : pDuty holds the duty cycle value
' Output    : None
' Notes     : None
'
Proc PWM2_Duty(pDuty As Word)
    CCP2CON = CCP2CON & %11001111
    WREG = pDuty << 4
    WREG = WREG & %00110000
    CCP2CON = CCP2CON | WREG
    CCPR2L = pDuty >> 2
EndProc

'-------------------------------------------------------------------------------------
' CCP3 peripheral
'-------------------------------------------------------------------------------------
' Setup CCP3
' Input     : None
' Output    : None
' Notes     : Setup to use Timer6
'
Proc PWM3_Init()
    CCP3CON = %00001100                                 ' CCP3 PWM
    CCPR3L = $00
    CCPR3H = $00
    CCPTMRS0bits_C3TSEL0 = 0                            ' \ Select Timer6
    CCPTMRS0bits_C3TSEL1 = 1                            ' /
EndProc

'-------------------------------------------------------------------------------------
' Write the duty value to CCP3
' Input     : pDuty holds the duty cycle value
' Output    : None
' Notes     : None
'
Proc PWM3_Duty(pDuty As Word)
    CCP3CON = CCP3CON & %11001111
    WREG = pDuty << 4
    WREG = WREG & %00110000
    CCP3CON = CCP3CON | WREG
    CCPR3L = pDuty >> 2
EndProc

'-------------------------------------------------------------------------------------
' CCP5 peripheral
'-------------------------------------------------------------------------------------
' Setup CCP5
' Input     : None
' Output    : None
' Notes     : Setup to use Timer8
'
Proc PWM5_Init()
    CCP5CON = %00001100                                 ' CCP5 PWM
    CCPR5L = $00
    CCPR5H = $00
    CCPTMRS1bits_C5TSEL0 = 0                            ' \ Select Timer8
    CCPTMRS1bits_C5TSEL1 = 1                            ' /
EndProc

'-------------------------------------------------------------------------------------
' Write the duty value to CCP5
' Input     : pDuty holds the duty cycle value
' Output    : None
' Notes     : None
'
Proc PWM5_Duty(pDuty As Word)
    CCP5CON = CCP5CON & %11001111
    WREG = pDuty << 4
    WREG = WREG & %00110000
    CCP5CON = CCP5CON | WREG
    CCPR5L = pDuty >> 2
EndProc

'-------------------------------------------------------------------------------------
' CCP8 peripheral
'-------------------------------------------------------------------------------------
' Setup CCP8
' Input     : None
' Output    : None
' Notes     : Setup to use Timer10
'
Proc PWM8_Init()
    CCP8CON = %00001100                                 ' CCP8 PWM
    CCPR8L = $00
    CCPR8H = $00
    CCPTMRS1bits_C8TSEL0 = 0                            ' \ Select Timer10
    CCPTMRS1bits_C8TSEL1 = 1                            ' /
EndProc

'-------------------------------------------------------------------------------------
' Write the duty value to CCP8
' Input     : pDuty holds the duty cycle value
' Output    : None
' Notes     : None
'
Proc PWM8_Duty(pDuty As Word)
    CCP8CON = CCP8CON & %11001111
    WREG = pDuty << 4
    WREG = WREG & %00110000
    CCP8CON = CCP8CON | WREG
    CCPR8L = pDuty >> 2
EndProc

'-------------------------------------------------------------------------------------
' Timer2
'-------------------------------------------------------------------------------------
$define Timer2_Start() T2CONbits_TMR2ON = 1             ' Start Timer2
$define Timer2_Stop() T2CONbits_TMR2ON = 0              ' Stop Timer2
$define Timer2_Read() TMR2                              ' Read Timer2
$define Timer2_Write(pTimerVal) TMR2 = pTimerVal        ' Write to Timer2
$define Timer2_Period(pPeriod) PR2 = pPeriod            ' Write a period value to Timer2

'-------------------------------------------------------------------------------------
' Setup Timer2
' Input     : None
' Output    : None
' Notes     : None
'
Proc Timer2_Init()
    PR2 = $FF
    TMR2 = $00
    PIR1bits_TMR2IF = 0                                 ' Clear the timer's IF flag
    T2CON = %00000100                                   ' T2CKPS 1:1, T2OUTPS 1:1, Timer on
EndProc

'-------------------------------------------------------------------------------------
' Timer4
'-------------------------------------------------------------------------------------
$define Timer4_Start() T4CONbits_TMR4ON = 1             ' Start Timer4
$define Timer4_Stop() T4CONbits_TMR4ON = 0              ' Stop Timer4
$define Timer4_Read() TMR4                              ' Read Timer4
$define Timer4_Write(pTimerVal) TMR4 = pTimerVal        ' Write to Timer4
$define Timer4_Period(pPeriod) PR4 = pPeriod            ' Write a period value to Timer4

'-------------------------------------------------------------------------------------
' Setup Timer4
' Input     : None
' Output    : None
' Notes     : None
'
Proc Timer4_Init()
    PR4 = $FF
    TMR4 = $00
    PIR3bits_TMR4IF = 0                                 ' Clear the timer's IF flag
    T4CON = %00000100                                   ' T4CKPS 1:1, T4OUTPS 1:1, Timer on
EndProc

'-------------------------------------------------------------------------------------
' Timer6
'-------------------------------------------------------------------------------------
$define Timer6_Start() T6CONbits_TMR6ON = 1             ' Start Timer6
$define Timer6_Stop() T6CONbits_TMR6ON = 0              ' Stop the Timer
$define Timer6_Read() TMR6                              ' Read Timer6
$define Timer6_Write(pTimerVal) TMR6 = pTimerVal        ' Write to Timer6
$define Timer6_Period(pPeriod) PR6 = pPeriod            ' Write a period value to Timer6

'-------------------------------------------------------------------------------------
' Setup Timer6
' Input     : None
' Output    : None
' Notes     : None
'
Proc Timer6_Init()
    PR6 = $00
    TMR6 = $00
    PIR3bits_TMR6IF = 0                                 ' Clear the timer's IF flag
    T6CON = %00000110                                   ' T6CKPS 1:16, T6OUTPS 1:1, Timer on
EndProc

'-------------------------------------------------------------------------------------
' Timer8
'-------------------------------------------------------------------------------------
$define Timer8_Start() T8CONbits_TMR8ON = 1             ' Start Timer8
$define Timer8_Stop() T8CONbits_TMR8ON = 0              ' Stop Timer8
$define Timer8_Read() TMR8                              ' Read Timer8
$define Timer8_Write(pTimerVal) TMR8 = pTimerVal        ' Write to Timer8
$define Timer8_Period(pPeriod) PR8 = pPeriod            ' Write a period value to Timer8

'-------------------------------------------------------------------------------------
' Setup Timer8
' Input     : None
' Output    : None
' Notes     : None
'
Proc Timer8_Init()
    PR8 = $FF
    TMR8 = $00
    PIR2bits_TMR8IF = 0                                 ' Clear the timer's IF flag
    T8CON = %00000100                                   ' T8CKPS 1:1, T8OUTPS 1:1, Timer on
EndProc

'-------------------------------------------------------------------------------------
' Timer10
'-------------------------------------------------------------------------------------
$define Timer10_Start() T10CONbits_TMR10ON = 1          ' Start Timer10
$define Timer10_Stop() T10CONbits_TMR10ON = 0           ' Stop Timer10
$define Timer10_Read() TMR10                            ' Read Timer10
$define Timer10_Write(pTimerVal) TMR10 = pTimerVal      ' Write to Timer10
$define Timer10_Period(pPeriod) PR10 = pPeriod          ' Write a period value to Timer10

'-------------------------------------------------------------------------------------
' Setup Timer10
'
Proc Timer10_Init()
    PR10 = $3F
    TMR10 = $00
    PIR2bits_TMR10IF = 0                                ' Clear the timer's IF flag
    T10CON = %00000101                                  ' T10CKPS 1:4, T10OUTPS 1:1, Timer on
EndProc

'-------------------------------------------------------------------------------------
' The main program starts here
'
Main:
    Setup()

    Do
        For wDutyValue = 0 to 1023
            PWM1_Duty(wDutyValue)
            PWM2_Duty(wDutyValue)
            PWM3_Duty(wDutyValue)
            PWM5_Duty(wDutyValue)
            PWM8_Duty(wDutyValue)
            DelayMs 10
        Next
    Loop

'-------------------------------------------------------------------------------------
' Setup the CCP and Timer peripherals for PWM
'
Proc Setup()
    Timer2_Init()
    Timer4_Init()
    Timer6_Init()
    Timer8_Init()
    Timer10_Init()

    PWM1_Init()
    PWM2_Init()
    PWM3_Init()
    PWM5_Init()
    PWM8_Init()

    Output CCP1_Pin
    Output CCP2_Pin
    Output CCP3_Pin
    Output CCP5_Pin
    Output CCP8_Pin
EndProc

okmn

There were codes that you and a few other users shared on the old site; at least I'm running after them.

because I could not copy those codes to my own computer, and then the site was closed anyway.

You shared that day and stated that you wrote one of the codes with pic18xxxq, but now the compiler does not support it, but you will.

Until the new compiler arrives, I would like to study the algorithm for the following ... procedure mechanism and others


you did well again!,
I don't want you to write all ready-made code for me;but you did again perfect help...
thank you Les for your close interesting to us.