Contiki 2.6

sht15.c

00001 /* Copyright (c) 2009  ARAGO SYSTEMS
00002    All rights reserved.
00003 
00004    Redistribution and use in source and binary forms, with or without
00005    modification, are permitted provided that the following conditions are met:
00006 
00007    * Redistributions of source code must retain the above copyright
00008      notice, this list of conditions and the following disclaimer.
00009    * Redistributions in binary form must reproduce the above copyright
00010      notice, this list of conditions and the following disclaimer in
00011      the documentation and/or other materials provided with the
00012      distribution.
00013    * Neither the name of the copyright holders nor the names of
00014      contributors may be used to endorse or promote products derived
00015      from this software without specific prior written permission.
00016 
00017   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00018   AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019   IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020   ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
00021   LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
00022   CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
00023   SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00024   INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00025   CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
00026   ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00027   POSSIBILITY OF SUCH DAMAGE.
00028 */
00029 #include "dev/sht15.h"
00030 
00031 #define DATA_OUT() P3DIR |= BIT7
00032 #define DATA_IN()  P3DIR &= ~BIT7
00033 #define DATA_SET() P3OUT |= BIT7;  halMcuWaitUs(10)
00034 #define DATA_CLR() P3OUT &= ~BIT7; halMcuWaitUs(10)
00035 #define DATA_VAL() (P3IN & BIT7)
00036 
00037 #define SCK_OUT() P5DIR |= BIT4
00038 #define SCK_SET() P5OUT |= BIT4;  halMcuWaitUs(10)
00039 #define SCK_CLR() P5OUT &= ~BIT4; halMcuWaitUs(10)
00040 
00041 
00042 /***********************************************************************************
00043 * @fn          halMcuWaitUs
00044 *
00045 * @brief       Busy wait function. Waits the specified number of microseconds. Use
00046 *              assumptions about number of clock cycles needed for the various
00047 *              instructions. The duration of one cycle depends on MCLK. In this HAL
00048 *              , it is set to 8 MHz, thus 8 cycles per usec.
00049 *
00050 *              NB! This function is highly dependent on architecture and compiler!
00051 *
00052 * @param       uint16 usec - number of microseconds delay
00053 *
00054 * @return      none
00055 */
00056 
00057 /* #pragma optimize=none */
00058 void
00059 halMcuWaitUs(uint16_t usec) /* 5 cycles for calling */
00060 {
00061   /* The least we can wait is 3 usec: */
00062   /* ~1 usec for call, 1 for first compare and 1 for return */
00063   while(usec > 3)   /* 2 cycles for compare */
00064   {                 /* 2 cycles for jump */
00065     nop();          /* 1 cycles for nop */
00066     nop();          /* 1 cycles for nop */
00067     nop();          /* 1 cycles for nop */
00068     nop();          /* 1 cycles for nop */
00069     nop();          /* 1 cycles for nop */
00070     nop();          /* 1 cycles for nop */
00071     nop();          /* 1 cycles for nop */
00072     nop();          /* 1 cycles for nop */
00073     usec -= 2;      /* 1 cycles for optimized decrement */
00074   }
00075 }                   /* 4 cycles for returning */
00076 
00077 
00078 /**
00079     SHT15/75 Driver
00080 
00081   !!! be advise that the SHT15 and SHT75 are not i2C compliant sensors
00082       they are just designed to not disturb i2C devices on a 2 wire bus
00083       this driver allow to drive the sensor with GPIO and delay
00084 */
00085 
00086 /***********************************************************************************
00087 * @fn          sht15_send_start
00088 *
00089 * @brief       This function perform the start sequence asked by SHT15 and SHT75
00090 *
00091 *
00092 *
00093 * @param       none
00094 *
00095 * @return      none
00096 */
00097 void
00098 sht15_send_start(void)
00099 {
00100   /* Sequence is to set data line to 1 then clock line to 1
00101      then set data line to 0, clock line to 0
00102      then set clock line to 1 and data line to 1
00103                        ___________              ________
00104    data line :  _____/            \___________/
00105                            ___________      ____________
00106    clock line : _________/            \___/
00107   */
00108 
00109   DATA_OUT();
00110   DATA_SET();
00111   SCK_SET();
00112   DATA_CLR();
00113   SCK_CLR();
00114   SCK_SET();
00115   DATA_SET();
00116   SCK_CLR();
00117 }
00118 /***********************************************************************************
00119 * @fn       sht15_read16()
00120 *
00121 * @brief
00122 *
00123 *
00124 *
00125 * @param       none
00126 *
00127 * @return      uint16_t
00128 */
00129 uint16_t
00130 sht15_read16(void)
00131 {
00132   uint16_t i;
00133   DATA_IN();
00134 
00135   SCK_CLR();
00136   uint16_t val = 0;
00137 
00138   for(i = 0; i < 18; i++) {
00139     if((i != 8) && (i != 17)) {
00140       SCK_SET();
00141       if(DATA_VAL()) {
00142         val |= 1;
00143       }
00144 
00145       val <<= 1;
00146       SCK_CLR();
00147     } else if(i == 8) {  /* Wait for first ACK from SHT15 */
00148       DATA_OUT();
00149 
00150       DATA_CLR();
00151 
00152       SCK_SET();
00153       SCK_CLR();
00154 
00155       DATA_IN();
00156     } else if(i == 17) {  /* Wait for second ACK from SHT15 */
00157       DATA_OUT();
00158 
00159       DATA_SET();
00160 
00161       SCK_SET();
00162       SCK_CLR();
00163     }
00164   }
00165   return val;
00166 }
00167 /***********************************************************************************
00168 * @fn          sht15_write8
00169 *
00170 * @brief
00171 *
00172 *
00173 *
00174 * @param       uint8 val
00175 *
00176 * @return      none
00177 */
00178 void
00179 sht15_write8(uint8_t val)
00180 {
00181   uint16_t i;
00182 
00183   DATA_OUT();
00184 
00185   for(i = 0; i < 8; i++) {
00186     halMcuWaitUs(4);
00187     SCK_CLR();
00188 
00189     if(val & 0x80) {
00190       DATA_SET();
00191     } else {
00192       DATA_CLR();
00193     }
00194     val <<= 1;
00195 
00196     SCK_SET();
00197   }
00198 
00199   DATA_IN();
00200 
00201   SCK_CLR();
00202 
00203   while(DATA_VAL());
00204 
00205   SCK_SET();
00206   SCK_CLR();
00207 }
00208 /***********************************************************************************
00209 * @fn          sht15_wait_measure
00210 *
00211 * @brief
00212 *
00213 *
00214 *
00215 * @param       none
00216 *
00217 * @return      none
00218 */
00219 void
00220 sht15_wait_measure(void)
00221 {
00222   while(DATA_VAL());
00223 }
00224 /***********************************************************************************
00225 * @fn          sht15_init
00226 *
00227 * @brief
00228 *
00229 *
00230 *
00231 * @param       none
00232 *
00233 * @return      none
00234 */
00235 void
00236 sht15_init(void)
00237 {
00238   /* DATA and SCK lines are I/O */
00239   P3SEL &= ~BIT7;
00240   P5SEL &= ~BIT4;
00241   /* Set SCK and DATA as output */
00242   DATA_OUT();
00243   SCK_OUT();
00244   DATA_SET();
00245   SCK_SET();
00246 }
00247 /***********************************************************************************
00248 * @fn          sht15_measure_temp
00249 *
00250 * @brief
00251 *
00252 *
00253 *
00254 * @param       none
00255 *
00256 * @return      none
00257 */
00258 void
00259 sht15_measure_temp(void)
00260 {
00261   sht15_send_start();
00262   sht15_write8(3);
00263 }
00264 /***********************************************************************************
00265 * @fn          sht15_measure_hum
00266 *
00267 * @brief
00268 *
00269 *
00270 *
00271 * @param       none
00272 *
00273 * @return      none
00274 */
00275 void sht15_measure_hum()
00276 {
00277   sht15_send_start();
00278   sht15_write8(5);
00279 }
00280 /***********************************************************************************
00281 * @fn          sht15_read_status
00282 *
00283 * @brief
00284 *
00285 *
00286 *
00287 * @param       none
00288 *
00289 * @return      none
00290 */
00291 void
00292 sht15_read_status()
00293 {
00294   sht15_send_start();
00295   sht15_write8(7);
00296 }
00297 /***********************************************************************************
00298 * @fn          sht15_write_status
00299 *
00300 * @brief
00301 *
00302 *
00303 *
00304 * @param       none
00305 *
00306 * @return      none
00307 */
00308 void
00309 sht15_write_status(void)
00310 {
00311   sht15_send_start();
00312   sht15_write8(6);
00313 }
00314 /***********************************************************************************
00315 * @fn          sht15_soft_reset
00316 *
00317 * @brief
00318 *
00319 *
00320 *
00321 * @param       none
00322 *
00323 * @return      none
00324 */
00325 void
00326 sht15_soft_reset(void)
00327 {
00328   sht15_send_start();
00329   sht15_write8(30);
00330 }