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

📄 isl29001c.nc

📁 tinyos2.0版本驱动
💻 NC
字号:
/**
 * 本程序用于测试I2C驱动,传感器为ISL29001,CPU为atmel1281
 * @author Majy & Lizm
 * @date 2008/09/22
 * @latest modified by Lizm at 2008/09/24 09:26
 */


#include "Timer.h"
#include "I2C.h"
#include "ISL29001.h"

module ISL29001C 
{
  uses interface Timer<TMilli> as Timer0;
  uses interface Timer<TMilli> as Timer1;
  uses interface Leds;
  uses interface GeneralIO as PD_Enable;
  uses interface I2CPacket<TI2CBasicAddr>;
  uses interface Resource as I2CResource;
  uses interface Boot;

  uses interface SplitControl as SerialControl;
  uses interface AMSend;
  uses interface Packet;
}
implementation
{

  uint8_t mI2CCmdBuffer[3];
  uint8_t mI2CDataBuffer[4];
  uint8_t mState;
  message_t packet;


  event void Boot.booted()  {
    // Power up the ISL29001
    call PD_Enable.makeOutput();
    //把DDR置为1,数据方向为出
    call PD_Enable.clr();
    //清数据寄存器
    //以上实现见\tos\chips\atm128\pins\HplAtm128GeneralIOPinP.nc
    mI2CCmdBuffer[0] = 0x00;
    //0x00表示将1号光电二极管的读数转换成16位无符号数值,详见29001关于控制寄存器TWCR的说明

    call SerialControl.start();
  }

  event void SerialControl.startDone(error_t error) {
    if (error == SUCCESS) {
      call I2CResource.request();
    }
  }

  event void SerialControl.stopDone(error_t error) { }

  event void I2CResource.granted()  {
    // Send ISL29001 0x00 command for preparing 
    call I2CPacket.write((I2C_START | I2C_STOP), ISL_ADDRESS, 1, mI2CCmdBuffer);
  }

  event void Timer1.fired()  {
    call Leds.led1Toggle();
    mI2CDataBuffer[0] = 0;
    mI2CDataBuffer[1] = 0;
    mI2CDataBuffer[2] = 0;
	mI2CDataBuffer[3] = 0;
    call I2CPacket.read((I2C_START | I2C_STOP), ISL_ADDRESS, 4, mI2CDataBuffer);
    //从mI2CDataBuffer读取4个字节数值
    //I2C共有4个8位数据寄存器TWDR,但无法为其都分配地址,因此只能一次性全部读出,
    //其中前2个寄存器中存放的分别是最近感知数值的低8位和高8位,little-endian方式
    //后2个寄存器中存放的分别是integration counter value的低8位和高8位
    //详见29001关于数据寄存器TWDR的说明
    //call I2CPacket.write((I2C_START | I2C_STOP), ISL_ADDRESS, 1, mI2CCmdBuffer);
  }

  event void Timer0.fired()  {
    call Leds.led1Toggle();
    mI2CDataBuffer[0] = 0;
    mI2CDataBuffer[1] = 0;
    mI2CDataBuffer[2] = 0;
	mI2CDataBuffer[3] = 0;
    call I2CPacket.read((I2C_START | I2C_STOP), ISL_ADDRESS, 4, mI2CDataBuffer);
    //call I2CPacket.write((I2C_START | I2C_STOP), ISL_ADDRESS, 1, mI2CCmdBuffer);
    //Timer0只触发一次,Timer1循环触发
  }


  event void AMSend.sendDone(message_t* bufPtr, error_t error) {
    call Timer1.startOneShot( 1000 );
    return;
  }
 
// I2C
  task void I2CWriteDone() {
     call Timer0.startOneShot(150);
     return;
  }

  task void I2CReadDone() {
    ISLSensorMsg *rcm = (ISLSensorMsg *)call Packet.getPayload(&packet, sizeof(ISLSensorMsg));
    if (rcm == NULL) {return;}
    if (call Packet.maxPayloadLength() < sizeof(ISLSensorMsg)) {
      return;
    }
    rcm -> mISLData[0] = mI2CDataBuffer[1];
    rcm -> mISLData[1] = mI2CDataBuffer[2];
    //mI2CDataBuffer的第一个元素是设备地址,后面才依次为感知读数,详见29001读操作时序图
    call AMSend.send(AM_BROADCAST_ADDR, &packet, sizeof(ISLSensorMsg));
    return;
  }

 async event void I2CPacket.readDone(error_t error, uint16_t addr, uint8_t length, uint8_t* data)  {
    if (error == SUCCESS && data == mI2CDataBuffer) {
      call Leds.led2Toggle();
      post I2CReadDone();
      //async定义的函数体要尽量简单,减少执行时间,如果有复杂操作最好封装成task,否则编译时将有警告
    }
  }
  
  async event void I2CPacket.writeDone(error_t error, uint16_t addr, uint8_t length, uint8_t* data)  {
    if (error == SUCCESS) {
      call Leds.led0Toggle();
      post I2CWriteDone();
    }
  }

}

⌨️ 快捷键说明

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