
 Originally Posted by 
Darrel Taylor
					
				 
				You can put the PIC to sleep, and it will re-enumerate when re-connected.
The main oscillator is stopped in sleep mode, so the USB module's clock also stops.
You can also place the USB module in SUSPEND mode to reduce the current from the USB module. That's done in response to an IDLEIF, currently used to determine un-plugged state in DT_HID.
When the USB cable is plugged in, you'll get ACTVIF interrupts (a signal to RESUME from SUSPEND mode).
			
		 
	 
 Darrel, I thought I understood how to do this, but am getting all kinds of assembler errors when I try to compile.  Here are the applicable excerpts of code I created to try to follow your suggestion.  Can you please tell me where this went wrong??
First I set up my DT_INTS as follows with intention of using a USB_ACTV_INT from your DT_INTS to wake up the MCU and run the USB interface when connected.
	Code:
	ASM
INT_LIST  macro      ; IntSource,            Label,  Type, ResetFlag?
        INT_Handler   USB_Handler 
        INT_Handler   USB_ACTV_INT  _ACTVIFhandler,   PBP,  yes
        INT_Handler   INT2_INT,             _Range,   PBP,  yes
        INT_Handler   HLVD_INT,           _LowVolt,   PBP,  yes
    endm
    INT_CREATE               ; Creates the interrupt processor
endasm
 Then I created this handler for the USB_ACTV_INT.
	Code:
	ACTVIFhandler:
    IF LCD_Flag = 1 Then ' This code block FOR TESTING ONLY 
        LCDOut $fe,1' Clear Display                                       
        LCDOUT $fe,Line1,"USBPlugged"
        LCDOUT $fe,Line2,"interrupt"
    ENDIF
    ; put code here to process USB interrupt
     FOR X = 0 to 1000       ; Check for incomming USB data while waiting
@       ON_USBRX_GOSUB  _HandleRX
        PAUSE 1
            New_PORTB2 = PORTB.2         ; Check PORTB.2 pin for change              
            IF New_PORTb2 != Old_PORTB2 THEN  ' PortB.2 changed
                Old_PORTb2 = New_PORTb2
                ' NEXT STATEMENT NOT WORKING...CHECK WHY!!
                ARRAYWRITE USBTXBuffer, ["USBDemo"]
                GOSUB WaitToSend     ' Send data set about one/sec
                ' Send device ID to PC
                ' Send current Date/Time to PC
                ' Send each EEPROM stored date stamped range measurement to PC
                ' Send current BATTLOW indicator to PC                    
                ARRAYWRITE USBTXBuffer,[0,deviceID1,deviceID2,Mon,date,Yr, _
                                   hr,MINs,sec,stamp,rng0,rng1,BATTLOW,0,0,0]
                GOSUB WaitToSend
            ENDIF 
    NEXT X
         
    IF J > 222 THEN     ' If reached maximum EEPROM usage location...
        J = 16            ' ..reset pointer to start of range data
    Endif
    READ j, stamp       ' Read date stamp of measurment
    READ J+1, rng0      ' Read range measurement from EEPROM
    READ J+2, rng1
    Pause 10
    J = J + 3
    
    ' Send Data to PC
        ' Send device ID to PC
        ' Send current Date/Time to PC
        ' Send each EEPROM stored range measurement to PC
        ' Send current BATTLOW indicator to PC                     
        ARRAYWRITE USBTXBuffer,[0,deviceID1,deviceID2,mon,date,yr, _
                           hr,MINs,sec,stamp,rng0,rng1,BATTLOW,0,0,0]
    GOSUB SendIfReady
    Pause 500      ' Delay for user to view LCD   
@ INT_RETURN
 Then I modified my Main loop per follows to put MCU in sleep mode whenever not plugged in to USB or not receiving an external interrupt from the Real-time-clock (INT2).
	Code:
	@    INT_ENABLE   USB_ACTV_INT ; enable USB activity interrupt on plug-in
@    INT_ENABLE   INT2_INT     ; enable external (INT) interrupts
ENABLE DEBUG
'--------------------[ Begin Main Program Loop ]-------------------------
;@ StartSize(MainLoop)    ; FOR TEST ONLY
Main:
     PAUSE 100 ' Without this Pause, there's nothing to keep the WDT clear.
               ' HIGH, LOW & GOTO don't generate CLRWDT instuctions.
     IF LCD_Flag = 1 Then ' This code block FOR TESTING ONLY                                       
        GOSUB DisplayDateTime
     ENDIF
     ' Store current date/time in EEPROM  
        WRITE 242, Mon
        WRITE 243, Date
        WRITE 244, Yr
        WRITE 245, hr                
        WRITE 246, MINs
        Write 247, sec               
                                                                          
    ' Place code here to put MCU and Ultrasonic Ranger in SLEEP mode.
    ' while waiting for clock or USB interrupt to wakeup from SLEEP mode.  
           
    ' IDLEIF is used in the DT_HID code to detect unplugged state. If unplugged,
    ' per DT, it is safe to put the USB module in suspend mode before sleep
        IF IDLEIF THEN     ' USB is in unplugged state..
           UCON.1 = 1      ' puts USB module in suspend mode to save power
        ENDIF
    ' Enable the USB ACTVIF interrupt to awaken MCU when USB connected
        UIE.2 = 1
    ' Perform following steps to save power during Sleep mode
        CVRCON = %00000000 ' Set Voltage Reference for minimum power consumption
                           ' Disable CVref during Sleep to save power        
        ADCON1= %00000000  ' Set PortA to Analog I/O to save power during Sleep.                   
        CMCON = %00000111  ' Disable comparators
        HLVDCON = %00000000' Disable HLDV register
        TRISB = %11111111  ' Set all PORTB pins to inputs
        TRISC = %11111111  ' Set all PORTC pins to inputs
        PortA = %11111111  ' Set TOCK1, MCLR & all PortA pins High before Sleep 
                           ' to save power
        PortB = %11101111  ' Set all Port B & C pins High to save power
        PortC = %11111101  ' except RB4 & RC2.
        @ sleep
        @ NOP
    ' Microcontroller is in Sleep State awaiting next INT2 or USB plug-in
    
    ' INT2 interrupt from RTC will log a range measurement and go back to sleep     
  
    ' ACTVIF interrupt from USB senses that USB connector is plugged in 
    ' and will dump data logged in EEPROM to PC via USB interface and then go
    ' back to sleep when the USB cable is disconnected.
GOTO Main
 Here are the assembler errors I get when I attempt to compile with above code:
				
			
Bookmarks