PIC 202 (pwm)

xxalexx at ix.netcom.com xxalexx at ix.netcom.com
Sun Jul 12 03:56:20 GMT 1998


This class illustrates pwm, for use on PIC chips with no built in pwm 
Note in class PIC 201 there was a rounding error should be t%100 >=50
New items are    #use fast_io( port letter )    this is defined by 
CCS compiler to directly access ports. Port letters can be A or B for 
a 16F84
  #byte  any_name  port_ number          This defines a byte  
variable any_name to a port number.  For all PICs 5 is port A  6 is 
port B.  If you change this value, you directly turn on or off the  
port bits, example any_name=3  =11000000 binary will turn I/0 pins B0 
and B1 on.  Also the first functions other than main() are 
written. Consult a C book in your local public libary for more 
information. The CCS compilier has built in functions for delays 
delay_us(a_number) and  delay_ms(a_number).  You can type in constant
numbers 0-65535 or use variables if number is 8 bit integer 0-255 
Function vdelay was written to handle variable 16 bit numbers;
pointers and address are beyond the scope of this class.
To add or subtract 1 from a variable you can use --a_variable; or 
++a_variable;  instead of a_variable=avariable+1;
The function    set_trisB( a_number );     sets up the bit registers 
as input=1 or output=0.   If you want B0 and B1 inputs and B2-B7
outputs.  a_number would = 3 = 11000000 
Note this function must called if using fast i/o

 //ex3.c pwm  by alex c peper 07-11-98
 #include<c:\picc\bin\examples\16F84.h>  
 #fuses XT, NOWDT, NOPROTECT
 #use delay(clock = 4000000) 
 #use rs232(baud=9600, xmit=PIN_A0, rcv=PIN_A1, invert)

 //acess port bits directly
 #use fast_io(B) 

 //defines port B adress 6  as a variable for direct port  access   
 #byte pwm_chan = 6

// 16 bit (0-65535us) delay timer function 
 vdelay( long period )
 {
	  int	phi, plo;

	 plo= period;	// get the lower byte of 16 bit long 
 	phi= *( &period+1 );	//get the upper byte of 16 bit long
            			 //note * is a pointer   & is address
  	while( phi != 0 )	// count down upper byte
  	{
  		delay_us(256);		//delay each upper count 256us
  		--phi;
 	}
 	delay_us(plo);// then delay lower byte 
 }	

 //sends pwm to port 
 //dc= 0-10000 (0-100.00 %) resolution( min=1us max=6us ) 
 //period= 10000-60000us in inc. of 10000us (hz=100 ...... 16.7)  
 //duration = 1-255 pwm cycles (10ms - 15.3 sec)
 //chan =  port B output logic    
 //calls function vdelay for timing 
 pwm(long dc, long period, int duration, int chan)
 { 
	 int	scale; // scales dc as function of period(1-6)
  	long 	dc_off;// sets dc off time 		

	 scale = (int)( period/10000 );
 	dc = dc*scale;  
  	dc_off = period-dc;
  	while( duration != 0 )
  	{
   		--duration;
   		pwm_chan=chan;	//turn on chan bit(s)
   		vdelay( dc );
 		 pwm_chan=0;		 //turn off all port bits 
  		vdelay( dc_off );
	 }		
}					

 main() 
 {
         long	 duty,period;
 	int	 duration;
 	int	 cyl;

 //define port B I/O  0=outputs
 // this must be done if using fast I/O or #defining a port 
  set_tris_B(0);
 printf("Hello PWM\n\r");
 duty=5000; 	//= 50%
 period=10000;	//=10ms = 100Hz
 duration=200;	//=200*10ms=2sec.
 cyl = 1;		// select 0-7 PWM output chanels
 while(TRUE) 
	  pwm(duty,period,duration,cyl);
 }



More information about the Diy_efi mailing list