[Tinyos-beta-commits]
CVS: tinyos-1.x/beta/chips/AD524X/v2 AD524X.h, NONE,
1.1 AD524X.nc, NONE, 1.1 AD524XC.nc, NONE, 1.1 AD524XM.nc, NONE, 1.1
Joe Polastre
jpolastre at users.sourceforge.net
Wed Aug 3 16:43:07 PDT 2005
Update of /cvsroot/tinyos/tinyos-1.x/beta/chips/AD524X/v2
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv23907
Added Files:
AD524X.h AD524X.nc AD524XC.nc AD524XM.nc
Log Message:
New implementation of the AD524X driver that supports all of the AD524X
series of devices instead of just the AD5241 and AD5242.
New interface defined; works in less code space that the previous implementation, especially when multiple potentiometers are located on the same board (ahem, prabal)
located in v2/ directory since NEST FE is using the first version
Ideally the first version will go away and eventually v2 will move to the
main tree once mica* platforms implement new I2CPacket interface
--- NEW FILE: AD524X.h ---
/*
* Copyright (c) 2005 Moteiv Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached MOTEIV-LICENSE
* file. If you do not find these files, copies can be found at
* http://www.moteiv.com/MOTEIV-LICENSE.txt and by emailing info at moteiv.com.
*
* @author Joe Polastre <info at moteiv.com>
*/
#ifndef _H_AD524X_H
#define _H_AD524X_H
typedef enum {
TYPE_AD5241 = 0,
TYPE_AD5242,
TYPE_AD5243,
TYPE_AD5245,
TYPE_AD5246,
TYPE_AD5247,
TYPE_AD5248,
} ad524x_type_t;
#endif
--- NEW FILE: AD524X.nc ---
// $Id: AD524X.nc,v 1.1 2005/08/03 23:43:05 jpolastre Exp $
/*
* "Copyright (c) 2000-2005 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
* Copyright (c) 2005 Moteiv Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached MOTEIV-LICENSE
* file. If you do not find these files, copies can be found at
* http://www.moteiv.com/MOTEIV-LICENSE.txt and by emailing info at moteiv.com.
*
*/
/**
* @author Joe Polastre <info at moteiv.com>
* Revision: $Revision: 1.1 $
*
* The AD524X interface provides commands for using the
* Analog Devices AD524X family of potentiometers.
*
* The lower 2 bits (AD1 and AD0) must be provided as the address.
* The full address may be provided as well, but all other bits will be
* stripped (addr = addr & 0x03)
*/
includes AD524X;
interface AD524X {
/**
* Start the AD5242 device. This sets the SD bit to enable the device
* via the I2C bus. This command does not alter the physical shutdown
* pin of the device. The StdControl interface is responsible for
* the physical shutdown of the device.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param type Type of address -- only some AD524X devices can be started
* @return SUCCESS if the request was accepted
*/
command result_t start(uint8_t addr, ad524x_type_t type);
/**
* Notification that there was an attempt to set the SD bit.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param result SUCCESS if the bit was actually set, FAIL if the
* device could not be reached or the operation failed
* @param type Type of device
*/
event void startDone(uint8_t addr, result_t result, ad524x_type_t type);
/**
* Stop the AD5242 device. This clears the SD bit to enable the device
* via the I2C bus. This command does not alter the physical shutdown
* pin of the device. The StdControl interface is responsible for
* the physical shutdown of the device.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param type Type of address -- only some AD524X devices can be stopped
* @return SUCCESS if the request was accepted
*/
command result_t stop(uint8_t addr, ad524x_type_t type);
/**
* Notification that there was an attempt to clear the SD bit.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param result SUCCESS if the bit was actually cleared, FAIL if the
* device could not be reached or the operation failed
* @param type Type of device
*/
event void stopDone(uint8_t addr, result_t result, ad524x_type_t type);
/**
* Set the value of one of the output pins.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param high TRUE if O should be set, FALSE if it should be cleared
* @param output FALSE if O1 should be used, TRUE for 02
* @param Type of device -- only some AD524X devices have outputs
* @return SUCCESS if the request was accepted
*/
command result_t setOutput(uint8_t addr, bool output, bool high, ad524x_type_t type);
/**
* Notification that the state of an output pin may have changed.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param output FALSE for O1, TRUE for O2
* @param result SUCCESS if the output O was successfully changed
* @param Type of device -- only some AD524X devices have outputs
*/
event void setOutputDone(uint8_t addr, bool output, result_t result, ad524x_type_t type);
/**
* Get the value of an output pin.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param output FALSE for O1, TRUE for 02
* @param type of device -- only some AD524X devices have outputs
* @return TRUE if the bit is set, FALSE otherwise
*/
command bool getOutput(uint8_t addr, bool output, ad524x_type_t type);
/**
* Set the value of an RDAC
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param rdac FALSE for RDAC1, TRUE for RDAC2 if exits
* parameter ignored if type != AD5242
* @param value A 256-bit value corresponding to the wiper position
* For 128-bit pots, the value must be *left* justified
* (the LSB will be discarded)
* @return SUCCESS if the request was accepted
*/
command result_t setPot(uint8_t addr, bool rdac, uint8_t value, ad524x_type_t type);
/**
* Notification that RDAC may be set to a new value
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param SUCCESS if the value of RDAC was changed
*/
event void setPotDone(uint8_t addr, bool rdac, result_t result, ad524x_type_t type);
/**
* Get the value of an RDAC
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param rdac FALSE for RDAC1, TRUE for RDAC2
* @param type The device type
* @return SUCCESS if the request was accepted
*/
command result_t getPot(uint8_t addr, bool rdac, ad524x_type_t type);
/**
* Result of the get operation with the value of the RDAC potentiometer.
*
* @param addr Lower 2 bits (AD1,AD0) of the device I2C address
* @param rdac The potentiometer that qas requested
* @param value A 256-bit value corresponding to the wiper position
* For 128-bit potentiometers, value is left-justified
* (shifted left by 1 bit)
* @param result SUCCESS if the value was correctly obtained from the
* device. If FAIL is returned, the value is not valid.
* @param type The type of the device
*/
event void getPotDone(uint8_t addr, bool rdac, uint8_t value, result_t result, ad524x_type_t type);
}
--- NEW FILE: AD524XC.nc ---
// $Id: AD524XC.nc,v 1.1 2005/08/03 23:43:05 jpolastre Exp $
/*
* "Copyright (c) 2000-2005 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*/
/**
* @author Joe Polastre <info at moteiv.com>
* Revision: $Revision: 1.1 $
*
* AD524XC provides access to primitives for the AD524X family of
* potentiometers. StdControl sets the physical hardware pin to turn
* the device on or off via the shutdown pin (if supported by the
* underlying platform).
*
* You *must* define the "AD524X_SD" pin in an included file, presumably
* your sensorboard.h file. The AD524X_SD pin is used to put the device
* into and out of shutdown when StdControl start() and stop() are called.
* These functions:
* TOSH_MAKE_AD524X_SD_OUTPUT()
* TOSH_MAKE_AD524X_SD_INPUT()
* TOSH_SET_AD524X_SD_PIN()
* TOSH_CLR_AD524X_SD_PIN()
* May be defined as empty functions for platforms that do not support the
* AD524X shutdown pin.
*
* The AD524X driver counts the number of users for systems with multiple
* pots and only causes the physical pin to initiate a shutdown when all
* users of the pot have called stop (in other words #start() == #stop())
*
* It is recommended that you use the SD bit in the AD524X by calling
* AD524X.start() and AD524X.stop() rather than toggling the actual
* shutdown pin. By setting the pin in the particular device, you can
* ensure that device has been shutdown.
*/
configuration AD524XC {
provides {
interface StdControl;
interface AD524X;
}
}
implementation
{
components I2CPacketC, AD524XM;
AD524X = AD524XM;
StdControl = AD524XM;
AD524XM.LowerControl -> I2CPacketC;
AD524XM.I2CPacket -> I2CPacketC;
}
--- NEW FILE: AD524XM.nc ---
// $Id: AD524XM.nc,v 1.1 2005/08/03 23:43:05 jpolastre Exp $
/*
* Copyright (c) 2005 Moteiv Corporation
* All rights reserved.
*
* This file is distributed under the terms in the attached MOTEIV-LICENSE
* file. If you do not find these files, copies can be found at
* http://www.moteiv.com/MOTEIV-LICENSE.txt and by emailing info at moteiv.com.
*
* "Copyright (c) 2000-2005 The Regents of the University of California.
* All rights reserved.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose, without fee, and without written agreement is
* hereby granted, provided that the above copyright notice, the following
* two paragraphs and the author appear in all copies of this software.
*
* IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
* OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
* CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
* AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS."
*
*/
/**
* @author Joe Polastre <info at moteiv.com>
* Revision: $Revision: 1.1 $
*
*/
includes AD524X;
module AD524XM
{
provides {
interface StdControl;
interface AD524X;
}
uses {
interface StdControl as LowerControl;
interface MSP430I2CPacket as I2CPacket;
}
}
implementation
{
enum {
AD524X_RDAC = 1 << 7,
AD524X_RS = 1 << 6,
AD524X_SD = 1 << 5,
AD524X_3_8_SD = 1 << 6, /* the AD5243 and AD5248 use a different bit */
AD524X_O1 = 1 << 4,
AD524X_O2 = 1 << 3
};
enum {
IDLE = 0,
AD524X_START,
AD524X_STOP,
AD524X_OUTPUT ,
AD524X_RPOT,
AD524X_WPOT,
};
uint8_t data[2];
uint8_t device[4];
uint8_t state;
uint8_t type;
bool rdac;
int8_t usercount;
result_t startWriteCommand(uint8_t _addr, uint8_t _length, uint16_t _data, uint8_t _newstate, bool _rdac, ad524x_type_t _type) {
uint8_t _state = 0;
atomic {
_state = state;
if (_state == IDLE) {
state = _newstate;
type = _type;
rdac = _rdac;
}
}
if (_state == IDLE) {
data[0] = _data & 0xFF;
data[1] = (_data >> 8) & 0xFF;
if (!call I2CPacket.writePacket((_addr & 0x03) | 0x2C, _length, data)) {
state = IDLE;
return FAIL;
}
return SUCCESS;
}
return FAIL;
}
result_t startReadCommand(uint8_t _addr, uint8_t _length, uint8_t _newstate, bool _rdac, ad524x_type_t _type) {
uint8_t _state = 0;
atomic {
_state = state;
if (_state == IDLE) {
state = _newstate;
type = _type;
rdac = _rdac;
}
}
if (_state == IDLE) {
if (!call I2CPacket.readPacket((_addr & 0x03) | 0x2C, _length, data)) {
state = IDLE;
return FAIL;
}
return SUCCESS;
}
return FAIL;
}
command result_t StdControl.init() {
atomic {
usercount = 0;
state = 0;
}
return call LowerControl.init();
}
command result_t StdControl.start() {
int8_t _localcount;
atomic {
if (usercount <= 0) {
TOSH_MAKE_AD524X_SD_OUTPUT();
TOSH_SET_AD524X_SD_PIN();
usercount = 0;
}
_localcount = usercount;
usercount++;
}
if (_localcount == 0)
return call LowerControl.start();
else
return SUCCESS;
}
command result_t StdControl.stop() {
int8_t _localcount;
atomic {
usercount--;
if (usercount <= 0) {
TOSH_CLR_AD524X_SD_PIN();
TOSH_MAKE_AD524X_SD_INPUT();
usercount = 0;
}
_localcount = usercount;
}
if (_localcount == 0)
return call LowerControl.stop();
else
return SUCCESS;
}
command result_t AD524X.start(uint8_t addr, ad524x_type_t _type) {
if ((_type == TYPE_AD5241) || (_type == TYPE_AD5242) || (_type == TYPE_AD5245)) {
atomic device[(int)(addr & 0x03)] &= ~AD524X_SD;
return startWriteCommand(addr, 1, device[(int)(addr & 0x03)], AD524X_START, 0, _type);
}
else if ((_type == TYPE_AD5243) || (_type == TYPE_AD5248)) {
atomic device[(int)(addr & 0x03)] &= ~AD524X_3_8_SD;
return startWriteCommand(addr, 1, device[(int)(addr & 0x03)], AD524X_START, 0, _type);
}
return FAIL;
}
command result_t AD524X.stop(uint8_t addr, ad524x_type_t _type) {
if ((_type == TYPE_AD5241) || (_type == TYPE_AD5242) || (_type == TYPE_AD5245)) {
atomic device[(int)(addr & 0x03)] |= AD524X_SD;
return startWriteCommand(addr, 1, device[(int)(addr & 0x03)], AD524X_STOP, 0, _type);
}
else if ((_type == TYPE_AD5243) || (_type == TYPE_AD5248)) {
atomic device[(int)(addr & 0x03)] |= AD524X_3_8_SD;
return startWriteCommand(addr, 1, device[(int)(addr & 0x03)], AD524X_STOP, 0, _type);
}
return FAIL;
}
command result_t AD524X.setOutput(uint8_t addr, bool output, bool high, ad524x_type_t _type) {
if ((_type == TYPE_AD5241) || (_type == TYPE_AD5242)) {
atomic {
if (!output)
if (high)
device[(int)(addr & 0x03)] |= AD524X_O1;
else
device[(int)(addr & 0x03)] &= ~AD524X_O1;
else
if (high)
device[(int)(addr & 0x03)] |= AD524X_O2;
else
device[(int)(addr & 0x03)] &= ~AD524X_O2;
}
return startWriteCommand(addr, 1, device[(int)addr & 0x03], AD524X_OUTPUT, output, _type);
}
return FAIL;
}
command bool AD524X.getOutput(uint8_t addr, bool output, ad524x_type_t _type) {
if ((_type == TYPE_AD5241) || (_type == TYPE_AD5242)) {
bool _high;
if (!output)
atomic _high = (device[(int)(addr & 0x03)] & AD524X_O1) >> AD524X_O1;
else
atomic _high = (device[(int)(addr & 0x03)] & AD524X_O2) >> AD524X_O2;
return _high;
}
return FALSE;
}
command result_t AD524X.setPot(uint8_t addr, bool _rdac,
uint8_t value, ad524x_type_t _type) {
uint16_t _temp;
if ((_type == TYPE_AD5241) || (_type == TYPE_AD5242)) {
atomic _temp = (device[(int)addr & 0x03] & ~AD524X_RDAC) | (value << 8);
if ((_type == TYPE_AD5242) && (_rdac)) {
_temp |= AD524X_RDAC;
}
return startWriteCommand(addr, 2, _temp, AD524X_WPOT, _rdac, _type);
}
else {
value = value >> 1; // turn 256-pos value to 128-pos value
return startWriteCommand(addr, 1, value, AD524X_WPOT, 0, _type);
}
}
command result_t AD524X.getPot(uint8_t addr, bool _rdac,
ad524x_type_t _type) {
uint8_t _temp;
if (_type == TYPE_AD5242) {
atomic _temp = (device[(int)addr & 0x03] & ~AD524X_RDAC);
return startWriteCommand(addr, 1, _temp, AD524X_RPOT, _rdac, _type);
}
else {
return startReadCommand(addr, 1, AD524X_RPOT, 0, _type);
}
}
event void I2CPacket.readPacketDone(uint16_t _addr, uint8_t _length, uint8_t* _data, result_t _success) {
uint8_t _state;
bool _rdac;
uint8_t _type;
atomic {
_state = state;
_rdac = rdac;
_type = type;
}
// check if the buffer is ours
if (data != _data)
return;
switch (_state) {
case AD524X_RPOT:
state = IDLE;
signal AD524X.getPotDone(_addr & 0x03, _rdac, data[0], _success, _type);
break;
}
}
event void I2CPacket.writePacketDone(uint16_t _addr, uint8_t _length, uint8_t* _data, result_t _success) {
uint8_t _state;
uint8_t _type;
bool _rdac;
atomic {
_state = state;
_type = type;
_rdac = rdac;
}
// check if the buffer is ours
if (data != _data)
return;
switch (_state) {
case AD524X_START:
state = IDLE;
signal AD524X.startDone(_addr & 0x03, _success, _type);
break;
case AD524X_STOP:
state = IDLE;
signal AD524X.stopDone(_addr & 0x03, _success, _type);
break;
case AD524X_OUTPUT:
state = IDLE;
signal AD524X.setOutputDone(_addr & 0x03, _rdac, _success, _type);
break;
case AD524X_WPOT:
state = IDLE;
if (_length == 1)
signal AD524X.setPotDone(_addr & 0x03, 0, _success, _type);
else
signal AD524X.setPotDone(_addr & 0x03, _rdac, _success, _type);
break;
case AD524X_RPOT:
state = IDLE;
startReadCommand(_addr, 1, AD524X_RPOT, rdac, type);
break;
}
}
}
More information about the Tinyos-beta-commits
mailing list