Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

PWM duty cycle update for Sinewave UPS

Status
Not open for further replies.

UroBoros

Advanced Member level 2
Joined
May 5, 2004
Messages
642
Helped
19
Reputation
38
Reaction score
8
Trophy points
1,298
Location
Cochin - India
Activity points
6,463
I am using a Dspic for doing PWM for a Sinewave inverter.

The sine reference update part I have some problems.

I read the reference value from a sinetable at 104 usec interval. I have the output voltage and current ADC value at that instant in hand. Can anybody suggest a simple method to calculate the duty cycle update value?

Thanks
 

You forgot to mention, what's your intended algorithm to calculate the PWM duty cycle, e.g. how an ADC is involved.
 
The duty-cicle is exacly the sine value recorded at lookup table.
I did it in an UPS firmware and works fine.

+++
 
A method to vary the amplitude of a sine wave.

Code:
#define MAXPWM  1000    /* Whatever your max pwm is? */
#define MAXVALUES 359   /* Size of look up table */

#define MAXVOLTS  16500U        /* Maximum pwm amplitude, choose to suit application */
#define MINVOLTS  5000U         /* Minimum pwm amplitude */

extern sinetable[];   /* Your sine table look up values */

unsigned int duty_cycle;
unsigned int amplitude;
unsigned int sine_table_index = 0;

/*--- Set duty cycle using a timer interrupt, change period register for frequency ---*/

duty_cycle = sinetable[sine_table_index];
duty_cycle = ((unsigned long)duty_cycle * (unsigned long)amplitude) >> 15;
duty_cycle = ((unsigned long)duty_cycle * (unsigned long)MAXPWM) >> 15;

if(++sine_table_index > MAXVALUES){
  sine_table_index = 0;
  }


/*--- Sinewave lookup table, 360 1 degree steps ---*/

const unsigned int sinetable[] = {
32500,33067,33634,34200,34767,35332,35897,36460,37023,37584,
38143,38701,39257,39810,40362,40911,41458,42002,42543,43080,
43615,44146,44674,45198,45718,46235,46747,47254,47757,48256,
48750,49238,49722,50200,50673,51141,51603,52058,52508,52952,
53390,53821,54246,54664,55076,55480,55878,56268,56652,57028,
57396,57757,58110,58455,58793,59122,59443,59756,60061,60357,
60645,60925,61195,61457,61710,61955,62190,62416,62633,62841,
63040,63229,63409,63579,63741,63892,64034,64167,64289,64402,
64506,64599,64683,64757,64821,64876,64920,64955,64980,64995,
65000,64995,64980,64955,64920,64876,64821,64757,64683,64599,
64506,64402,64289,64167,64034,63892,63741,63579,63409,63229,
63040,62841,62633,62416,62190,61955,61710,61457,61195,60925,
60645,60357,60061,59756,59443,59122,58793,58455,58110,57757,
57396,57028,56652,56268,55878,55480,55076,54664,54246,53821,
53390,52952,52508,52058,51603,51141,50673,50200,49722,49238,
48750,48256,47757,47254,46747,46235,45718,45198,44674,44146,
43615,43080,42543,42002,41458,40911,40362,39810,39257,38701,
38143,37584,37023,36460,35897,35332,34767,34200,33634,33067,
32500,31932,31365,30799,30232,29667,29102,28539,27976,27415,
26856,26298,25742,25189,24637,24088,23541,22997,22456,21919,
21384,20853,20325,19801,19281,18764,18252,17745,17242,16743,
16250,15761,15277,14799,14326,13858,13396,12941,12491,12047,
11609,11178,10753,10335,9923,9519,9121,8731,8347,7971,
7603,7242,6889,6544,6206,5877,5556,5243,4938,4642,
4354,4074,3804,3542,3289,3044,2809,2583,2366,2158,
1959,1770,1590,1420,1258,1107,965,832,710,597,
493,400,316,242,178,123,79,44,19,4,
0,4,19,44,79,123,178,242,316,400,
493,597,710,832,965,1107,1258,1420,1590,1770,
1959,2158,2366,2583,2809,3044,3289,3542,3804,4074,
4354,4642,4938,5243,5556,5877,6206,6544,6889,7242,
7603,7971,8347,8731,9121,9519,9923,10335,10753,11178,
11609,12047,12491,12941,13396,13858,14326,14799,15277,15761,
16250,16743,17242,17745,18252,18764,19281,19801,20325,20853,
21384,21919,22456,22997,23541,24088,24637,25189,25742,26298,
26856,27415,27976,28539,29102,29667,30232,30799,31365,31932
};
 
Last edited:
Thanks for all the replays and especially that sin table.
I can generate Sine wave now.Got it.But how to adjust the duty cycle for voltage correction based on inverter load.
I am reading inverter output volt and current using two channel ADC every 104 uS (ON every sinetable update - I have
sinetable with 192 points) to track the waveform. But how to apply PID or any simple method to compensate load changes?

Thanks
 

If you are using MPLAB C30 compiler, in the \src\include\ directory you will find 'dsp.h'. At the end of that file you will find the function prototypes for a PID controller that is included in the library.
You could use that PID controller to control the amplitude of your sine wave.
 
I think, the multiple table solution provided by andre is good for tiny processor like pic16 or pic18, that has problems to carry out a multiply each PWM cycle. At PIC24 or dsPIC has a fast 16-Bit hardware multiplier and can use a single table, scaling the output. The voltage controller should use a measurement of averaged rectified value or even rms to adjust the duty cycle.
 
I think, the multiple table solution provided by andre is good for tiny processor like pic16 or pic18, that has problems to carry out a multiply each PWM cycle. At PIC24 or dsPIC has a fast 16-Bit hardware multiplier and can use a single table, scaling the output. The voltage controller should use a measurement of averaged rectified value or even rms to adjust the duty cycle.

I am trying to implement this in assembly in PIC16F73.
Can you elaborate this method little bit more?
Thanks
 

My assumption holds that PIC16 has difficulties to multiply table values on the fly during pwm generation. So the multiple table method suggested in post #5 would be a more promising solution.
 
Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top