[Tinyos-help] why sampack.senddone() event is not called sometimes when sampack.send() even returns success

Farhana Jabeen j_farhana at yahoo.com
Mon Dec 4 02:26:04 PST 2006


Skipped content of type multipart/alternative-------------- next part --------------
includes message;


module SimpleMessageM
{
   provides
   {
	interface StdControl;
 	

   }
   uses
   {
        interface ReceiveMsg as RcvSimpleMsg;
        interface SendMsg as SndSimpleMsg;
  

 
        interface ADC as Temperature;
        interface StdControl as TemperatureControl;
	  interface Timer as SendTimer; //the timer controls the SENDING BY 1,2, 3 AND 4
        interface Timer as forwardTimer; //the timer controls the forwarding by 2 and 5
        interface Timer as SyncTimer;// the timer controls the standard time - sysTime

	  interface StdControl as CommControl;

	  // these are only needed for Atmel AVR based platforms
	  #ifdef __AVR__
	    uses interface PowerManagement;
	    uses command result_t Enable();
	  #endif

     }
}
implementation
{
    bool m_sending, start,repeat;
    struct TOS_Msg message1;
  
    uint8_t  slide;
    uint8_t timeId;
    uint8_t currentMsg, currentMsg1;
    
    int temperature;
    int iptr=-1;
    TOS_MsgPtr  m_msg[2];
    SimpleMsgPtr  m_msg1[5];
    int parentId;
    char timeBuf[128];
    SimpleMsgPtr  messgptr[3];
    
  
command result_t StdControl.init()
 {
    atomic
    {
       slide=5;
       timeId = 0; // actually the value to be incremented each time depending on time stamp (time data collected)
       iptr=0;
      
       currentMsg = 0;
       currentMsg1 = 0;
       atomic{
         temperature=0;
         
         m_sending = FALSE;
  	 start = FALSE;
	}
	

	parentId=0;
	m_msg[0]=&message1;

	m_msg[1]=&message1;


	repeat=FALSE;  // used as send done will be called both after forwarding and sending simple messages
      
	
	#ifdef __AVR__
  	  call Enable();
  	  call PowerManagement.adjustPower();
	#endif

    }

    call CommControl.init();
 
    call TemperatureControl.init();
    
    if (TOS_LOCAL_ADDRESS==1)
	parentId=2;
    if (TOS_LOCAL_ADDRESS==2)
	parentId=3;
    if (TOS_LOCAL_ADDRESS==4)
	parentId=5;
    if (TOS_LOCAL_ADDRESS==5)
	parentId=3;
    if (TOS_LOCAL_ADDRESS==3)
	parentId=0;

    return SUCCESS;
 }
 command result_t StdControl.start()
 {
    call SyncTimer.start(TIMER_REPEAT,10);
 call CommControl.start();
    
    return SUCCESS;
 }

command result_t StdControl.stop()
{
    call SendTimer.stop();
    call TemperatureControl.stop();
    
    return SUCCESS;
}

//this timer controls the sysTime. each mote has such timer, but only mote0 can increase the sysTime.
//the time difference between motes is less than 10ms. you can change this 10ms to any value you want 
//by set the last parameter of SyncTimer.start();


event result_t SyncTimer.fired()
{
    if(TOS_LOCAL_ADDRESS==0)
    {
         sysTime+=10;//millisecond
   	   
    }
    if(sysTime==5000)
    {//after 5s later ,we will start the SendTimer. we assume that all the motes have been started in 5 seconds.
        
	  call SyncTimer.stop();//if you will not use the SyncTimer any more, you can stop it.
	  printTime(timeBuf, 128);
          dbg(DBG_USR1, "Local Host Turned on at %s\n", timeBuf);
	  if ((TOS_LOCAL_ADDRESS==1)||(TOS_LOCAL_ADDRESS==2)||(TOS_LOCAL_ADDRESS==4)||(TOS_LOCAL_ADDRESS==5))
   	  {
    		    
   		    call TemperatureControl.start();
     	          call SendTimer.start(TIMER_ONE_SHOT,2000);  
		    
          }
	
    }
    return SUCCESS;
}

task void sendTim()
{
  



            
    
  if ( ( m_sending == FALSE ) && (start == TRUE) ) {  
      
      
      if( call SndSimpleMsg.send(parentId, sizeof(struct SimpleMsg), m_msg[currentMsg]) == SUCCESS )
      {
		
   		atomic{
		
		 m_sending = TRUE;
		currentMsg ^= 0x1; 
       }
      }
    }

}

event result_t SendTimer.fired() {
SimpleMsgPtr body; 	
	 if (timeId < slide)
                { 
     
        
	call Temperature.getData();
if (temperature>=300)
   	{ 
   if( ( m_sending == FALSE ) && (start == FALSE) )
  {    
      
        
	
            body = (SimpleMsgPtr)(m_msg[currentMsg]->data);  
               atomic
                {
                       body->sourceId = TOS_LOCAL_ADDRESS;
                       
 	     	       body->tempreading = temperature;
	               body->timeId=timeId;
		  }
                
                 atomic start = TRUE;
        	 repeat=TRUE;
 		 atomic timeId++;
           
                 
	    }		 	
   //	call CommControl.start();   
    		post sendTim();
                
   	}
	else if (temperature<300){
		dbg(DBG_USR1,"temperature less than 300 \%d %d\n",timeId,temperature);

                
    	
		 atomic timeId++; 
	  	   call SendTimer.start(TIMER_REPEAT,2200); 
	 
         }
             

	
   }

     return SUCCESS;

}



async event result_t Temperature.dataReady(uint16_t data)
{
    char str[10];
    char * pEnd;

    

    
	atomic temperature=strtol ((itoa(data, str, 10)), &pEnd,10);
 
  //    atomic timeId++;
        
	
	

 //   post sendTim();   
    return SUCCESS;
 }
	
    

event result_t SndSimpleMsg.sendDone( TOS_MsgPtr pmsg, result_t success )
 { 
    SimpleMsgPtr body;
    body = (SimpleMsgPtr )(pmsg->data);

    if (success==SUCCESS)
    {

		dbg(DBG_USR1,"sent msg time Id \%x  from source \%d temperature \%d  \n",body->timeId,body->sourceId,body->tempreading);

    }
    else
	dbg(DBG_USR1,"             Unsuccessful sent\n");
 //   call CommControl.stop();
    atomic 
     {
        m_sending = FALSE;
    	atomic start = FALSE;
         
   
    } 
    if (repeat) // to differentiate if its called by simpemessage.fired to call continuously 5 times if by forwardmsg then only one time by mking repeat=FALSE
    {
    	if (timeId < slide)
	{
    		//atomic timeId++;      
               call SendTimer.start(TIMER_ONE_SHOT, 2000);
 		
        }
    }
    repeat=FALSE;
  
    return SUCCESS;

} // Ennd of SndSimpleMsg




task void forwardTim()
{

if( ( m_sending == FALSE ) && (start == FALSE) )
  {    
   
        
            *((SimpleMsgPtr)&message1.data) = *messgptr[iptr];
               atomic
                {

		       start = TRUE;
        	       repeat=FALSE;
                }
           
              call forwardTimer.start(TIMER_ONE_SHOT, 15);
                 post forwardTim(); 
    
  }	
         
 else if ( ( m_sending == FALSE ) && (start == TRUE) )
  {  


          if(( call SndSimpleMsg.send(parentId, sizeof(struct SimpleMsg), (TOS_MsgPtr)&message1)) == SUCCESS )
          {
 
 dbg(DBG_USR1,"            hello\n"); 

   		atomic {
				m_sending = TRUE;
				currentMsg ^= 0x1; 
			}

           }

    }     

  	

 

}// End of forwardTim()
  

inline void forwarder(SimpleMsgPtr mptr) {

         atomic
        {
           iptr++;
           if (iptr>=5)
                iptr=iptr%5;
	    m_sending = FALSE ;
            start = FALSE;
      	    messgptr[iptr]= mptr;

                       
         }
post forwardTim();

} // end of forwarder


event result_t  forwardTimer.fired()
{

return SUCCESS;
}// end of forwardTimer


event TOS_MsgPtr RcvSimpleMsg.receive(TOS_MsgPtr pmsg) 
{
      m_msg1[currentMsg1]=(SimpleMsgPtr )(pmsg->data);
      
      dbg(DBG_USR1,"Received time id \%d  from source \%x temperature \%d \n",m_msg1[currentMsg1]->timeId,m_msg1[currentMsg1]->sourceId,m_msg1[currentMsg1]->tempreading );

   if ((((m_msg1[currentMsg1]->sourceId==1)&&(TOS_LOCAL_ADDRESS ==2))|| ((m_msg1[currentMsg1]->sourceId==4)&&(TOS_LOCAL_ADDRESS ==5)))||((TOS_LOCAL_ADDRESS ==3)&&(m_msg1[currentMsg1]->sourceId!=3)))
   {		
	 call forwardTimer.start(TIMER_ONE_SHOT, 15);
   
        	 forwarder(m_msg1[currentMsg1]);
	 //	atomic currentMsg1 ^= 0x1;
          atomic{
                 currentMsg1++;
         if (currentMsg1>=5)
                currentMsg1=currentMsg1%5;
                 }   
    }
   
  
       return pmsg;
}// end of RcvSimpleMsg

}// end of program



More information about the Tinyos-help mailing list