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 support@ccsinfo.com

Deep Sleep wake up on INT0 !
Goto page Previous  1, 2
 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Tue Jun 07, 2011 6:14 pm     Reply with quote

This code appears to do what you want. Here is the output on TeraTerm:

Quote:

DSWAKEL: 01 // DSPOR bit = 1. This is the initial power-up of the board.
DSWAKEH: 00

//-------------------
// Next, I pressed the pushbutton on Pin B0.
DSWAKEL: 00
DSWAKEH: 01 // DSINT0 = 1. The board woke-up on the falling edge.

// Then I released the pushbutton on pin B0.
DSWAKEL: 00
DSWAKEH: 01 // DSINT0 = 1. The board did a wake-up on the rising edge.

//-------------------
// Then I press and release the button again. It works here too.

DSWAKEL: 00
DSWAKEH: 01

DSWAKEL: 00
DSWAKEH: 01
//----------------------
And again, and it still works.

DSWAKEL: 00
DSWAKEH: 01

DSWAKEL: 00
DSWAKEH: 01


The pushbutton circuit looks like this:
Code:

           +3.3v
            |
            <
            > 10K       
            <         ___ Push button switch 
To          |        _|_|_
pin -----------------o   o------
B0                             |             
                              --- GND
                               -   


Here is the test program. I don't know if all the 10ms delays in here are
necessary. Some of them are. This program was tested with compiler
versions 4.095 and 4.121.
Code:

#include <18F24J11.h>           
#fuses HS, NOWDT
#use delay(crystal=20M)   
#use rs232(baud=9600, UART1, ERRORS)

#byte WDTCON = 0xFC0
#byte DSCONH = 0xF4D
#byte DSCONL = 0xF4C
#byte RTCCFG = 0xF3F
#byte DSWAKEH= 0xF4b
#byte DSWAKEL= 0xF4a
#byte OSCCON = 0xFD3

#bit IDLEN =OSCCON.7      // Used to set IDLE low-power mode
#bit DSEN = DSCONH.7      // Used to set deep sleep
#bit REGSLP =WDTCON.7
#bit RELEASE = DSCONL.0
#bit RTCSYNC = RTCCFG.4
#bit DS_WAKEUP_BIT = WDTCON.3   // Bit that detects wake up from DS
#bit DSRTC = DSWAKEL.3


//==============================================
void main(void)
{

// Release the PIC's i/o pins for normal operation
// after waking up from Deep Sleep.  Important !
RELEASE = 0;   
delay_ms(10);

printf("\n\r");
printf("DSWAKEL: %x \n\r", DSWAKEL);
printf("DSWAKEH: %x \n\r", DSWAKEH);
delay_ms(10);

// Clear the wake-up source registers, regardless
// of what the PIC data sheet says.
DSWAKEL = 0;
DSWAKEH = 0;

// Look at the current state of the push-button switch.
// Based on that, set the edge that we expect to see next.
if(input(PIN_B0) == 1)   // If switch is high
   ext_int_edge(H_TO_L); // Then expect a falling edge next
else                     // If switch is low
   ext_int_edge(L_TO_H); // Then expect a rising edge next

clear_interrupt(INT_EXT);
enable_interrupts(INT_EXT);
delay_ms(10);

// Enable Deep Sleep mode.
REGSLP = 1;    // enable low-power operation in sleep mode
IDLEN = 0;
#asm         // Time-critical section must be in ASM 
BSF DSEN
SLEEP
NOP
#endasm

printf("Should never get here\n\r");


while(1);
}
heUAcyp



Joined: 16 Mar 2011
Posts: 33

View user's profile Send private message

PostPosted: Wed Jun 08, 2011 6:12 am     Reply with quote

Sir thank you very very much for your help.

Interrupt is working with a small problem. I have tested the suggested code and get the expected results on the HyperTerminal:

Quote:
DS_WAKEUP_BIT: 00
DS_WAKEUP_BIT: 00
DSWAKEH: 00
DSWAKEL: 00


DS_WAKEUP_BIT: 01
DS_WAKEUP_BIT: 01
DSWAKEH: 01
DSWAKEL: 00


DS_WAKEUP_BIT: 01
DS_WAKEUP_BIT: 01
DSWAKEH: 01
DSWAKEL: 00


The code I am using is:

Code:
#include <18F25J11.h>
#device ADC=10
#include <STDIO.H>
#include <stdlib.h>
#include <math.h>
#include <STRING.H>
#include <2408.c>

#fuses HS,NOWDT,NOPROTECT
#use delay(clock=4000000)
#use rs232 (baud=9600, xmit=PIN_C6, rcv=PIN_C7, ERRORS)


//
#byte WDTCON = 0xFC0
#byte DSCONH = 0xF4D
#byte DSCONL = 0xF4C
#byte RTCCFG = 0xF3F
#byte DSWAKEH= 0xF4b
#byte DSWAKEL= 0xF4a
#byte OSCCON = 0xFD3
#byte INTCON = 0xFF2
#byte INTCON2 = 0xFF1
//
#bit IDLEN=OSCCON.7      // used to set IDLE low-power mode ( will be set to zero for both deep-sleep and sleep modes)
#bit DSEN = DSCONH.7     // used to set deep sleep (1 for deep-sleep)
#bit REGSLP =WDTCON.7
#bit RELEASE = DSCONL.0
#bit RTCSYNC = RTCCFG.4
#bit DSINT0 = DSWAKEH.0 // bit for INT0 interrupt - change detection
#bit DS_WAKEUP_BIT = WDTCON.3     // bit that detects wake up from deep sleep
#bit INT0IE = INTCON.4
#bit INT0IF = INTCON.1
#bit INTEDG0 = INTCON2.6


void EnterDeepSleep()
{
// Enable Deep Sleep mode.
REGSLP = 1;    // enable low-power operation in sleep mode
IDLEN = 0;
#asm         // Time-critical section must be in ASM 
BSF DSEN
SLEEP
NOP
#endasm
}

void PerformingTaskON()
{
output_high(PIN_A1) ;

}
void main()
{
//disable_interrupts(GLOBAL);

RELEASE = 0;   // Activate i/o pins
delay_ms(10);


printf("\n\r\n\r");
printf("DS_WAKEUP_BIT:  %x \n\r", DS_WAKEUP_BIT);
delay_ms(10);
printf("DS_WAKEUP_BIT:  %x \n\r", DSINT0);
delay_ms(10);
printf("DSWAKEH:  %x \n\r", DSWAKEH);
delay_ms(10);
printf("DSWAKEL:  %x \n\r", DSWAKEL);
delay_ms(10);
//
if((DS_WAKEUP_BIT == 1) && (DSWAKEH == 1)&&(DSINT0==1))
{
PerformingTaskON() ;
delay_ms(200);
DSWAKEL = 0;
DSWAKEH = 0;
}

// Clear the wake-up source registers, regardless
// of what the PIC data sheet says.
DSWAKEL = 0;
DSWAKEH = 0;
//
// Look at the current state of the push-button switch.
// Based on that, set the edge that we expect to see next.
if(input(PIN_B0) == 1)   // If switch is high
ext_int_edge(H_TO_L); // Then expect a falling edge next
else                     // If switch is low
ext_int_edge(L_TO_H); // Then expect a rising edge next


clear_interrupt(INT_EXT);
enable_interrupts(INT_EXT);
delay_ms(10);

EnterDeepSleep() ;

printf("Should never get here\n\r");

while(true)
{

}

}


However, PIC does not go back to sleep when I try to perform a task.

With a simple test task (if function commented in above code), when interrupt fires, I am turning a LED on. The problem is , LED does not turn back to off afterwards, meaning that PIC is not getting back to deep sleep mode.

in my complete design I will keep real time while in deep sleep , than wake up only to save the date and time to an external EEPROM when interrupt fires and go back to sleep. I have written and tested the other parts of the code and they are working. But I want PIC to be awake only while performing a task and than go back to sleep again.

Something is still wrong, I tried to add the if function to various places in the code flow and it still not working.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Wed Jun 08, 2011 12:25 pm     Reply with quote

I assume that setting pin A1 to high level turns the LED on. I don't see
any place in your code where you turn the LED off. You never set pin A1
to a low level.

Going into Deep Sleep mode doesn't turn it off. Read the data sheet:
Quote:

4.6.2 I/O PINS DURING DEEP SLEEP
During Deep Sleep, the general purpose I/O pins will retain their previous states.

Download the PIC data sheet and read the whole section on Deep Sleep.
heUAcyp



Joined: 16 Mar 2011
Posts: 33

View user's profile Send private message

PostPosted: Wed Jun 08, 2011 2:55 pm     Reply with quote

Thank you boss
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Goto page Previous  1, 2
Page 2 of 2

 
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