Library for MAX31850 thermocouple temperature sensor

Files at this revision

API Documentation at this revision

Comitter:
croberts21
Date:
Wed Jan 23 23:44:57 2019 +0000
Commit message:
All files added

Changed in this revision

LinkedList.cpp Show annotated file Show diff for this revision Revisions of this file
LinkedList.h Show annotated file Show diff for this revision Revisions of this file
MAX31850.cpp Show annotated file Show diff for this revision Revisions of this file
MAX31850.h Show annotated file Show diff for this revision Revisions of this file
diff -r 000000000000 -r 5530bf2d0e94 LinkedList.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/LinkedList.cpp	Wed Jan 23 23:44:57 2019 +0000
@@ -0,0 +1,194 @@
+/**
+ * @file    LinkedList.cpp
+ * @brief   Core Utility - Templated Linked List class
+ * @author  sam grove
+ * @version 1.0
+ * @see     
+ *
+ * Copyright (c) 2013
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "LinkedList.h"    // api wrapper
+
+template<class retT>
+LinkedList<retT>::LinkedList()
+{
+    // clear the member
+    _head = 0;
+
+    return;
+}
+
+template<class retT>
+LinkedList<retT>::~LinkedList()
+{
+    // free any memory that is on the heap
+    while(remove(1) != NULL);
+
+    return;
+}
+
+template<class retT>
+retT *LinkedList<retT>::push(void *data)
+{
+    retT *new_node = new retT [1];
+    // make sure the new object was allocated
+    if (0 == new_node)
+    {
+        error("Memory allocation failed\n");
+    }
+    // update the next item in the list to the current head
+    new_node->next = _head;
+    // store the address to the linked datatype
+    new_node->data = data;
+    _head = new_node;
+
+    return _head;
+}
+
+//template<class retT>
+//retT *LinkedList<retT>::insert(void *data, uint32_t loc)
+//{
+//    retT *new_node = new retT [1];
+//    // make sure the new object was allocated
+//    if (0 == new_node)
+//    {
+//        error("Memory allocation failed\n");
+//    }
+//    retT *current = _head->next;
+//    retT *prev = _head;
+//    // move to the item we want to insert
+//    for (uint32_t i=1; i!=(loc-1); i++)
+//    {
+//        prev = current;
+//        current = current->next;
+//    }
+//    // store the address to the linked datatype
+//    new_node->data = data;
+//    // clear the next pointer
+//    new_node->next = 0;
+//    // update the list and store the new stuff
+//    prev->next = new_node;
+//    new_node->next = current;
+//    // store the address to the linked datatype
+//    _head->data = data;
+//
+//    return prev->next;
+//}
+
+template<class retT>
+retT *LinkedList<retT>::append(void *data)
+{
+    retT *current = _head;
+    retT *new_node = new retT [1];
+    // make sure the new object was allocated
+    if (0 == new_node)
+    {
+        error("Memory allocation failed\n");
+    }
+    // store the address to the linked datatype
+    new_node->data = data;
+    // clear the next pointer
+    new_node->next = 0;
+    // check for an empty list
+    if (0 == current)
+    {
+        _head = new_node;
+        return _head;
+    }
+    else
+    {
+        // look for the end of the list
+        while (current->next != 0)
+        {
+            current = current->next;
+        }
+        // and then add the new item to the list
+        current->next = new_node;
+    }
+
+    return current->next;
+}
+
+template<class retT>
+retT *LinkedList<retT>::remove(uint32_t loc)
+{
+    retT *current = _head;
+    retT *prev = 0;
+    // make sure we have an item to remove
+    if ((loc <= length()) && (loc > 0))
+    {
+        // move to the item we want to delete
+        if (1 == loc)
+        {
+            _head = current->next;
+            delete [] current;
+        }
+        else
+        {
+            for (uint32_t i=2; i<=loc; ++i)
+            {
+                prev = current;
+                current = current->next;
+            }
+            // store the item + 1 to replace what we are deleting
+            prev->next = current->next;
+            delete [] current;
+        }
+    }
+
+    return _head;
+}
+
+template<class retT>
+retT *LinkedList<retT>::pop(uint32_t loc)
+{
+    retT *current = _head;
+    // make sure we have something in the location
+    if ((loc > length()) || (loc == 0))
+    {
+        return 0;
+    }
+    // and if so jump down the list
+    for (uint32_t i=2; i<=loc; ++i)
+    {
+        current = current->next;
+    }
+
+    return current;
+}
+
+template<class retT>
+uint32_t LinkedList<retT>::length(void)
+{
+    int32_t count = 0;
+    retT *current = _head;
+    //loop until the end of the list is found
+    while (current != 0)
+    {
+        ++count;
+        current = current->next;
+    }
+
+    return count;
+}
+
+// pre-define the type for the linker
+template class LinkedList<node>;
+
+
+
+
+
diff -r 000000000000 -r 5530bf2d0e94 LinkedList.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/LinkedList.h	Wed Jan 23 23:44:57 2019 +0000
@@ -0,0 +1,124 @@
+/**
+ * @file    LinkedList.h
+ * @brief   Core Utility - Templated Linked List class
+ * @author  sam grove
+ * @version 1.0
+ * @see     
+ *
+ * Copyright (c) 2013
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef LINKEDLIST_H_
+#define LINKEDLIST_H_
+
+#include <stdint.h>
+#include "mbed.h"
+
+/**
+ *  @struct node
+ *  @brief The Linked List structure
+ */ 
+struct node
+{
+    void *data;         /*!< pointer to list member data */
+    struct node *next;  /*!< pointer to the next list member */
+};
+
+/** Example using the LinkedList Class
+ * @code
+ *  #include "mbed.h"
+ *  #include "LinkedList.h"
+ *  
+ *  LinkedList<node>list;
+ *  
+ *  int main()
+ *  {
+ *      node *tmp;
+ *      
+ *      list.push((char *)"Two\n");
+ *      list.append((char *)"Three\n");
+ *      list.append((char *)"Four\n");
+ *      list.push((char*)"One\n");
+ *      list.append((char*)"Five\n");
+ *      
+ *      for(int i=1; i<=list.length(); i++)
+ *      {
+ *          tmp = list.pop(i);
+ *          printf("%s", (char *)tmp->data);
+ *      }
+ *      
+ *      error("done\n");
+ *  }
+ * @endcode
+ */
+
+/**
+ *  @class LinkedList
+ *  @brief API abstraction for a Linked List
+ */ 
+template<class retT>
+class LinkedList
+{
+protected:
+    retT *_head;
+
+public:
+    /** Create the LinkedList object
+     */   
+    LinkedList();
+    
+    /** Deconstructor for the LinkedList object
+     *  Removes any members
+     */ 
+    ~LinkedList();
+
+    /** Add a member to the begining of the list
+     *  @param data - Some data type that is added to the list
+     *  @return The member that was just inserted (NULL if empty)
+     */
+    retT *push(void *data);
+    
+//    /** Add a member to some position in the list
+//     *  @param data - Some data type that is added to the list
+//     *  @param loc - Place in the list to put the data
+//     *  @return The member that was just inserted (NULL if empty)
+//     */
+//    retT *insert(void *data, uint32_t loc);
+    
+    /** Add a member to the end of the list
+     *  @param data - Some data type that is added to the list
+     *  @return The member that was just inserted (NULL if empty)
+     */
+    retT *append(void *data);
+    
+    /** Remove a member from the list
+     *  @param loc - The location of the member to remove
+     *  @return The head of the list
+     */
+    retT *remove(uint32_t loc);
+    
+    /** Get access to a member from the list
+     *  @param loc - The location of the member to access
+     *  @return The member that was just requested (NULL if empty or out of bounds)
+     */
+    retT *pop(uint32_t loc);
+    
+    /** Get the length of the list
+     *  @return The number of members in the list
+     */
+    uint32_t length(void);
+};
+
+#endif /* LINKEDLIST_H_ */
diff -r 000000000000 -r 5530bf2d0e94 MAX31850.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MAX31850.cpp	Wed Jan 23 23:44:57 2019 +0000
@@ -0,0 +1,364 @@
+#include "MAX31850.h"
+
+Serial pc(USBTX, USBRX);
+
+#define ONEWIRE_INPUT(pin)  pin->input()
+#define ONEWIRE_OUTPUT(pin) pin->output()
+#define ONEWIRE_INIT(pin)
+
+LinkedList<node> MAX31850::probes;
+ 
+ 
+MAX31850::MAX31850 (PinName data_pin, PinName power_pin, bool power_polarity) : _datapin(data_pin), _parasitepin(power_pin) {
+    int byte_counter;
+    _power_polarity = power_polarity;
+
+    _power_mosfet = power_pin != NC;
+    
+    for(byte_counter=0;byte_counter<9;byte_counter++)
+        scratchpad[byte_counter] = 0x00;
+    
+    ONEWIRE_INIT((&_datapin));
+
+    if (!unassignedProbe(&_datapin, _ROM))
+        error("No unassigned MAX31850 found!\n");
+    else {
+        _datapin.input();
+        probes.append(this);
+        _parasite_power = false; //only set up to use external power right now
+    }
+}
+
+MAX31850::~MAX31850 (void) {
+    node *tmp;
+    for(int i=1; i<=probes.length(); i++)
+    {
+        tmp = probes.pop(i);
+        if (tmp->data == this)
+            probes.remove(i);
+    }
+}
+
+ 
+bool MAX31850::onewire_reset(DigitalInOut *pin) {
+// This will return false if no devices are present on the data bus
+    bool presence=false;
+    ONEWIRE_OUTPUT(pin);
+    pin->write(0);          // bring low for 500 us
+    wait_us(500);
+    ONEWIRE_INPUT(pin);       // let the data line float high
+    wait_us(90);            // wait 90us
+    if (pin->read()==0) // see if any devices are pulling the data line low
+        presence=true;
+    wait_us(410);
+    return presence;
+}
+ 
+void MAX31850::onewire_bit_out (DigitalInOut *pin, bool bit_data) {
+    ONEWIRE_OUTPUT(pin);
+    pin->write(0);
+    wait_us(3);                 // DXP modified from 5
+    if (bit_data) {
+        pin->write(1); // bring data line high
+        wait_us(55);
+    } else {
+        wait_us(55);            // keep data line low
+        pin->write(1);
+        wait_us(10);            // DXP added to allow bus to float high before next bit_out
+    }
+}
+ 
+void MAX31850::onewire_byte_out(char data) { // output data character (least sig bit first).
+    int n;
+    for (n=0; n<8; n++) {
+        onewire_bit_out(&this->_datapin, data & 0x01);
+        data = data >> 1; // now the next bit is in the least sig bit position.
+    }
+}
+ 
+bool MAX31850::onewire_bit_in(DigitalInOut *pin) {
+    bool answer;
+    ONEWIRE_OUTPUT(pin);
+    pin->write(0);
+    wait_us(3);                 // DXP modified from 5
+    ONEWIRE_INPUT(pin);
+    wait_us(10);                // DXP modified from 5
+    answer = pin->read();
+    wait_us(45);                // DXP modified from 50
+    return answer;
+}
+ 
+char MAX31850::onewire_byte_in() { // read byte, least sig byte first
+    char answer = 0x00;
+    int i;
+    for (i=0; i<8; i++) {
+        answer = answer >> 1; // shift over to make room for the next bit
+        if (onewire_bit_in(&this->_datapin))
+            answer = answer | 0x80; // if the data port is high, make this bit a 1
+    }
+    return answer;
+}
+
+bool MAX31850::unassignedProbe(PinName pin) {
+    DigitalInOut _pin(pin);
+    ONEWIRE_INIT((&_pin));
+    char ROM_address[8];
+    return search_ROM_routine(&_pin, 0xF0, ROM_address);
+}
+ 
+bool MAX31850::unassignedProbe(DigitalInOut *pin, char *ROM_address) {
+    return search_ROM_routine(pin, 0xF0, ROM_address);
+}
+ 
+bool MAX31850::search_ROM_routine(DigitalInOut *pin, char command, char *ROM_address) {
+    bool DS1820_done_flag = false;
+    int DS1820_last_discrepancy = 0;
+    char DS1820_search_ROM[8] = {0, 0, 0, 0, 0, 0, 0, 0};
+    
+    int discrepancy_marker, ROM_bit_index;
+    bool return_value, Bit_A, Bit_B;
+    char byte_counter, bit_mask;
+ 
+    return_value=false;
+    while (!DS1820_done_flag) {
+        if (!onewire_reset(pin)) {
+            return false;
+        } else {
+            ROM_bit_index=1;
+            discrepancy_marker=0;
+            char command_shift = command;
+            for (int n=0; n<8; n++) {           // Search ROM command
+                onewire_bit_out(pin, command_shift & 0x01);
+                command_shift = command_shift >> 1; // now the next bit is in the least sig bit position.
+            } 
+            byte_counter = 0;
+            bit_mask = 0x01;
+            while (ROM_bit_index<=64) {
+                Bit_A = onewire_bit_in(pin);
+                Bit_B = onewire_bit_in(pin);
+                if (Bit_A & Bit_B) {
+                    discrepancy_marker = 0; // data read error, this should never happen
+                    ROM_bit_index = 0xFF;
+                } else {
+                    if (Bit_A | Bit_B) {
+                        // Set ROM bit to Bit_A
+                        if (Bit_A) {
+                            DS1820_search_ROM[byte_counter] = DS1820_search_ROM[byte_counter] | bit_mask; // Set ROM bit to one
+                        } else {
+                            DS1820_search_ROM[byte_counter] = DS1820_search_ROM[byte_counter] & ~bit_mask; // Set ROM bit to zero
+                        }
+                    } else {
+                        // both bits A and B are low, so there are two or more devices present
+                        if ( ROM_bit_index == DS1820_last_discrepancy ) {
+                            DS1820_search_ROM[byte_counter] = DS1820_search_ROM[byte_counter] | bit_mask; // Set ROM bit to one
+                        } else {
+                            if ( ROM_bit_index > DS1820_last_discrepancy ) {
+                                DS1820_search_ROM[byte_counter] = DS1820_search_ROM[byte_counter] & ~bit_mask; // Set ROM bit to zero
+                                discrepancy_marker = ROM_bit_index;
+                            } else {
+                                if (( DS1820_search_ROM[byte_counter] & bit_mask) == 0x00 )
+                                    discrepancy_marker = ROM_bit_index;
+                            }
+                        }
+                    }
+                    onewire_bit_out (pin, DS1820_search_ROM[byte_counter] & bit_mask);
+                    ROM_bit_index++;
+                    if (bit_mask & 0x80) {
+                        byte_counter++;
+                        bit_mask = 0x01;
+                    } else {
+                        bit_mask = bit_mask << 1;
+                    }
+                }
+            }
+            DS1820_last_discrepancy = discrepancy_marker;
+            if (ROM_bit_index != 0xFF) {
+                int i = 1;
+                node *list_container;
+                while(1) {
+                    list_container = probes.pop(i);
+                    if (list_container == NULL) {                             //End of list, or empty list
+                        if (ROM_checksum_error(DS1820_search_ROM)) {          // Check the CRC
+                            return false;
+                        }
+                        for(byte_counter=0;byte_counter<8;byte_counter++)
+                            ROM_address[byte_counter] = DS1820_search_ROM[byte_counter];
+                        return true;
+                    } else {                    //Otherwise, check if ROM is already known
+                        bool equal = true;
+                        MAX31850
+                     *pointer = (MAX31850
+                    *) list_container->data;
+                        char *ROM_compare = pointer->_ROM;
+                        
+                        for(byte_counter=0;byte_counter<8;byte_counter++) {
+                            if ( ROM_compare[byte_counter] != DS1820_search_ROM[byte_counter])
+                                equal = false;
+                        }
+                        if (equal)
+                            break;
+                        else
+                            i++;
+                    }
+                }                        
+            }
+        }
+        if (DS1820_last_discrepancy == 0)
+            DS1820_done_flag = true;
+    }
+    return return_value;
+}
+ 
+void MAX31850::match_ROM() {
+// Used to select a specific device
+    int i;
+    onewire_reset(&this->_datapin);
+    onewire_byte_out( 0x55);  //Match ROM command
+    for (i=0;i<8;i++) {
+        onewire_byte_out(_ROM[i]);
+    }
+}
+ 
+void MAX31850::skip_ROM() {
+    onewire_reset(&this->_datapin);
+    onewire_byte_out(0xCC);   // Skip ROM command
+}
+ 
+bool MAX31850::ROM_checksum_error(char *_ROM_address) {
+    char _CRC=0x00;
+    int i;
+    for(i=0;i<7;i++) // Only going to shift the lower 7 bytes
+        _CRC = CRC_byte(_CRC, _ROM_address[i]);
+    // After 7 bytes CRC should equal the 8th byte (ROM CRC)
+    return (_CRC!=_ROM_address[7]); // will return true if there is a CRC checksum mis-match         
+}
+ 
+bool MAX31850::scratchpad_checksum_error() {
+    char _CRC=0x00;
+    int i;
+    for(i=0;i<8;i++) // Only going to shift the lower 8 bytes
+        _CRC = CRC_byte(_CRC, scratchpad[i]);
+    // After 8 bytes CRC should equal the 9th byte (scratchpad CRC)
+    return (_CRC!=scratchpad[8]); // will return true if there is a CRC checksum mis-match        
+}
+ 
+char MAX31850::CRC_byte (char _CRC, char byte ) {
+    int j;
+    for(j=0;j<8;j++) {
+        if ((byte & 0x01 ) ^ (_CRC & 0x01)) {
+            // DATA ^ LSB CRC = 1
+            _CRC = _CRC>>1;
+            // Set the MSB to 1
+            _CRC = _CRC | 0x80;
+            // Check bit 3
+            if (_CRC & 0x04) {
+                _CRC = _CRC & 0xFB; // Bit 3 is set, so clear it
+            } else {
+                _CRC = _CRC | 0x04; // Bit 3 is clear, so set it
+            }
+            // Check bit 4
+            if (_CRC & 0x08) {
+                _CRC = _CRC & 0xF7; // Bit 4 is set, so clear it
+            } else {
+                _CRC = _CRC | 0x08; // Bit 4 is clear, so set it
+            }
+        } else {
+            // DATA ^ LSB CRC = 0
+            _CRC = _CRC>>1;
+            // clear MSB
+            _CRC = _CRC & 0x7F;
+            // No need to check bits, with DATA ^ LSB CRC = 0, they will remain unchanged
+        }
+        byte = byte>>1;
+    }
+return _CRC;
+}
+ 
+void MAX31850::readAll() {
+    // Convert temperature into scratchpad for all devices at once
+    int delay_time = 75; //default delay time
+
+    skip_ROM(); //Skip ROM command, will convert for all devices
+    
+    onewire_byte_out( 0x44);  //perform temperature conversion
+    
+    wait_ms(delay_time);
+}
+ 
+void MAX31850::read_scratchpad() {
+    // This will copy the MAX31850's 9 bytes of scratchpad data
+    // into the objects scratchpad array. Functions that use
+    // scratchpad values will automaticaly call this procedure.
+    int i;
+    match_ROM();             // Select this device
+    onewire_byte_out( 0xBE);   //Read Scratchpad command
+    for(i=0;i<9;i++) {
+        scratchpad[i] = onewire_byte_in();
+    }
+}
+
+ 
+float MAX31850::getTemp(int scale) {
+    float answer;
+    int reading;
+    read_scratchpad();
+    if (scratchpad_checksum_error()) {
+        //indicate we got a CRC error
+        answer = invalid_conversion;
+        pc.printf("CRC Error\r\n");
+    }
+    else {
+        reading = (scratchpad[1] << 8) + scratchpad[0]; //combine first two bytes of scratchpad 
+        reading  = reading >> 2; //shift right two to drop unused bits
+        if (reading & 0x2000) { //check MSB to determin sign 
+            reading = 0-((reading ^ 0x3fff) + 1); //use 2's compliment to convert back to positive number and make it a signed int
+        }
+        answer = reading +0.0; //convert to floating point
+        answer = answer / 4.0; //shift decimal place over two places
+
+        //unit convertion 
+        //checks for passed in value first and if there is none it sets the units baced on class units variable
+        switch(scale) {
+            case C:
+                break;
+            case K:
+                answer = answer + 273.15f;
+                break;
+            case F:
+                answer = answer * 1.8f + 32.0f;
+                break;
+            case R:
+                answer = answer * 1.8f + 491.67f;
+                break;
+            default:
+                switch(_units) {
+                    case C:
+                        break;
+                    case K:
+                        answer = answer + 273.15f;
+                        break;
+                    case F:
+                        answer = answer * 1.8f + 32.0f;
+                        break;
+                    case R:
+                        answer = answer * 1.8f + 491.67f;
+                        break;
+                }
+        }
+    }
+    return answer;
+}
+
+// Contributed by John M. Larkin (jlarkin@whitworth.edu)
+unsigned long long MAX31850::getId() {
+// This will return the 64 bit address of the connected MAX31850
+    unsigned long long myName = 0;
+    for (int i = 0; i<8; i++) {
+        myName = (myName<<8) | _ROM[i];
+    }
+    return myName;
+}
+
+void MAX31850::setUnits(int units) {
+    _units = units;
+}
\ No newline at end of file
diff -r 000000000000 -r 5530bf2d0e94 MAX31850.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MAX31850.h	Wed Jan 23 23:44:57 2019 +0000
@@ -0,0 +1,165 @@
+/* mbed MAX31850
+ Library, for the Dallas (Maxim) 1-Wire Digital Thermometer
+ * Copyright (c) 2010, Michael Hagberg Michael@RedBoxCode.com
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ * 
+ * 
+ * This library has been adapted from the DS1820 library to work with MAX31850 thermocouple sensor
+ * Chris Roberts (croberts21@my.whitworth.edu)
+ * Craig Russell (crussell21@my.whitworth.edu)
+ * 
+ * For our application, we modified readAll() (previously convertTemperature) to force a small 
+ * wait rather than it being optional, and removed the ability to select a single sensor.
+ * 
+ * getTemp() (previously temperature) has been updated to deal with the correct number of bits that 
+ * the temperature is stored in as well as updated convertions to all four units
+ * 
+ *  as well as adding a setUnits() function to set the 
+ * units that the sensor will return.
+ * 
+ * We removed some functionality that dealt with parasite power. 
+ * 
+ *
+ */
+
+#ifndef MBED_MAX31850_H
+#define MBED_MAX31850_H
+
+#include "mbed.h"
+#include "LinkedList.h"
+
+#define C 0 //celsius 
+#define K 1 //Kelvin
+#define F 2 //fahrenheit
+#define R 3 //Rankin
+
+extern Serial pc;
+
+/** MAX31850
+ *
+ * Example:
+ * @code
+ * #include "mbed.h"
+ * #include "MAX31850.h"
+ *
+ * MAX31850 probe(DATA_PIN);
+ *  
+ * int main() {
+ *     while(true) {
+ *         probe.convertTemperature(true, MAX31850::all_devices); //Start temperature conversion, wait until ready
+ *         printf("It is %3.1foC\r\n", probe.temperature());
+ *         wait(1);
+ *     }
+ * }
+ * @endcode
+ */
+class MAX31850
+ {
+public:
+    enum devices{
+        this_device,     // command applies to only this device
+        all_devices };   // command applies to all devices
+    
+    enum {
+        invalid_conversion = -1000
+    };
+
+    /** Create a probe object connected to the specified pins
+    * 
+    * The probe might either by regular powered or parasite powered. If it is parasite
+    * powered and power_pin is set, that pin will be used to switch an external mosfet connecting
+    * data to Vdd. If it is parasite powered and the pin is not set, the regular data pin
+    * is used to supply extra power when required. This will be sufficient as long as the 
+    * number of probes is limitted.
+    * 
+    * For our application, we have the functions set up to only use external power. The constructor still supports
+    * parasite power but the functions to not support it.
+    */
+    MAX31850 (PinName data_pin, PinName power_pin = NC, bool power_polarity = 0); // Constructor with parasite power pin
+  
+    ~MAX31850();
+
+    /** Function to see if there are MAX31850
+     *  devices left on a pin which do not have a corresponding MAX31850
+     *  object
+    *
+    * @return - true if there are one or more unassigned devices, otherwise false
+      */
+    static bool unassignedProbe(PinName pin);
+
+    /** This routine will initiate the temperature conversion within
+      *  all MAX31850
+      *  probes. 
+      */
+    void readAll();
+
+    /** This function will return the probe temperature. Approximately 10ms per
+      * probe to read its scratchpad, do CRC check and convert temperature on the LPC1768.
+      *
+      * @scratchpad scale, may be either 'c', 'f', 'k', and 'r'
+      * @returns temperature for that scale, or MAX31850::invalid_conversion (-1000) if CRC error detected.
+      */
+    float getTemp(int scale = 4);     
+
+    /** This function returns the 64 bit address associated with a
+      * particular DS18B20.
+      *
+      * Contributed by John M. Larkin (jlarkin@whitworth.edu)
+      *
+      * @returns unsigned long long
+      */
+    unsigned long long getId();
+
+
+    /** This function sets the _units variable to the 
+     * users desired temperature units
+     */
+    void setUnits(int);
+    
+
+private:
+    bool _parasite_power;
+    bool _power_mosfet;
+    bool _power_polarity;
+    
+    static char CRC_byte(char _CRC, char byte );
+    static bool onewire_reset(DigitalInOut *pin);
+    void match_ROM();
+    void skip_ROM();
+    static bool search_ROM_routine(DigitalInOut *pin, char command, char *ROM_address);
+    static void onewire_bit_out (DigitalInOut *pin, bool bit_data);
+    void onewire_byte_out(char data);
+    static bool onewire_bit_in(DigitalInOut *pin);
+    char onewire_byte_in();
+    static bool ROM_checksum_error(char *_ROM_address);
+    bool scratchpad_checksum_error();
+    void read_scratchpad();
+    static bool unassignedProbe(DigitalInOut *pin, char *ROM_address);
+
+    DigitalInOut _datapin;
+    DigitalOut _parasitepin;
+    
+    char _ROM[8];
+    char scratchpad[9];
+    int _units;
+    
+    static LinkedList<node> probes;
+};
+#endif
\ No newline at end of file