0
\$\begingroup\$

I am working on dsPic33EP512GM604 microcontroller.

I have written a small program to light a tower lamp with 3 LEDs (RED, YELLOW, GREEN).

Below is the circuit diagram :

enter image description here

As shown in the circuit diagram :

RED led is connected to pin<20> RA1

YELLOW led is connected to pin<19> RA0

GREEN led is connected to pin<15> RB15

Below is my sample code :

// Tower LAMP
#define LAMP_ON      1  //  LAMP ON 
#define LAMP_OFF     0  //  LAMP OFF

#define RED             0   //  Color Code
#define YELLOW          1   //  Color Code
#define GREEN           2   //  Color Code
#define DEFAULT_LAMP    4   //  Color Code 

#define RED_LIGHT       PORTAbits.RA1       // Output : RED Light
#define YELLOW_LIGHT    PORTAbits.RA0       // Output : Yellow Light
#define GREEN_LIGHT     PORTBbits.RB15      // Output : Green Light


#pragma config ICS = PGD3           // ICD Communication Channel Select bits (Communicate on PGEC1 and PGED1)
#pragma config JTAGEN = OFF         // JTAG Enable bit (JTAG is disabled)

// FPOR
#pragma config BOREN = ON           // Brown-out Reset (BOR) Detection Enable bit (BOR is enabled)
#pragma config ALTI2C1 = OFF        // Alternate I2C1 pins (I2C1 mapped to SDA1/SCL1 pins)
#pragma config ALTI2C2 = OFF        // Alternate I2C2 pins (I2C2 mapped to SDA2/SCL2 pins)
#pragma config WDTWIN = WIN25       // Watchdog Window Select bits (WDT Window is 25% of WDT period)

// FWDT
#pragma config WDTPOST = PS32768    // Watchdog Timer Postscaler bits (1:32,768)
#pragma config WDTPRE = PR128       // Watchdog Timer Prescaler bit (1:128)
#pragma config PLLKEN = OFF         // PLL Lock Enable bit (Clock switch to PLL source will wait until the PLL lock signal is valid.)
#pragma config WINDIS = OFF         // Watchdog Timer Window Enable bit (Watchdog Timer in Non-Window mode)
#pragma config FWDTEN = OFF         // Watchdog Timer Enable bit (Watchdog timer enabled/disabled by user software)

// FOSC
#pragma config POSCMD = NONE        // Primary Oscillator Mode Select bits (XT Crystal Oscillator Mode)
#pragma config OSCIOFNC = OFF       // OSC2 Pin Function bit (OSC2 is clock output)
#pragma config IOL1WAY = OFF        // Peripheral pin select configuration (Allow multiple reconfigurations)
#pragma config FCKSM = CSECMD       // Clock Switching Mode bits (Clock switching is enabled,Fail-safe Clock Monitor is disabled)

 // FOSCSEL
#pragma config FNOSC = FRC          // Oscillator Source Selection (Internal Fast RC (FRC))
#pragma config PWMLOCK = ON         // PWM Lock Enable bit (Certain PWM registers may only be written after key sequence)
#pragma config IESO = OFF           // Two-speed Oscillator Start-up Enable bit (Start up with user-selected oscillator source)

// FGS
#pragma config GWRP = OFF           // General Segment Write-Protect bit (General Segment may be written)
#pragma config GCP = OFF            // General Segment Code-Protect bit (General Segment Code protect is Disabled)



// Timer 1 Interrupt
void __attribute__ ( (interrupt, no_auto_psv) ) _T1Interrupt( void ) 
{
    static int i = 0;
    static int count = 1;

    IFS0bits.T1IF = 0;
    T1CONbits.TON = 0;

    // Do your stuff here
    if ( count == 1000 ){
        execTowerLamp (i, LAMP_ON);
        i++;
        if (i == 4) i = 0;
        count = 0;
    }
    count++;
//    execTowerLamp (YELLOW, LAMP_ON);

    TMR1 = 0;
    T1CONbits.TON = 1;
    /* reset Timer 1 interrupt flag */
}


void InitClock( void )
{
    // Configure PLL prescaler, PLL postscaler, PLL divisor
    // Configure Oscillator to operate the device at 60Mhz
    // Fosc= Fin*M/(N1*N2), Fcy=Fosc/2
    // Fosc= 8M*60/(2*2)=120Mhz for 8M input clock
    PLLFBD  =   63;                      // M=65
    CLKDIVbits.PLLPOST  =   0;           // N2=2
    CLKDIVbits.PLLPRE   =   0;           // N1=2

    // Initiate Clock Switch to FRC oscillator with PLL (NOSC=0b001)
    __builtin_write_OSCCONH(0x01);
    __builtin_write_OSCCONL(OSCCON | 0x01);
    // Wait for Clock switch to occur
    while (OSCCONbits.COSC!= 0b001);
    // Wait for PLL to lock
    while (OSCCONbits.LOCK!= 1);
}


// Initialize common Ports
void InitPorts () {
    ANSELA = 0x00;
    ANSELB = 0x00;

    // Tower Lamp
    TRISAbits.TRISA1 = 0;   // Output : RED Light
    TRISAbits.TRISA0 = 0;   // Output : Yellow Light
    TRISBbits.TRISB15 = 0;  // Output : Green Light

    // Rejector
    TRISBbits.TRISB0 = 0;   // Output : Rejector

    // IR SENSOR
    TRISBbits.TRISB1 = 1;   // Input : IR Sensor
}

    // Main function
    int main(int argc, char** argv) {

    int i = 0;

    InitClock();    // This is the PLL settings
    InitPort1();    // LEDs outputs, Switches Inputs
    InitPorts();    // Configure all Input/Output Ports


    init_Timer1();
    execTimer1(40, 1); // timer for 40msec, status : ON


    /* Wait at least 105 microseconds (1/9600) before sending first char */
    DELAY_105uS;

    while( 1 )
    {                

        for (i = 0; i < 1000; i++){
            DELAY_105uS;
        }

    }

    return (EXIT_SUCCESS);
}

// Execute Tower Lamp
void execTowerLamp ( int color, int status){
    switch (color) {

        case RED :
            RED_LIGHT = status;
            YELLOW_LIGHT = !status;
            GREEN_LIGHT = !status;
            break;

        case YELLOW :
            RED_LIGHT = !status;
            YELLOW_LIGHT = status;
            GREEN_LIGHT = !status;
            break;

        case GREEN :
            RED_LIGHT = !status;
            YELLOW_LIGHT = !status;
            GREEN_LIGHT = status;
            break;

        default :
            RED_LIGHT = status;
            YELLOW_LIGHT = status;
            GREEN_LIGHT = status;
            break;

    }
}

Here is a datasheet

I am facing issue while toggling RED LAMP i.e. pin<20> RA1.

Conditions where i m facing this issue :

  1. If only RED LAMP is turned ON, It continue as ON forever
  2. IF only RED LAMP is toggled, It just turns ON for once than permanent OFF
  3. I have a Timer1 interrupt in my sample code, Here I am turning ON all three lamps simultaneously. So, RED_LAMP turns ON once than YELLOW and Then GREEN and Thereafter only YELLOW & GREEN. RED_LAMP turns ON Randomly once in a while.

Pin<19:20> have same multifuntion such as A/D, Comparators. I have turned Off other functions as mentioned in the datasheet.

Can any one help me resolving the issue ???

If I am lacking any info, please let me know. I will provide it asap.

\$\endgroup\$
7
  • 1
    \$\begingroup\$ Please post source of execTowerLamp. Can you disconnect from MCU and apply Vdd to that trace manually? You could ascertain that way if the problem is with the MCU and not in the circuit somewhere else. \$\endgroup\$
    – Szidor
    Commented Dec 6, 2016 at 15:14
  • \$\begingroup\$ @Szidor, Thanks for your response. I have edited my code to add execTowerLamp(). Also I have traced it Manually, by providing 3.3v to its track. It works fine. Also as I mentioned, If I provide continuous Positive signal to Pin RA1 only, It works. RED_LAMP gets ON and remains ON. The Issue is coming only when I am trying to toggle it alone or with other Lamp. In Such case, its behaving abnormally (Random behaviour). Please check my circuit also. Might be design issue i am not able to get. \$\endgroup\$
    – skg
    Commented Dec 7, 2016 at 4:55
  • \$\begingroup\$ Did you try cases 2 and 3 with manual 3.3 also? \$\endgroup\$
    – Szidor
    Commented Dec 7, 2016 at 6:50
  • \$\begingroup\$ Also please include defines. \$\endgroup\$
    – Szidor
    Commented Dec 7, 2016 at 6:51
  • 1
    \$\begingroup\$ Try to write LAT registers instead of PORT registers. \$\endgroup\$
    – Szidor
    Commented Dec 7, 2016 at 7:20

1 Answer 1

3
\$\begingroup\$

Always set the digital outputs by writing the LAT registers. PORT registers are only to be read.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.