Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Hardware PWM on PIC

camerart

Active Member
C... the code works if you use CCP1CON = 0x89 as per Pommie's suggestion
Oshonsoft interrupt fires...
Hi R,M and I,
So it does :)
I think it's fantastic, that people from all around the world can work on one thing together.

'M' posted a program. Am I correct that it won't work on this PIC? OR is it still worth me holding it for later. How does it compare to this one?

Thanks all.
C
 
Last edited:

tumbleweed

Active Member
C... the code works if you use CCP1CON = 0x89 as per Pommie's suggestion
Oshonsoft interrupt fires...
Then it's time to get rid of Oshonsoft since that's not a valid setting for the 18F4431 (the msb is undefined).
CCP1CON = 0x08, 0x09, and 0x0A should all set the CCP1IF and generate an interrupt.
 

Pommie

Well-Known Member
Most Helpful Member
Then it's time to get rid of Oshonsoft since that's not a valid setting for the 18F4431 (the msb is undefined).
CCP1CON = 0x08, 0x09, and 0x0A should all set the CCP1IF and generate an interrupt.
I'd be more inclined to think it's a misprint in the datasheet.
Using 0x89 will always clear the CCP pin on a match. To just generate an interrupt use 0x86.

Mike.
Edit, thinking about it, it's definitely a mistake in the datasheet.
The same mistake would be made in ANY language if the datasheet is wrong, which it clearly is.
 
Last edited:

Pommie

Well-Known Member
Most Helpful Member
Could you also post the INCLUDES please?
The includes are pretty straight forward,
"config.c" contains the config data which is different for most pics.
"stdint.h" just contains the standard integer notations. I.E. unit8_t int32_t etc.

Mike.
 

camerart

Active Member
Hi all,
Here's a page from the D/S I have.

'M' How did you find that BIT7 is needed?
C
 

Attachments

  • CCPxCON.jpg
    CCPxCON.jpg
    333.2 KB · Views: 10

camerart

Active Member
it's just how most datasheets are.
Simples.

Mike,
Hi M,
I sometimes look for errata sheets, but I'm surprised that this happen frequently. It's hard enough to get things to work, thinking their true.

How did you know to add BIT 7 into the mix?
C
 
Last edited:

camerart

Active Member
Its just how the datasheet for my chip works.

Mike.
Hi M,
How strange!

I can see all of the PORTB PINS switching ok. I've changed the times 3x short 2x mid 3xlong, but visually, they look the same (In SIM)
I haven't wired them up so I can test with an Oscilloscope yet.
C
 

camerart

Active Member
Hi,
Odd things are happening!
A suggestion from AAC is to add save system here:
On High Interrupt
Save System

I've also added a TOGGLE LED in MAIN, so I can see what's going on when 'live'.

In the SIM, the LED appears to switch, then once the INTERRUPT fires, it doesn't appear to go back to the MAIN LOOP

This could be an Oshonsoft problem, as it's intermittent?
C
 

tumbleweed

Active Member
Mike.
Edit, the code uses a Pic16F18854 as I had this handy.
There's no mistake in the 18F4431 datasheet. The 18F is different than the 16F.
In some 18F's, CCP1CON bits 7 and 6 control the Enhanced PWM Output Configuration, but that's not being used here.

If changing CCP1CON bit 7 in a PIC18F4431 causes Oshonsoft to work, then it (Oshonsoft) is broken.
 

camerart

Active Member
There's no mistake in the 18F4431 datasheet. The 18F is different than the 16F.
In some 18F's, CCP1CON bits 7 and 6 control the Enhanced PWM Output Configuration, but that's not being used here.

If changing CCP1CON bit 7 in a PIC18F4431 causes Oshonsoft to work, then it (Oshonsoft) is broken.
Hi T,
This is possible, there have been issues in the past, but I can't tell whether it is broken
C
 

Ian Rogers

User Extraordinaire
Forum Supporter
Most Helpful Member
Then it's time to get rid of Oshonsoft since that's not a valid setting for the 18F4431 (the msb is undefined).
CCP1CON = 0x08, 0x09, and 0x0A should all set the CCP1IF and generate an interrupt.
As is 0x02 (toggle) I use proteus and setting CCP1CON = 0x02 works just dandy..
Hi R,M and I,
So it does :)
I think it's fantastic, that people from all around the world can work on one thing together.

'M' posted a program. Am I correct that it won't work on this PIC? OR is it still worth me holding it for later. How does it compare to this one?

Thanks all.
C
Pretty much of a muchness... Very similar operation..
 

jjw

Member
There's no mistake in the 18F4431 datasheet. The 18F is different than the 16F.
In some 18F's, CCP1CON bits 7 and 6 control the Enhanced PWM Output Configuration, but that's not being used here.

If changing CCP1CON bit 7 in a PIC18F4431 causes Oshonsoft to work, then it (Oshonsoft) is broken.
It works in Oshonsoft without bit 7 -> CCP1CON = 0x01
Edit: should be: CCP1CON = 0x09
 
Last edited:

jjw

Member
Hi,
Odd things are happening!
A suggestion from AAC is to add save system here:
On High Interrupt
Save System

I've also added a TOGGLE LED in MAIN, so I can see what's going on when 'live'.

In the SIM, the LED appears to switch, then once the INTERRUPT fires, it doesn't appear to go back to the MAIN LOOP

This could be an Oshonsoft problem, as it's intermittent?
C
It works for me in the simulator.
You have to make the led toggle at about 1ms, otherwise it takes ages.
 

camerart

Active Member
I'm confused, is this being tested in actual hardware or in a simulator?

Mike.
Hi M,
Back from AAC, after a couple of mods.

The SIM works intermittently. Here is a live view, from an Oscilloscope.
I have the LED LOOP set to 20ms.
Here is the program and OSC view:

C.
Code:
'18f4431 32mhz XTL REMOTE PWM HW 130522 1330
Define CONFIG1L = 0x00
Define CONFIG1H = 0x06  '8mHz XTLx4 32mHz    0x02
Define CONFIG2L = 0x0e
Define CONFIG2H = 0x20
Define CONFIG3L = 0x1c
Define CONFIG3H = 0x9d
Define CONFIG4L = 0x80
Define CONFIG4H = 0x00
Define CONFIG5L = 0x0f
Define CONFIG5H = 0xc0
Define CONFIG6L = 0x0f
Define CONFIG6H = 0xe0
Define CONFIG7L = 0x0f
Define CONFIG7H = 0x40

//File:   servo_pwm_test_v2.C
//Author: robert jenkins, converted to BASIC by Ian Rogers

//Created On 09 May 2022, 09:45

//Better optimised version, more consistent Output timing And
//no timer Interrupt Or anything needed in main program section,
//beyond the initialisations.

//The main program loop can have delays Or wait loops,
//As Long As interrupts are never blocked.

Define CLOCK_FREQUENCY = 32
ANSEL0 = 0
ANSEL1 = 1

Dim index As Byte

Dim servo_times(8) As Word

Dim time_now As Word
Dim time_set As Word

Dim shift_reg As Byte

//With this timing, 1mS = 1000 counts;
//servo 1mS to 2mS = 1000 to 2000,
//with 1500 as mid point.

//For demonstration, I'm setting the servo times
//to various fixed values.

//Set them from your program as needed.

servo_times(0) = 1500  //Port bit 0, Mid position
servo_times(1) = 1100  //Port bit 1, Near min position
servo_times(2) = 1900  //Port bit 2, Near max position
servo_times(3) = 1300  //Port bit 3, Under mid position
servo_times(4) = 1700  //Port bit 4, Over mid position
servo_times(5) = 1200  //Port bit 5, etc
servo_times(6) = 1800  //Port bit 6
servo_times(7) = 1400  //Port bit 7

TRISB = 0  'Port C all outputs changed &
TRISD = 0  'Port D all outputs changed &

T1CON = 0x31  //8:1, switch on

//Without an output pin defined, just an interrupt from CCP
CCP1CON = 0x02  //ccp_compare_toggle

//And enable the interrupts for the hardware used
//the reference for CCP1, so no time interrupt required.
PIE1.CCP1IE = 1
'INTCON1.PEIE = 1  //INTCON bit 6'ADDED #81 &
'INTCON1.GIE = 1
INTCON.PEIE = 1  //INTCON bit 6'ADDED #81 &
INTCON.GIE = 1  'CHANGED &
'NOTE, line from old program CCP1IP = 1  'High Priority interrupt for CCP1

//Main loop
loop:

Toggle RD6  'Something to do
Toggle RD7  'Something to do

WaitMs 20

//Nothing needed here for servos, it's all in the CCP interrupt.
//Rest of the program here onwards.

Goto loop

End                                               

//INT_CCP1
On High Interrupt
Save System

PIR1.CCP1IF = 0  //clear IF ADDED

shift_reg = ShiftLeft(shift_reg, 1)  //Shift the bit left one place.
//shift_reg = shift_reg + shift reg would do the same.
LATB = shift_reg  //Write the shift register bits to the port CHANGED &

//Increment index for next servo time value
index = index + 1

If index < 8 Then  //All servos already done?
    //No, do next servo

    //Set the duration for this output, as a new offset
    //from the last compare time.
    time_set = time_set + servo_times(index)

    CCPR1L = time_set.LB  //Write the compare time to CCP 1 register.
    CCPR1H = time_set.HB

Else
    //No output needed as the port is already updated.
    //output_c(0); // Turn off all servo bits.

    //restarting the sequence.

    time_set = time_set + 1500  //add 1.5mS for the next interrupt
    //Update CCP
    CCPR1L = time_set.LB  //Write the compare time to CCP 1 register.
    CCPR1H = time_set.HB

    If index > 15 Then
        //15 * average 1.5mS = 22.5mS, a reasonable frame repeat time
    
        //Set up for a new sequence
        index = 0
        shift_reg = 1  //Set a bit that will be at port bit 0.
    
        time_now.LB = TMR1L  //Get the timer present count
        time_now.HB = TMR1H
        time_set = time_now + servo_times(index)  //And set the first duration
        LATB = shift_reg  //Write the shift register bits to the port CHANGED &
        CCPR1L = time_set.LB  //Write the compare time to CCP 1 register.
        CCPR1H = time_set.HB
    Endif
Endif


Resume
 

Attachments

  • OSC2.jpg
    395.7 KB · Views: 8

camerart

Active Member
Hi,
If I'm correct, that the ENVELOPE is over 24ms, where it should be 20ms. Does this matter, and how can it be corrected?
Channel timing seems cprrect.
C
 

Latest threads

New Articles From Engineer's Garage

Top