⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 agrimonitorrootc.nc

📁 tinyos2.0版本驱动
💻 NC
字号:
#include "../Node/Datastructure.h"
//#include "BitVecUtils.h"

module AgriMonitorRootC
{
  uses
  {
    interface Boot;
    interface Leds;
    interface SplitControl as SerialControl;
    interface SplitControl as RadioControl;
    
    interface StdControl as CollectionControl;
    interface StdControl as DisseminationControl;
    interface RootControl;
    
    interface Receive as SensorDataReceive;
    //接收感知数据    interface Receive as TopoDataReceive;
    //接收拓扑数据    interface Receive as StateDataReceive;
    //接收状态数据  
    interface Pool<message_t> as SensorDataPool;
    interface Queue<message_t *> as SensorDataQueue;
    //感知数据的Pool和Queue
    interface Pool<message_t> as TopoDataPool;
    interface Queue<message_t *> as TopoDataQueue;
    //拓扑数据的Pool和Queue
    interface Pool<message_t> as StateDataPool;
    interface Queue<message_t *> as StateDataQueue;
    //状态数据的Pool和Queue
    
    interface AMSend as SerialSendSensorData;
    //向串口发送感知数据    interface AMSend as SerialSendTopoData;
    //向串口发送拓扑数据    interface AMSend as SerialSendStateData;
    //向串口发送状态数据    
    interface AMPacket as SerialAMPacket;
    interface AMPacket as RadioAMPacket; //xiugai --zjw
    //interface Packet as CTPPacket;
    interface Packet as SerialPacket;
    interface Packet as RadioPacket; // xiugai --zjw
    
    interface Receive as DisCommandReceive;
    //接收网关通过串口发送的分发指令    interface Receive as BcastCommandReceive;
    //接收网关通过串口发送的广播指令    
    interface Packet as DisCommandPacket;
    //获取分发指令的数据包    interface Packet as BcastCommandPacket;
    //获取广播指令的数据包    /*通过Packet的getPayload命令可以返回指向payload的指针*/
    
    interface DisseminationUpdate<rootDissemination_t> as DisCommandUpdate;
    //向网络中分发指令    
    interface Send as BcastCommandSender;
    interface CtpPacket;
    
  }
}



implementation
{
  task void SensorDataSendTask();
  //向串口发送感知数据  task void StateDataSendTask();
  //向串口发送状态数据  task void TopoDataSendTask();
  //向串口发送拓扑数据
  bool isRepeatMsg(am_addr_t id, uint8_t seqNum);  rootDissemination_t DisCommand;
  message_t BcastBuf; //广播缓冲区
  rootDissemination_t DisBuf; //分发命令缓冲区
  am_addr_t currentID[5];
  uint8_t currentseqNum[5] ;
  uint8_t index = 0;  
  event void Boot.booted()
  {
  	uint8_t i;
    for(i =0 ;i < 5 ; i++ ){
    	currentID[i] = 0xFFFF;
    	currentseqNum[i] = 0xFF;
    }
    call SerialControl.start();
    call RadioControl.start();
  }
  
  event void RadioControl.startDone(error_t error)
  {
    if(error == SUCCESS)
    {
      //call Leds.led0On();
      call DisseminationControl.start();
      call CollectionControl.start();
      call RootControl.setRoot();
    }
    else
    {
      call RadioControl.start();
    }
  }
  
  event void SerialControl.startDone(error_t error) { }
  
  event void SerialControl.stopDone(error_t error) { }
  event void RadioControl.stopDone(error_t error) { }  
  /*########################################################################*/
  //接收感知数据,向串口转发  
  event message_t* SensorDataReceive.receive(message_t* msg, void* payload, uint8_t len)
  {
    
    message_t* tmp;
    am_addr_t tempID;
    uint8_t tempseqNum;
    if(!call SensorDataPool.empty() && call SensorDataQueue.size() < call SensorDataQueue.maxSize())
    {
    	tempID = call CtpPacket.getOrigin(msg);
    	tempseqNum = call CtpPacket.getSequenceNumber(msg);
      if(!isRepeatMsg(tempID,tempseqNum)){
    		currentID[index] = tempID;
    		currentseqNum[index] = tempseqNum;
    		index++;
    		index = index%5;
    		tmp = call SensorDataPool.get();
        call SensorDataQueue.enqueue(msg);
     // if(!SerialBusy)//串口不忙,开始发送      //{
        post SensorDataSendTask();
      //}
        return tmp;
      }
    }
    return msg;
  }
  
  task void SensorDataSendTask()
  {
    uint8_t len ;
    am_addr_t addr, src;
    message_t* msg;
    
    if(call SensorDataQueue.empty())
    {
      return;
    }
    else
    {
      //if(!SerialBusy)
      //{
        msg = call SensorDataQueue.dequeue();
        //修改 ---张集文       
        src = call RadioAMPacket.source(msg);
        addr = call RadioAMPacket.destination(msg);
        len = call RadioPacket.payloadLength(msg);  
        call SerialPacket.clear(msg); 
        call SerialAMPacket.setSource(msg, src);   
        if(len == 17 || len == 19)
          len++;
        if(call SerialSendSensorData.send(addr, msg, len) == SUCCESS)
        {
         // SerialBusy = TRUE;
        } 
      //}
    }
  }
  
  event void SerialSendSensorData.sendDone(message_t *msg, error_t error)
  {
    if(error == SUCCESS)
    {
      //SerialBusy = FALSE;
      call Leds.led0Toggle();
      call SensorDataPool.put(msg);
    }
    if(!call SensorDataQueue.empty())
    {
      post SensorDataSendTask();
    }
  }
  
  
  /*########################################################################*/
  //接收状态数据,向串口转发  
  event message_t* StateDataReceive.receive(message_t* msg, void* payload, uint8_t len)
  {
    
    message_t* tmp;
    am_addr_t tempID;
    uint8_t tempseqNum;
    if(!call StateDataPool.empty() && call StateDataQueue.size() < call StateDataQueue.maxSize())
    {
    	tempID = call CtpPacket.getOrigin(msg);
    	tempseqNum = call CtpPacket.getSequenceNumber(msg);
      if(!isRepeatMsg(tempID,tempseqNum)){
    		currentID[index] = tempID;
    		currentseqNum[index] = tempseqNum;
    		index++;
    		index = index%5;
        tmp = call StateDataPool.get();
        call StateDataQueue.enqueue(msg);
     // if(!SerialBusy)//串口不忙,开始发送      //{
        post StateDataSendTask();
      //}
      return tmp;
      }
   }
    return msg;
  }
  
  task void StateDataSendTask()
  {
    uint8_t len;
    am_addr_t addr, src;
    message_t* msg;
    //stateData_t *buf;
    
    if(call StateDataQueue.empty())
    {
      return;
    }
    else
    {
      //if(!SerialBusy)
      //{
        msg = call StateDataQueue.dequeue();
        src = call RadioAMPacket.source(msg);
        addr = call RadioAMPacket.destination(msg);
        len = call RadioPacket.payloadLength(msg);
        call SerialPacket.clear(msg); 
        call SerialAMPacket.setSource(msg, src);
        if(len == 17 || len == 19)
          len++;
        if(call SerialSendStateData.send(addr, msg, len) == SUCCESS)
        {
          //SerialBusy = TRUE;
        } 
      //}
    }
  }
  
  event void SerialSendStateData.sendDone(message_t *msg, error_t error)
  {
    if(error == SUCCESS)
    {
      //SerialBusy = FALSE;
      call Leds.led0Toggle();
      call StateDataPool.put(msg);
    }
    if(!call StateDataQueue.empty())
    {
      post StateDataSendTask();
    }
  }


  /*########################################################################*/
  //接收拓扑数据,向串口转发  
  event message_t* TopoDataReceive.receive(message_t* msg, void* payload, uint8_t len)
  {
   
    message_t* tmp;
    am_addr_t tempID;
    uint8_t tempseqNum;
    if(!call TopoDataPool.empty() && call TopoDataQueue.size() < call TopoDataQueue.maxSize())
    {
    	tempID = call CtpPacket.getOrigin(msg);
    	tempseqNum = call CtpPacket.getSequenceNumber(msg);
      if(!isRepeatMsg(tempID,tempseqNum)){
    		currentID[index] = tempID;
    		currentseqNum[index] = tempseqNum;
    		index++;
    		index = index%5;
        tmp = call TopoDataPool.get();
        call TopoDataQueue.enqueue(msg);
      //if(!SerialBusy)//串口不忙,开始发送      //{
        post TopoDataSendTask();
      //}
      return tmp;
    }
   }
    return msg;
  }
  
  task void TopoDataSendTask()
  {
    uint8_t len;
    am_addr_t addr, src;
    message_t* msg;
    //topologyData_t *buf;
    
    if(call TopoDataQueue.empty())
    {
      return;
    }
    else
    {
      //if(!SerialBusy)
      //{
        msg = call TopoDataQueue.dequeue();
        src = call RadioAMPacket.source(msg);
        addr = call RadioAMPacket.destination(msg);
        len = call RadioPacket.payloadLength(msg);
        call SerialPacket.clear(msg); 
        call SerialAMPacket.setSource(msg, src);
        if(len == 17 || len == 19)
          len++;

        if(call SerialSendTopoData.send(addr, msg, len) == SUCCESS)
        {
         // SerialBusy = TRUE;
        } 
      //}
    }
  }
  
  event void SerialSendTopoData.sendDone(message_t *msg, error_t error)
  {
    if(error == SUCCESS)
    {
      //SerialBusy = FALSE;
      call Leds.led0Toggle();
      call TopoDataPool.put(msg);
    }
    if(!call TopoDataQueue.empty())
    {
      post TopoDataSendTask();
    }
  }
  
  
  /*########################################################################*/
  //接收网关发来的分发指令,向网络中分发  
  event message_t* DisCommandReceive.receive(message_t* bufPtr, void* payload, uint8_t len)
  {
      memcpy(&DisBuf , payload , len);
      call Leds.led2Toggle();
      call DisCommandUpdate.change(&DisBuf);
      return bufPtr;
  }
  
  
  /*########################################################################*/
  //接收网关发来的广播指令,向网络中广播  
  event message_t* BcastCommandReceive.receive(message_t* bufPtr, void* payload, uint8_t len)
  { 
    //BroadCastMsg_t* BcastCommand;
    BroadCastMsg_t* tempPtr;
    call RadioPacket.clear(&BcastBuf);
    tempPtr =(BroadCastMsg_t*) call BcastCommandSender.getPayload(&BcastBuf, sizeof(BroadCastMsg_t));
    memcpy(tempPtr, payload, len);
    call BcastCommandSender.send(&BcastBuf, len);
    return bufPtr;
  }
  event void BcastCommandSender.sendDone(message_t* bufPtr, error_t error)
  {
    if(error == SUCCESS){
    	call Leds.led1Toggle();
    }
    else
    {
      call Leds.led0Toggle(); 
    }
  }
  bool isRepeatMsg(am_addr_t id, uint8_t seqNum){
  	uint8_t i;
    for(i =0 ;i < 5 ; i++){
      if(id == currentID[i] && seqNum == currentseqNum[i])
    	  return TRUE;
  	}
  	return FALSE;
  }   
//ROOT接收来自感知节点的感知数据,拓扑数据,状态数据,//ROOT监听串口,网关通过串口发送分发指令和广播指令//ROOT把分发命令和广播命令发送到网络中//ROOT不作任何的判断  
//初始化时网关等一段时间,分发传感器数据提取命令,等待节点反馈}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -