This class provides simplified I2C access to a Microchip 24LCxx Serial EEPROM device: - Rename the class (C2424 -> C24) - Add EraseMemoryArea method - Add DumpMemoryArea method only accessible in DEBUG mode - Add 'const' qualifier in parameters

Fork of 24LCxx_I2C by Yann Garcia

24LCxx_I2C.cpp

Committer:
acesrobertm
Date:
2018-04-25
Revision:
4:650f3259bd4f
Parent:
3:5df584fbabfe
Child:
5:2f61885d8bc3

File content as of revision 4:650f3259bd4f:

/* mbed simplified access to Microchip 24LCxx Serial EEPROM devices (I2C)
 * Copyright (c) 2010-2012 ygarcia, MIT License
 *
 * 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.
 */
 
#include "24LCxx_I2C.h"

namespace _24LCXX_I2C {
    C24LCXX_I2C::C24LCXX_I2C(const PinName p_sda, const PinName p_scl, const unsigned char p_address, const unsigned int p_frequency) {
        
        _i2cInstance = new I2C(p_sda, p_scl); //, "24LCxx_I2C"
        _slaveAddress = (p_address << 1) | 0xa0; // Slave address format is: 1 0 1 0 A3 A2 A1 R/W
        _i2cInstance->frequency(p_frequency); // Set the frequency of the I2C interface
    }

    C24LCXX_I2C::~C24LCXX_I2C() {
        delete _i2cInstance;
        _i2cInstance = NULL;
    }

    bool C24LCXX_I2C::Write(const short p_address, const unsigned char p_byte) {
        // 1.Prepare buffer
        char i2cBuffer[3]; // Memory address + one byte of data
        // 1.1. Memory address
        short address = p_address;
        i2cBuffer[0] = (unsigned char)(address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)address & 0xff);
        // 1.2. Datas
        i2cBuffer[2] = p_byte;
    
        // 2. Send I2C start + I2C address + Memory Address + Datas + I2C stop
        int result = _i2cInstance->write(_slaveAddress, i2cBuffer, 3);
        wait(0.02);
    
        return (bool)(result == 0);
    }
    
    bool C24LCXX_I2C::Write(const short p_address, const short p_short, const C24LCXX_I2C::Mode p_mode) {
        // 1.Prepare buffer
        char i2cBuffer[4]; // Memory address + one short (2 bytes)
        // 1.1. Memory address
        short address = p_address;
        i2cBuffer[0] = (unsigned char)(address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)address & 0xff);
        // 1.2. Datas
        if (p_mode == BigEndian) {
            i2cBuffer[2] = (unsigned char)(p_short >> 8);
            i2cBuffer[3] = (unsigned char)((unsigned char)p_short & 0xff);
        } else {
            i2cBuffer[2] = (unsigned char)((unsigned char)p_short & 0xff);
            i2cBuffer[3] = (unsigned char)(p_short >> 8);
        }
    
        // 2. Send I2C start + I2C address + Memory Address + Datas + I2C stop
        int result = _i2cInstance->write(_slaveAddress, i2cBuffer, 4);
        wait(0.02);
    
        return (bool)(result == 0);
    }
    
    bool C24LCXX_I2C::Write(const short p_address, const int p_int, const C24LCXX_I2C::Mode p_mode) {
        // 1.Prepare buffer
        char i2cBuffer[6]; // Memory address + one integer (4 bytes)
        // 1.1. Memory address
        short address = p_address;
        i2cBuffer[0] = (unsigned char)(address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)address & 0xff);
        // 1.2. Datas
        if (p_mode == BigEndian) {
            i2cBuffer[2] = (unsigned char)(p_int >> 24);
            i2cBuffer[3] = (unsigned char)(p_int >> 16);
            i2cBuffer[4] = (unsigned char)(p_int >> 8);
            i2cBuffer[5] = (unsigned char)((unsigned char)p_int & 0xff);
        } else {
            i2cBuffer[2] = (unsigned char)((unsigned char)p_int & 0xff);
            i2cBuffer[3] = (unsigned char)(p_int >> 8);
            i2cBuffer[4] = (unsigned char)(p_int >> 16);
            i2cBuffer[5] = (unsigned char)(p_int >> 24);
        }
    
        // 2. Send I2C start + I2C address + Memory Address + Datas + I2C stop
        int result = _i2cInstance->write(_slaveAddress, i2cBuffer, 6);
        wait(0.02);
    
        return (bool)(result == 0);
    }
    
    bool C24LCXX_I2C::Read(const short p_address, unsigned char * p_byte) {
        // 1.Prepare buffer
        char i2cBuffer[2];
        // 1.1. Memory address
        i2cBuffer[0] = (unsigned char)(p_address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)p_address & 0xff);
    
        // 2. Send I2C start + memory address
        if (_i2cInstance->write(_slaveAddress, i2cBuffer, 2, true) == 0) {
            // 2. Read data + I2C stop
            int result = _i2cInstance->read(_slaveAddress, (char *)p_byte, 1);
    
            return (bool)(result == 0);
        }
    
        return false;
    }
    
    bool C24LCXX_I2C::Read(const short p_address, short *p_short, const C24LCXX_I2C::Mode p_mode) {
        // 1.Prepare buffer
        char i2cBuffer[2];
        // 1.1. Memory address
        i2cBuffer[0] = (unsigned char)(p_address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)p_address & 0xff);
    
        // 2. Send I2C start + memory address
        if (_i2cInstance->write(_slaveAddress, i2cBuffer, 2, true) == 0) {
            // 2. Read data + I2C stop
            int result = _i2cInstance->read(_slaveAddress, i2cBuffer, 2);
            if (result == 0) {
                if (p_mode ==  BigEndian) {
                    *p_short = (short)(i2cBuffer[0] << 8 | i2cBuffer[1]);
                } else {
                    *p_short = (short)(i2cBuffer[1] << 8 | i2cBuffer[0]);
                }
        
                return true;
            }
        }
    
        return false;
    }
    
    bool C24LCXX_I2C::Read(const short p_address, int *p_int, const C24LCXX_I2C::Mode p_mode) {
        // 1.Prepare buffer
        char i2cBuffer[4];
        // 1.1. Memory address
        i2cBuffer[0] = (unsigned char)(p_address >> 8);
        i2cBuffer[1] = (unsigned char)((unsigned char)p_address & 0xff);
    
        // 2. Send I2C start + memory address
        if (_i2cInstance->write(_slaveAddress, i2cBuffer, 2, true) == 0) {
            // 2. Read data + I2C stop
            int result = _i2cInstance->read(_slaveAddress, i2cBuffer, 4);
            if (result == 0) {
                if (p_mode ==  BigEndian) {
                    *p_int = (int)(i2cBuffer[0] << 24 | i2cBuffer[1] << 16 | i2cBuffer[2] << 8 | i2cBuffer[3]);
                } else {
                    *p_int = (int)(i2cBuffer[3] << 24 | i2cBuffer[2] << 16 | i2cBuffer[1] << 8 | i2cBuffer[0]);
                }
                return true;
            }
            return false;
        }
        return false;
    }
} // End of namespace _24LCXX_I2C