Répondre à la discussion
Affichage des résultats 1 à 25 sur 25

Besoin de 3 PWM avec un PIC



  1. #1
    HULK28

    Question Besoin de 3 PWM avec un PIC


    ------

    Salut à tous, j'ai besoin dans un montage d'utiliser 3xPWM pour piloter 3 charges de 100mA.
    Jusque là tout va bien.
    Utilisant des µC Microchip (16f87X de préférence), je cherche quelqu'un qui aurait déjà réfléchit au problème puisque les 16f87x on au max 2xPWM.
    Soit une astuce, soit carrément un autre PIC.
    0%<PWM1<100%
    Idem pour PWM2 et PWM3.
    Fréquence de l'ordre de 150Hz.
    Merci d'avance pour vos suggestions.

    HULK

    -----

  2. Publicité
  3. #2
    T-Bot

    Re : Besoin de 3 PWM avec un PIC

    Pic 18f2431

  4. #3
    joe_d

    Re : Besoin de 3 PWM avec un PIC

    Pour une freq de 150Hz je pense pas que t'as besoin de blocks dedies pwm pour faire du pwm. Meme avec un 16f628, t'as 3 timers, tu peux generer assez d'interruptions et faire des bsf/bcf sur les ports Aet B. Moi j'ai fait du pwm avec le 16f84 comme ca sans probleme.

    Salut,
    Joe.

  5. #4
    mictour

    Re : Besoin de 3 PWM avec un PIC

    bonjour HULK,
    Dans mes "archives" j'ai ce lien :
    http://www.dattalo.com/technical/software/pic/pwm8.asm
    Petit programme astucieux !
    Bonne prog.

    mictour.

  6. #5
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    merci à toi Mictour pour ce bout de soft.
    Je vais de ce pas l'adapter au PIC16F877 et faire une routine en C plus commode à manipuler.

    Joe_d as-tu quelque chose à proposer, sinon merci pour ta réponse.

    HULK

  7. A voir en vidéo sur Futura
  8. #6
    DavidDB

    Re : Besoin de 3 PWM avec un PIC

    Salut,

    Si la solution de Mictour ne te convient pas, je peux aussi te fournir une routine pour obtenir un troisième PWM software qui utilisera l'interruption du Timer2 sur base du PWM hardware.

    Par contre, c'est de l'Assembleur et non du C...

    David.

  9. Publicité
  10. #7
    DavidDB

    Re : Besoin de 3 PWM avec un PIC

    Re,

    En annexe une méthode simple pour faire un PWM software à partir du PWM hardware du PIC.

    David.
    Fichiers attachés Fichiers attachés

  11. #8
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    salut DavidDB, merci pour ton offre, je veux bien voir ta routine, sachant que les 3 PWM doivent être totalement indépendante.
    Pour ce qui est de l'assembleur ça ne me dérange pas du tout.


    hulk

  12. #9
    DavidDB

    Re : Besoin de 3 PWM avec un PIC

    Attention,

    Car dans mon exemple, la fréquence est identique à tous les PWM...

    Par contre, le rapport cyclique est évidemment modifable pour tous les PWM.

    David.

  13. #10
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    C'est bien de voir un prog si bien commenté, c'est si rare.

    La fréquence des 3 PWM est identiques dans mon appli, donc pas de soucis ton prog peux coller.

    L'avantage effectivement c'est que je peux utiliser un PIC16F877, donc pas besoin d'approvisionner un autre modèle.
    Je vous ferais connaitre ma routine en C, quand je l'aurais transposée.

    A+ et merci pour votre attention.


    hulk

  14. #11
    ABN84

    Re : Besoin de 3 PWM avec un PIC

    bonsoir,
    je ressorts ce topic des oubliettes.
    salut HULK, est ce que tu as reussi à faire la routine en question?
    "Engineering is the art of making what you want from what you get"

  15. #12
    ABN84

    Re : Besoin de 3 PWM avec un PIC

    un petit up.
    "Engineering is the art of making what you want from what you get"

  16. Publicité
  17. #13
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    Bin vi.
    Pourquoi?
    Le génie est fait d'1 pour cent d'inspiration et de 99% pour cent de transpiration. Edison

  18. #14
    ABN84

    Re : Besoin de 3 PWM avec un PIC

    Euh! c'est juste par curiosité, je n'ai aucune arriere pensée
    ça s'interprete comment ça:
    Citation Envoyé par HULK28 Voir le message
    "Engineering is the art of making what you want from what you get"

  19. #15
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    J'avais donc bien compris, tu veux donc le prog, y avait qu'à demander

    Je t'enverrai ça ce week end, n'hésite pas à me relancer au cas où.
    Le génie est fait d'1 pour cent d'inspiration et de 99% pour cent de transpiration. Edison

  20. #16
    FSE

    Re : Besoin de 3 PWM avec un PIC

    bonsoir
    voir le site
    http://www.digitalspirit.org/wiki/pr...tionde24servos
    Il y a plein de sulutions intéressantes sans faire appel à 24 PWM

  21. #17
    Melodie Nelson

    Question Re : Besoin de 3 PWM avec un PIC

    Salut Hulk.

    Je ressors moi aussi ce vieux sujet car je suis moi aussi intéressé par une PWM avec mon PIC16F877. Pour l'instant je n'en ai besoin que d'une pour commander 2 LM3914 qui vont commander les 2 bar-graph à LED.
    Puis je piloterai sûrement un moteur ensuite.
    Je ne sais pas du tout comment configurer le port C pour faire ça. Ni lire l'assembleur....

    Y'a -t- il une solution à mon souchis ?

    Merci

  22. #18
    gedonet

    Re : Besoin de 3 PWM avec un PIC

    Bonjour
    La serie des pics 16F737, 747, 767 et 777 disposent en hard de 3 pwm.
    Gilles

  23. Publicité
  24. #19
    Melodie Nelson

    Re : Besoin de 3 PWM avec un PIC

    A ??
    J'avoue n'en voir que 2 sur le datasheet : RC1 et RC2 pour le 16f877

    Sansa mon soucis vient plus du côté software, comme j'ai dit au-dessus


  25. #20
    FSE

    Re : Besoin de 3 PWM avec un PIC

    Bonsoir
    Il y a 6 mois j'ai indiqué les références d'un site "24servos" pour répondre au même souci
    Je m'en suis iinspiré : avec un PIC628 on gère 5 servos sans utiliser de PWM

  26. #21
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    Salut,

    voici un programme que j'ai en cours de réalisation mais pas encore totalement fonctionnel, je vous le livre en l'état, ça vous fera une base de départ.

    Code:
    /*==============================================================================
    
     Dimmer 3 PWM pour leds de puissance
    
     Composant : PIC16F628A
    										
     Auteur  : HULK28
    
    ==============================================================================*/
    
    #include	<pic.h>
    #include	"ecl_pwm.h"	// Définitions spécifiques
    
    
    /*=============================================================================
    
     |Historique	| Date			| Modification	
     ------------------------------------------------------------------------------
     | V1.0		| 12/04/2007		| - Date de création
     ------------------------------------------------------------------------------
     Compilateur HitechC                                                                                              
     Fichier c			: ecl_pwm.c	
     Fichier définition		: ecl_pwm.h
     Fichier définition PIC	: pic.h -> pic16f6x.h
     Fichier Hex		: ecl_pwm.hex
    
    ===============================================================================
    
    			PRÉSENTATION DU PROGRAMME
    
     Ce programme tourne sur un PIC16F628 			
                                                                                                   
     Les entrées / Sorties sont définies comme suit :
                                                                                                        
    * Sorties :	- Sortie PWM (0-255) S1	---> RA6
    		- Sortie PWM (0-255) S2	---> RA7
    		- Sortie PWM (0-255) S3	---> RB3
    
    * Entrées :          - Bouton poussoir UP	---> RB6
    	            - Bouton poussoir DOWN	---> RB7
    
    	* Entrée ANA :	aucune
    
    	* E/S :
    
    ===============================================================================
    
     Tous les "timming" sont basés sur un résonnateur de fréquence 4 Mhz.
     Le temps de cycle par instruction est de 1 µs.
    
     Toutes les données utilisées sont exprimées en décimal, sauf celles
     spécifiées.	                                                
    
    ==============================================================================*/
    
    /******************************************************************************/
    ushort	Compteur62us ;
    uchar	Flag62us ;
    
    ushort	ValeurPwmS1 ;
    ushort	ValeurPwmS2 ;
    ushort	ValeurPwmS3 ;
    
    uchar	Valeur3Pas ;
    
    uchar 	CompteurPression ;
    uchar 	CombinaisonBPs ;
    
    /******************************************************************************
                    Déclaration des prototypes de fonctions
    *******************************************************************************/
    
    void init_pic(void);
    void interrupt traite_int(void);
    void clock_pic(void);
    
    void DelayMs(uchar cpt) ;
    void init_var(void) ;
    
    void init_pwm(void) ;
    void stop_pwm(void) ;
    void setDC_pwm(ushort dc) ;
    
    uchar TestBPs(void) ;
    void GestionBPs(void) ;
    
    /******************************************************************************
    	        	Temporisation en millisecondes
    *******************************************************************************/
    
    void DelayMs(uchar cpt)
    {
    	ushort t ;
    	while (cpt != 0)
    	{
    		CLRWDT() ;
    		-- cpt ;
    		t = 112 ;
    		while (t !=0)	-- t ;
    	}
    }
    
    /******************************************************************************
    		        Traitement des interruptions
    ******************************************************************************/
    void interrupt traite_int(void)
    {
    	if(TMR1IF)
    	{
    		TMR1IF = 0 ;
     	 	Flag62us = 1 ;
    		TMR1H = 0xFF ;
    		TMR1L = 0xC1 ;	// 0xFFFF - 0xFFC1 = 62 => 62 x 1 µs = 62 µs
    	}
    
    }
    
    /******************************************************************************
    		        Initialisation du PIC
    ******************************************************************************/
    void init_pic(void)
    {
    	// Configuration du module CCP
    	CCP1CON = 0x00 ;		// module CCP1 désactivée
    
    	// Configuration du port B
    	RBPU = 0 ;			// active pull up
    	RBIE = 0 ;
    
    	// Configuration des I/O
    	PwmS1 = 0 ;			// à l'init.	S1 = 0
    	PwmS2 = 0 ;			// 		S2 = 0
    	PwmS3 = 0 ;			// 		S3 = 0
    	TRISA = ConfigIOPortA ;
    	TRISB = ConfigIOPortB ;
    
    	// Timer 0 (8 bits) est utilisé pour le wachtdog à 2,3 s.
    	T0CS = 0 ;		// Clock interne
    	PSA = 1 ;		// timer0 = Wachtdog
    	PS2 = 1 ;		// \
    	PS1 = 1 ;		//  => 111 + WDT => 18 ms x 128 = 2,304 s
    	PS0 = 1 ;		// /
    
     // Timer 1 (16 bits) est utilisé pour l'horloge: base de 62 µs.
     // Quartz 4 Mhz => 1 instruction = 1 µs
    	T1CON = 0x00 ;		// Prédivision de l'horloge par 1
    	TMR1H = 0xFF ;
    	TMR1L = 0xC1 ;		// 0xFFFF - 0xFFC1 = 62 => 62 x 1 µs = 62 µs
    	TMR1ON = 1 ;		// On lance le timer 1
    	TMR1IE = 1 ;		// On autorise les interruptions du timer 1
    
    	// Autorisation des interruptions
    	PEIE = 1 ;			// Autorisation des IT peripherique
    	GIE = 1 ;			// Autorisation général des IT
    }
    
    /****************************************************************
    		Initialisation des variables globales
    ****************************************************************/
    void init_var(void)
    {
    	Flag62us = 0 ;
    	Compteur62us = 0 ;		// Raz compteur clock
    
    	ValeurPwmS1 = 0 ;
    	ValeurPwmS2 = 0 ;
    	ValeurPwmS3 = 0 ;
    
    	Valeur3Pas = 0 ;
    }
    
    /****************************************************************
    		Initialisation du périphérique PWM
    ****************************************************************/
    void init_pwm(void)
    {
       CCP1CON = 0x00 ;      // module off
       TMR2 = 0 ;	        // raz timer2 value
       PR2 = 0x7C ;	        // PR2 = 124 --> f = 500 Hz
       CCPR1L = 0 ;	        // Duty cycle = 0 à l'init
       TRISB3 = 0 ;	        // RB3 = output
       T2CKPS1 = 1 ;           // Prescaler = 1:16
       T2CKPS0 = 1 ;
       CCP1CON = 0x0C ;     // Mode PWM 10 bits + init two LSBs of PWM duty cycle at 0
       TMR2ON = 1 ;	       // Timer2 ON
    }
    
    /****************************************************************
    		Arrête le périphérique PWM
    ****************************************************************/
    void stop_PWM(void)
    {
    	RB3 = 0 ;
    	TMR2ON = 0 ;
    	CCP1CON = 0x00 ;
    }
    
    /****************************************************************
    	Charge le rapport cyclique PWM [0-1023] -> [0-100%]
    ****************************************************************/
    void setDC_PWM(ushort dc)
    {
    CCP1CON = CCP1CON & 0b11001111 ;		// clear CCP1CON<5:4>
    CCP1CON = CCP1CON | ((dc << 4) & 0b00110000) ;	// set the two LSBs duty cycle
    CCPR1L = dc >> 2 ;				// set the eight MSBs duty cycle
    }
    
    /****************************************************************
    		Gestion horloge du PIC
    ****************************************************************/
    void clock_pic(void)
    {
    	Flag62us = 0 ;
    
    	// ValeurPwmSx  [0-256]
    	// Compteur62us [0-256]
    
    	if (ValeurPwmS1 == 0)				PwmS1 = 0 ;
    	else
    	{
    		if 	(Compteur62us == 0)		PwmS1 = 1 ;			
    		else if (Compteur62us == ValeurPwmS1)	PwmS1 = 0 ;
    	}
    
    	if (ValeurPwmS2 == 0)				PwmS2 = 0 ;
    	else
    	{
    		if 	(Compteur62us == 0)		PwmS2 = 1 ;
    		else if (Compteur62us == ValeurPwmS2)	PwmS2 = 0 ;
    	}
    
    	Compteur62us = Compteur62us + 8 ;
    
    	if (Compteur62us == 256)	Compteur62us = 0 ;// période = 2 ms
    
    }
    
    /****************************************************************
    	Test périodiquement l'action sur les boutons poussoirs
    ****************************************************************/
    uchar TestBPs(void)
    {
    	CompteurPression = 0 ;
    	CombinaisonBPs = AUCUNE ;
    
    	while (!BoutonUp)
    	{
    		DelayMs(10) ;
    		++CompteurPression ;
    		if (!BoutonDown)		CombinaisonBPs = UP_ET_DOWN ;
    		else				CombinaisonBPs = UP ;
    		if (CompteurPression > 200)	break ;		// expiration
    	}
    
    	while (!BoutonDown)
    	{
    		DelayMs(10) ;
    		++CompteurPression ;
    		if (!BoutonUp)			CombinaisonBPs = UP_ET_DOWN ;
    		else				CombinaisonBPs = DOWN ;
    		if (CompteurPression > 200)	break ;		// expiration
    	}
    
    	return(CombinaisonBPs) ;
    }
    
    /****************************************************************
    		Gestion des boutons poussoirs
    ****************************************************************/
    void GestionBPs(void)
    {
        switch (CombinaisonBPs)
    	{
    	case UP :
    		if (CompteurPression > 100)
    			{
    			if (ValeurPwmS1 < 256)	ValeurPwmS1 = ValeurPwmS1 + 8 ;
    			if (ValeurPwmS2 < 256) 	ValeurPwmS2 = ValeurPwmS2 + 8 ;
    			if (ValeurPwmS3 < 256) 	ValeurPwmS3 = ValeurPwmS3 + 8 ;
    			}
    		else
    			{
    			if (ValeurPwmS1 < 256)	ValeurPwmS1 = ValeurPwmS1 + 32 ;
    			if (ValeurPwmS1 < 256)	ValeurPwmS2 = ValeurPwmS2 + 32 ;
    			if (ValeurPwmS1 < 256)	ValeurPwmS3 = ValeurPwmS3 + 32 ;
    			}
    			break ;
    	case DOWN :
    		if (CompteurPression > 100)
    			{
    			if (ValeurPwmS1 >  7)	ValeurPwmS1 = ValeurPwmS1 - 8 ;
    			if (ValeurPwmS2 >  7) 	ValeurPwmS2 = ValeurPwmS2 - 8 ;
    			if (ValeurPwmS3 >  7) 	ValeurPwmS3 = ValeurPwmS3 - 8 ;
    			}
    			else
    			{
    			if (ValeurPwmS1 > 31)	ValeurPwmS1 = ValeurPwmS1 - 32 ;
    			if (ValeurPwmS1 > 31)	ValeurPwmS2 = ValeurPwmS2 - 32 ;
    			if (ValeurPwmS1 > 31)	ValeurPwmS3 = ValeurPwmS3 - 32 ;
    			}
    			break ;
    	case UP_ET_DOWN :
    		if (CompteurPression > 100)
    			{
    				switch (Valeur3Pas)
    				{
    					case 0 :
    						Valeur3Pas = 50 ;	// 50%
    						ValeurPwmS1 = 128 ;
    						ValeurPwmS2 = 128 ;
    						ValeurPwmS3 = 128 ;
    						break ;
    					case 50 :
    						Valeur3Pas = 100 ;	// 100%
    						ValeurPwmS1 = 256 ;
    						ValeurPwmS2 = 256 ;
    						ValeurPwmS3 = 256 ;
    						break ;
    					case 100 :
    						Valeur3Pas = 0 ;	// 0%
    						ValeurPwmS1 = 0 ;
    						ValeurPwmS2 = 0 ;
    						ValeurPwmS3 = 0 ;
    						break ;
    				}
    			}
    			break ;
    	}
    
    	// S1 est mis à jour par ValeurPwmS1 --> Timer1
    	// S2 est mis à jour par ValeurPwmS2 --> Timer1
    	// S3 est mis à jour par ValeurPwmS3 --> PWM
    
    	setDC_PWM((ValeurPwmS3 * 4)-1) ;    // on se ramène à l'échelle [0-1023]
    
    	while (TestBPs() != AUCUNE)  // attent le relâchement
            CLRWDT() ;
    
    	Compteur62us = 0 ;
    
    }
    
    /****************************************************************
    			Programme principal
    ****************************************************************/
    main()
    {
    	CLRWDT() ;
    
    	init_pic();     // init registres
    
    	init_var() ;    // init variables globales
    	
    
    	init_pwm() ;    // init PWM hard
    	setDC_PWM((ValeurPwmS3 * 4)-1) ;
    
    	while(1)
    	{
    
    		CLRWDT() ;       // raffraichissement watchdog
    
      		if (Flag62us)   // gestion 62 µs
                    clock_pic();
    
    
    		if (TestBPs() != AUCUNE)  // gestion des boutons poussoirs
                    GestionBPs() ;
    	}
    }
    Dernière modification par HULK28 ; 20/07/2007 à 22h51.
    Le génie est fait d'1 pour cent d'inspiration et de 99% pour cent de transpiration. Edison

  27. #22
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    Code:
    // Définitions spécifiques
    
    /********************************************************************
    *   	  		    						       *
    *   Ecrit en C pour être compilé avec HI-TECH, testé avec MPLAB                                   *
    *********************************************************************
    *********************************************************************
    *   Fichier : ecl_pwm.h                                     	    	                                 *
    *   Date: 12/07/2006                                                                                              *
    *   Version: 1.00                                             	                                              *
    *********************************************************************
    *   Fonctions:                                                                                                        *
    *                                                                                                                         *
    *********************************************************************
    *   Revision History:                                                                                                *
    *      V1.00 - Version beta    					                    *
    ********************************************************************/
    
    /*====================================================================
    		 -----= Predefined instructions =-----
    ====================================================================*/
    // Predefined instructions
    #define	PORTBIT(adr, bit)	((unsigned)(&adr)*8+(bit))
    #define	NOP()	asm("nop")
    #define FALSE	0
    #define TRUE	!FALSE	
    #define BYTE	unsigned char	/* sizeof(BYTE) must == 1 */
    #define uchar	unsigned char
    #define ushort      unsigned short
    #define ulong	unsigned long
    
    // Descriptions des différentes entrées et sorties
    static bit	PwmS1          @	PORTBIT(PORTA, 6) ;	// sortie S1 PWM
    static bit	PwmS2          @	PORTBIT(PORTA, 7) ;	// sortie S2 PWM
    static bit	PwmS3          @	PORTBIT(PORTB, 3) ;	// sortie S3 PWM
    static bit	BoutonUp	       @   PORTBIT(PORTB, 6) ;	// entrée poussoir UP
    static bit	BoutonDown   @	PORTBIT(PORTB, 7) ;	// entrée poussoir DOWN
    
    
    // Remarque: 1 = entrée, 0 = sortie
    #define		ConfigIOPortA	0x3F	// RA6 et RA7 = sorties PWM, le reste en entrée
    #define		ConfigIOPortB	0xFF	// port B en entrée
    
    #define		AUCUNE		0x00
    #define		UP		0x01
    #define		DOWN		0x02
    #define		UP_ET_DOWN	0x03
    Dernière modification par HULK28 ; 20/07/2007 à 23h15.
    Le génie est fait d'1 pour cent d'inspiration et de 99% pour cent de transpiration. Edison

  28. #23
    Melodie Nelson

    Re : Besoin de 3 PWM avec un PIC

    Merci beaucoup, nikel

    Sauf que j'utilise Mplab 7.4 avec CCS, et apparemment la syntaxe est différentes, mais j'ai trouvé un exemple avec CCS donc maintenant c'est bon merci.

    Biz

  29. #24
    HULK28

    Re : Besoin de 3 PWM avec un PIC

    Peut-être que d'autres seraient intéressés par le prog CCS, pense à eux.
    Le génie est fait d'1 pour cent d'inspiration et de 99% pour cent de transpiration. Edison

  30. Publicité
  31. #25
    Melodie Nelson

    Re : Besoin de 3 PWM avec un PIC

    Voilou, gérer une PWM avec Mplab 7.4 + CCS :

    Code:
    int value ;
    
    setup_ccp1(CCP_PWM);   // Configure CCP1 as a PWM
    
              //   The cycle time will be (1/clock)*4*t2div*(period+1)
           //   In this program clock=10000000 and period=127 (below)
              //   For the three possible selections the cycle time is:
    	    //     (1/10000000)*4*1*128 =  51.2 us or 19.5 khz
    	    //     (1/10000000)*4*4*128 = 204.8 us or 4.9 khz
    	    //     (1/10000000)*4*16*128= 819.2 us or 1.2 khz
    
       
    setup_timer_2(T2_DIV_BY_1, 127, 1);
                    
           
        
    set_pwm1_duty(value);         // This sets the time the pulse is
                                 // high each cycle.  We use the A/D
                                 // input to make a easy demo.
                                 // the high time will be:
                                 //  if value is LONG INT:
                                 //    value*(1/clock)*t2div
                                 //  if value is INT:
                                 //    value*4*(1/clock)*t2div
                                 // for example a value of 30 and t2div
                                 // of 1 the high time is 12us
                                 // WARNING:  A value too high or low will
                                 //           prevent the output from
                                 //           changing.
      }
    
    }
    good luck

Sur le même thème :

Discussions similaires

  1. Generer signal PWM precis avec un PIC
    Par black_is_beautiful dans le forum Électronique
    Réponses: 9
    Dernier message: 06/04/2012, 20h05
  2. Pwm Pic 18f4550
    Par Lethargy dans le forum Électronique
    Réponses: 3
    Dernier message: 09/03/2009, 14h57
  3. pwm sur pic
    Par alainav1 dans le forum Électronique
    Réponses: 5
    Dernier message: 07/12/2007, 00h31
  4. pwm sur pic
    Par noisyboxes dans le forum Électronique
    Réponses: 3
    Dernier message: 28/04/2007, 20h07
  5. Besoin d'aide sur un montage avec pic 16F876
    Par laatysha dans le forum Électronique
    Réponses: 17
    Dernier message: 03/02/2006, 14h25
Découvrez nos comparatifs produits sur l'informatique et les technologies.