CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

Triac Gate Pulses

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
pop



Joined: 18 Sep 2004
Posts: 22

View user's profile Send private message

Triac Gate Pulses
PostPosted: Tue Feb 15, 2005 5:55 pm     Reply with quote

Hi,

I am working on a project where I independently control two triacs
(pins B1 and B2) with 16F877 microcontroller. Before using an actual
microcontroller I thoroughly tested my triac firing code on a MPLAB
simulator just to work out any possible logic problems. I have also
ensured that if two firing angles are within three degrees of each
other (e.g. 39� and 42�), that both triacs would fire at same time.
(e.g. in this case 39�)

Anyway to the problem:


Today, I've connected the signal generator (square pulse, period=1/60
sec, 5 V amplitude) to PIN B0.This was only a test run before I would
connect a zero crossing circuit. Also I did not connect the
optocouplers yet (MOC 3023), as I wanted to see my triggering pulses
directly out of pins B1 and B2.

When I looked at my B1 and B2 (gate firing) outputs, my firing pulses
(100usec wide as set in program) fired at correct firing
angles.However, I also got some small-width (~5usec to 10 usec) pulses before and after actual gate trigger pulse.

Does anybody know why these small pulses occur? Is it because the two
triac firing pins are next to each other?

How can I get rid of these small pulses as I am afraid that they might
trigger a triac?

I looked at a datasheet for MOC3023 optocoupler but I am not sure if
these small pulses will be problematic?

Thank you.

P.S. Unfortunately I could not post the osciloscope image on this website, as there seems to be no way to upload an attachment and I do not have a website. If anybody needs an image I can send it.
Mark



Joined: 07 Sep 2003
Posts: 2838
Location: Atlanta, GA

View user's profile Send private message Send e-mail

PostPosted: Tue Feb 15, 2005 9:09 pm     Reply with quote

Well, you didn't post any code so here is the best I'll give you.

Keep it simple, only fire one of the pulses and see what happens. That will answer you question if the other signal is affecting the one that you are looking at.

Toggle an ouput pin inside your external interrupt routine. Take a look at this signal in comparison to the input signal. They should match unless you are getting some false triggers by the input.

Like I said before, no code means we can't tell you much.
Guest








PostPosted: Wed Feb 16, 2005 12:19 pm     Reply with quote

I am sorry for not posting the code. Mark, I did the code as based on your earlier suggestion as well as based on another code that I found on this website. I will give your suggestions a try and that might solve the problem.

Anyway here is the code for independent firing of two triacs.
Note that the zero cross pulse out of LM311 begins at ~0 sec and ends at ~8.33msec. Also this is my test code

Code:

#include <16f877.h>

#fuses HS,NOWDT,NOPROTECT
//#device PIC 16F877 ADC=8
#use delay(clock=20000000)
#use rs232(BAUD=9600,XMIT=PIN_C6,RCV=PIN_C7)
#opt 9

// Reserve top 255 bytes of memory for the bootloader
#ORG 0x1F00,0x1FFF{}

//the folowing 2 lines are currently used only for testing!
#define FIRING_ANGLE_0 9260  //40�
#define FIRING_ANGLE_1 20833 //90�


/******************************Global Variables***********************/

unsigned int STATUS_ANGLE=0;
#define PULSE_WIDTH 463  //463 counts = 2 deg or 92.6usec


#bit INTEDGE = 0x81.6 // Ext INT edge select bit (e.g. interrupt on rising or falling edge)
            //see p.21 of 16F877 datasheet




short int ANGLES_CHANGED = 0;
short int GATE_HIGH = 0;
short int FIRST_PULSE_DONE = 0;
short int ALL_FIRING_DONE = 0;
short int INT_EDGE_TOGGLED = 1;

/******************************End Global Variables*******************/

/******************************Non-Interrupt Function Declarations*************/

void compareAngles(signed long, signed long);


/******************************END Non-Interrupt Function Declarations**********/




#int_CCP1 //this interrupt occurs when "timer1 == ccp_1"
void fireTriacs()
{

   if (STATUS_ANGLE == 0) //fire both triacs at the same time
   {
      if(!GATE_HIGH)
      {
         //turn-on both gates
         output_high( PIN_B1 );
         output_high( PIN_B2 );
         GATE_HIGH=1;
         ccp_1+=PULSE_WIDTH;
      }
      else //i.e. ( GATE_HIGH == 1 )
      {
         //turn-off both gates
         output_low( PIN_B1 );
         output_low( PIN_B2 );
         GATE_HIGH=0;

         ALL_FIRING_DONE=1;
      }
   }
   if (STATUS_ANGLE == 1) //fire triac 1 first and triac 2 second
   {
      if(!GATE_HIGH)
      {
         if(!FIRST_PULSE_DONE)
         {
            output_high( PIN_B1 );
            ccp_1+=PULSE_WIDTH;
            GATE_HIGH=1;
         }
         else
         {
            output_high( PIN_B2 );
            ccp_1+=PULSE_WIDTH;
            GATE_HIGH=1;
         }
      }
      else //e.g. GATE_HIGH == 1
      {
         if(!FIRST_PULSE_DONE)
         {
            output_low( PIN_B1 );
            GATE_HIGH=0;
            FIRST_PULSE_DONE=1;
            ccp_1=FIRING_ANGLE_1;
         }
         else
         {
            output_low( PIN_B2 );
            GATE_HIGH=0;
            FIRST_PULSE_DONE=0;

            ALL_FIRING_DONE=1;
         }   
      }
   }
   if (STATUS_ANGLE == 2) //fire triac 2 first and triac 1 second
   {
      if(!GATE_HIGH)
      {
         if(!FIRST_PULSE_DONE)
         {
            output_high( PIN_B2 );
            ccp_1+=PULSE_WIDTH;
            GATE_HIGH=1;
         }
         else
         {
            output_high( PIN_B1 );
            ccp_1+=PULSE_WIDTH;
            GATE_HIGH=1;
         }
      }
      else //e.g. GATE_HIGH == 1
      {
         if(!FIRST_PULSE_DONE)
         {
            output_low( PIN_B2 );
            GATE_HIGH=0;
            FIRST_PULSE_DONE=1;
            ccp_1=FIRING_ANGLE_0;
         }
         else
         {
            output_low( PIN_B1 );
            GATE_HIGH=0;
            FIRST_PULSE_DONE=0;

            ALL_FIRING_DONE=1;
         }   
      }
   }
}


#int_ext //pin RB0 EXT interrupt
void zeroCross()
{
   ALL_FIRING_DONE=0; //reset this flag because the new firing cycle has just begun!
   INT_EDGE_TOGGLED=0; //reset this flag
      
   //load CCP1 and then reset timer1
   switch(STATUS_ANGLE)
   {
      case 0: ccp_1=FIRING_ANGLE_0;
         break;
      case 1: ccp_1=FIRING_ANGLE_0;
         break;
      case 2: ccp_1=FIRING_ANGLE_1;
         break;
      default://this is an error condition!
         //maybe set ccp_1 to 150 deg (34722 counts) for minimum power
         ccp_1 =34722;
         break;
   }
   set_timer1(0);      
}

void init_PIC() //initialize PIC hardware
{
   set_tris_b(0b00000001); //PIN_B0 is external interrupt input.
            //PIN_B1 is for triac1
            //PIN_B2 is for triac2
   

   set_timer1(0); //The following 2 lines ensure that no accidental
               //CCP interupt occurs
   /*a false interrupt occurred before the pic had fully initialised
   with the code due to the fact that on boot up some registers can
   have any value. See the Microchip data sheet for the device.*/

   ccp_1=65535; //ensures that no false CCP interrupt occurs!
   ext_int_edge(L_TO_H); //initialize L_to_H by default!
   output_low( PIN_B1 );
   output_low( PIN_B2 );
   setup_ccp1( CCP_COMPARE_INT );
   enable_interrupts( INT_EXT );
   enable_interrupts( INT_CCP1 );
   setup_timer_1( T1_INTERNAL|T1_DIV_BY_1 );
   enable_interrupts( GLOBAL );                      //set this up last!
}



main()
{
   init_PIC();

   ANGLES_CHANGED = 1; //This variable changes whenever software or user decide
           //   to change power in heating cables. It is placed here for
           //   TESTING purposes only!

   compareAngles( FIRING_ANGLE_0, FIRING_ANGLE_1 );
   
   while(1)
   {
      //Do something like the following:
      //tempControl(); Sets newAngle1, newAngle2 and ANGLES_CHANGED
      
      //lcdControl();

      if ((ALL_FIRING_DONE == 1) && (INT_EDGE_TOGGLED == 0))
      {
         INTEDGE = !INTEDGE; //toggle interrupt edge to give precise zero cross detection
         INT_EDGE_TOGGLED = 1;
      }

      
      if((ALL_FIRING_DONE == 1) && (ANGLES_CHANGED == 1))
      {
         //Do something like:
         //FIRING_ANGLE_0=newAngle1;
         //FIRING_ANGLE_1=newAngle2;
         
         //change the STATUS_ANGLE
         compareAngles( FIRING_ANGLE_0, FIRING_ANGLE_1 );
         ANGLES_CHANGED =0;
      }
   }
}



/************************************************************************
* Function: void compareAngles(signed long,signed long);
* Parameters: 2 Firing Angles (long is a 16bit integer. Firing angles are 16 bit values)
* Returns: void
* Purpose: Compare 2 firing angles and set STATUS_ANGLE variable. This is done
*      to ensure that the microcontroller never misses a triac firing.
*      Currently the resolution is at 3 deg or 695 clock cycles. This means
*      that if 2 angles are within 3 degrees of each other, then the 2 triacs
*      will be fired at the same time. Note resoltuion must be larger than PULSE_WIDTH!
*
*
* Modified: Nov 21, 2004
*
*************************************************************************/

void compareAngles(signed long angle1,signed long angle2)
{

   if (angle1 < (angle2 - 695))
   {
      STATUS_ANGLE=1;
   }
   else if (angle2 < (angle1 - 695))
   {
      STATUS_ANGLE=2;
   }
   else
   {
      STATUS_ANGLE=0;
   }
}


Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group