Test application for the library FM24Vxx_I2C
Dependencies: DebugLibrary FM24Vxx_I2C mbed
main.cpp
- Committer:
- Yann
- Date:
- 2013-04-03
- Revision:
- 2:dd6a152749c5
- Parent:
- 1:e3c92ff30be3
File content as of revision 2:dd6a152749c5:
#include <string> #include <iostream> #include <iomanip> #include "FM24Vxx_I2C.h" struct UserChoice { char choice; unsigned char moduleId; }; /* * Declare functions */ void AvailableIndicator(); // LED1 flashing for program while program is alive UserChoice DisplayMenuAndGetChoice(); // Display and get the user choice void RunStateMachine_WithStdStringValue(); // Write and read a string void RunStateMachine_WithByteValue(); // Write and read a byte void RunStateMachine_WithShortValue(CFM24VXX_I2C::Mode p_mode); // Write and read a short void RunStateMachine_WithIntegerValue(CFM24VXX_I2C::Mode p_mode); // Write and read an integer void RunStateMachine_WithStdVectorOfByteValue(); // Write and read a buffer of bytes void RunStateMachine_WithLengthPlusStdVectorOfByteValue(); // Write and read a buffer of bytes void ReadStdStringValue(const int p_address); // Read a string enum States { Idle, // Idle state / Read memory operation done Write, // Write memory operation Written, // Write memory operation done Read // Read memory operation }; States g_state; // Process states for memory operations DigitalOut g_availableLed(LED1); // To verify if program in running Ticker g_available; // LED1 will flash with a period of 2s UserChoice g_userChoice; // Used to store user choice from displayed menu CFM24VXX_I2C g_myFM24V10G(p28, p27, 0x00, p12); // Create an instance of the class CFM24VXX_I2C, p9/28: SDA, p10/29:SDL, p12: wired to WP input of FM24Vxx, address: A2=0,A1=1, on I2C bus int main() { unsigned char memoryPage = 0x00; // Launch available indicator g_available.attach(&AvailableIndicator, 2.0); g_myFM24V10G.WriteProtect(false); while (true) { // Interrupt driven processing g_state = Idle; // Set initial state g_userChoice = DisplayMenuAndGetChoice(); // Retrieve the user selection DEBUG("Page select is set to %d", memoryPage) switch (g_userChoice.choice) { case 'a': do { RunStateMachine_WithStdStringValue(); } while (g_state != Idle); break; case 'b': do { RunStateMachine_WithByteValue(); } while (g_state != Idle); break; case 'c': do { RunStateMachine_WithShortValue(CFM24VXX_I2C::BigEndian); } while (g_state != Idle); break; case 'd': do { RunStateMachine_WithShortValue(CFM24VXX_I2C::LittleEndian); } while (g_state != Idle); break; case 'e': do { RunStateMachine_WithIntegerValue(CFM24VXX_I2C::BigEndian); } while (g_state != Idle); break; case 'f': do { RunStateMachine_WithIntegerValue(CFM24VXX_I2C::LittleEndian); } while (g_state != Idle); break; case 'g': do { RunStateMachine_WithStdVectorOfByteValue(); } while (g_state != Idle); break; case 'h': do { RunStateMachine_WithLengthPlusStdVectorOfByteValue(); } while (g_state != Idle); break; case 'i': ReadStdStringValue(0x100); break; case 'j': ReadStdStringValue(0x100); break; case 'k': #if defined(__DEBUG) g_myFM24V10G.DumpMemoryArea(0, 0x14); #else // __DEBUG std::cout << "DEBUG mode is not set, nothing to do!\r" << std::endl; #endif // __DEBUG break; case 'l': g_myFM24V10G.EraseMemoryArea(0, 0x14); break; case 'm': { std::string test("Test"); g_myFM24V10G.Write(0x20, test); } break; case 'n': ReadStdStringValue(0x20); break; case 'o': { const CFM24VXX_SN *sn = g_myFM24V10G.GetSerialNumber(); std::cout << "\tCustomerID\t\t: " << std::setw(4) << std::setfill('0') << std::hex << sn->GetCustomerID() << "\r" << std::endl; std::cout << "\tChecksum\t\t: " << std::setw(2) << std::setfill('0') << std::hex << sn->GetChecksum() << "\r" << std::endl; } break; case 'p': { const CFM24VXX_IDs *deviceId = g_myFM24V10G.GetDeviceID(); #ifdef __DEBUG DEBUG("\tManufacturerID\t\t: %02x", deviceId->GetManufacturerID()); DEBUG("\tProductID\t\t: %02x", deviceId->GetProductID()); DEBUG("\tRevisionID\t\t: %02x", deviceId->GetRevisionID()); DEBUG("\tDensity\t\t\t: %02x", deviceId->GetDensity()); DEBUG("\tVariation\t\t: %02x", deviceId->GetVariation()); #else std::cout << "\tManufacturerID\t\t: " << std::setw(2) << std::setfill('0') << std::hex << deviceId->GetManufacturerID() << "\r" << std::endl; std::cout << "\tProductID\t\t: " << std::setw(2) << std::setfill('0') << std::hex << deviceId->GetProductID() << "\r" << std::endl; std::cout << "\tRevisionID\t\t: " << std::setw(2) << std::setfill('0') << std::hex << deviceId->GetRevisionID() << "\r" << std::endl; std::cout << "\tDensity\t\t\t: " << std::setw(2) << std::setfill('0') << std::hex << deviceId->GetDensity() << "\r" << std::endl; std::cout << "\tVariation\t\t: " << std::setw(2) << std::setfill('0') << std::hex << deviceId->GetVariation() << "\r" << std::endl; #endif // __DEBUG } break; case 's': memoryPage = (memoryPage + 1) % 2; DEBUG("New page select is set to %d", memoryPage) g_myFM24V10G.SelectMemoryPage(memoryPage); do { RunStateMachine_WithStdStringValue(); } while (g_state != Idle); break; default: std::cout << "Invalid user choice\r" << std::endl; break; } // End of 'switch' statement } // End of 'while' statement } // End of program - nerver reached void AvailableIndicator() { g_availableLed = !g_availableLed; } // End of AvailableIndicator UserChoice DisplayMenuAndGetChoice() { static UserChoice userChoice; // Display the title std::cout << "\r" << std::endl << "FM24Vxx_I2C v0.2\r" << std::endl; // Display the menu std::cout << "\tWrite/Read with std::string:\t\t\ta\r" << std::endl; std::cout << "\tWrite/Read with a byte:\t\t\t\tb\r" << std::endl; std::cout << "\tWrite/Read with a short (Big Endian):\t\tc\r" << std::endl; std::cout << "\tWrite/Read with a short (Little Endian):\td\r" << std::endl; std::cout << "\tWrite/Read with an integer (Big Endian):\te\r" << std::endl; std::cout << "\tWrite/Read with an integer (Little Endian):\tf\r" << std::endl; std::cout << "\tWrite/Read with std::vector<byte>:\t\tg\r" << std::endl; std::cout << "\tWrite/Read with std::vector<byte> + length:\th\r" << std::endl; std::cout << "\tRead with std::string:\t\t\t\ti\r" << std::endl; std::cout << "\tRead a string is address 0x0000:\t\tj\r" << std::endl; std::cout << "\tHexadump from address 0x0000:\t\t\tk\r" << std::endl; std::cout << "\tErase from address 0x0000:\t\t\tl\r" << std::endl; std::cout << "\tWrite 'Test' at address 0x0020:\t\t\tm\r" << std::endl; std::cout << "\tRead from address 0x0020:\t\t\tn\r" << std::endl; std::cout << "\tGet serial number:\t\t\t\to\r" << std::endl; std::cout << "\tGet devide ID:\t\t\t\t\tp\r" << std::endl; std::cout << "\tSwitch page select:\t\t\t\ts\r" << std::endl; std::cout << "Enter your choice: " << std::flush; userChoice.choice = getchar(); return userChoice; } void RunStateMachine_WithStdStringValue() { DEBUG_ENTER("RunStateMachine_WithStdStringValue") switch (g_state) { case Idle: g_state = Write; break; case Write: { DEBUG("Writing data..."); time_t ctTime; ctTime = time(NULL); std::string str("Current time is: "); str += ctime(&ctTime); str += " UTC"; std::cout << "RunStateMachine_WithStdStringValue: Write '" << str << "'\r" << std::endl; if (!g_myFM24V10G.Write(0x40, str)) { // Write the string, including the length indicator #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithStdStringValue: write failed at address 256") #else // __DEBUG std::cout << "RunStateMachine_WithStdStringValue: write failed at address 256\r" << std::endl; #endif // __DEBUG g_state = Idle; } else { g_state = Written; } } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas..."); std::string readtext; if (!g_myFM24V10G.Read(0x40, readtext)) { // Read the string, including the length indicator #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithStdStringValue: write failed at address 256") #else // __DEBUG std::cout << "RunStateMachine_WithStdStringValue: write failed at address 256\r" << std::endl; #endif // __DEBUG } else { std::cout << "RunStateMachine_WithStdStringValue: Read: " << readtext << "\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithStdStringValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithStdStringValue") } void RunStateMachine_WithByteValue() { DEBUG_ENTER("RunStateMachine_WithByteValue") switch (g_state) { case Idle: g_state = Write; break; case Write: DEBUG("Writing data...") std::cout << "RunStateMachine_WithByteValue: Write 0xaa\r" << std::endl; if (!g_myFM24V10G.Write(128, (unsigned char)0xaa)) { #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithByteValue: write failed at address 128") #else // __DEBUG std::cout << "RunStateMachine_WithByteValue: write failed at address 128\r" << std::endl; #endif // __DEBUG g_state = Idle; } else { g_state = Written; } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas...") unsigned char value = 0x00; if (!g_myFM24V10G.Read(128, &value)) { #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithByteValue: Read operation failed at address 128") #else // __DEBUG std::cout << "RunStateMachine_WithByteValue: Read operation failed at address 128\r" << std::endl; #endif // __DEBUG } else { std::cout << "RunStateMachine_WithByteValue: Read '0x" << std::setw(2) << std::setfill('0') << std::ios::hex << value << "'\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithByteValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithByteValue") } void RunStateMachine_WithShortValue(CFM24VXX_I2C::Mode p_mode) { DEBUG_ENTER("RunStateMachine_WithShortValue") switch (g_state) { case Idle: g_state = Write; break; case Write: DEBUG("Writing data...") std::cout << "RunStateMachine_WithShortValue: Write 0xbeef\r" << std::endl; if (!g_myFM24V10G.Write(64, (short)0xbeef, p_mode)) { // See http://en.wikipedia.org/wiki/Hexspeak for more ideas on hexadecimal wording!!! DEBUG_FATAL("RunStateMachine_WithShortValue: write failed at address 64") g_state = Idle; } else { g_state = Written; } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas..."); short value = 0; if (!g_myFM24V10G.Read(64, &value, p_mode)) { #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithShortValue: write failed at address 64") #else // __DEBUG std::cout << "RunStateMachine_WithShortValue: write failed at address 64\r" << std::endl; #endif // __DEBUG } else { std::cout << "RunStateMachine_WithShortValue: Read '0x" << std::setw(4) << std::setfill('0') << std::hex << value << "' / '" << (unsigned short)value << "'\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithShortValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithShortValue") } void RunStateMachine_WithIntegerValue(CFM24VXX_I2C::Mode p_mode) { DEBUG_ENTER("RunStateMachine_WithIntegerValue") switch (g_state) { case Idle: g_state = Write; break; case Write: DEBUG("Writing data...") std::cout << "RunStateMachine_WithIntegerValue: Write 0xdeaddead\r" << std::endl; if (!g_myFM24V10G.Write(0, (int)0xdeaddead, p_mode)) { DEBUG_FATAL("RunStateMachine_WithIntegerValue: write failed at address 32") g_state = Idle; } else { g_state = Written; } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas...") int value = 0; if (!g_myFM24V10G.Read(0, &value, p_mode)) { #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithIntegerValue: write failed at address 32") #else // __DEBUG std::cout << "RunStateMachine_WithIntegerValue: write failed at address 32\r" << std::endl; #endif // __DEBUG } else { std::cout << std::setw(8) << std::setfill('0') << std::hex << "RunStateMachine_WithIntegerValue: Read '0x" << value << "'/ '" << (unsigned int)value << "'\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithIntegerValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithIntegerValue") } void RunStateMachine_WithStdVectorOfByteValue() { DEBUG_ENTER("RunStateMachine_WithStdVectorOfByteValue") switch (g_state) { case Idle: g_state = Write; break; case Write: { std::vector<unsigned char> datas; datas.push_back(0xfe); datas.push_back(0xed); datas.push_back(0xfa); datas.push_back(0xce); DEBUG("Writing data...") std::cout << "RunStateMachine_WithStdVectorOfByteValue: Write {0xfe, 0xed, 0xfa, 0xce}\r" << std::endl; if (!g_myFM24V10G.Write(0, datas, false)) { // Write the full buffer, not including the length indication DEBUG_FATAL("RunStateMachine_WithStdVectorOfByteValue: write failed at address 16") g_state = Idle; } else { g_state = Written; } } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas...") std::vector<unsigned char> datas(4); if (!g_myFM24V10G.Read(0, datas, false)) { // Read bytes, without the lenght indication, buffer size shall be set before the call #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithStdVectorOfByteValue: write failed at address 16") #else // __DEBUG std::cout << "RunStateMachine_WithStdVectorOfByteValue: write failed at address 16\r" << std::endl; #endif // __DEBUG } else { std::cout << "RunStateMachine_WithStdVectorOfByteValue: Read {" << "', '" << datas[0] << "', '" << datas[1] << "', '" << datas[2] << "', '" << datas[3] <<"'}\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithStdVectorOfByteValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithStdVectorOfByteValue") } void RunStateMachine_WithLengthPlusStdVectorOfByteValue() { DEBUG_ENTER("RunStateMachine_WithLengthPlusStdVectorOfByteValue") switch (g_state) { case Idle: g_state = Write; break; case Write: { DEBUG("Writing data...") std::vector<unsigned char> datas; datas.push_back(0xde); datas.push_back(0x5e); datas.push_back(0xa5); datas.push_back(0xed); std::cout << "RunStateMachine_WithLengthPlusStdVectorOfByteValue: Write {0xde, 0x5e, 0xa5, 0xed}\r" << std::endl; if (!g_myFM24V10G.Write(0, datas)) { // Write the full buffer, including the length indication DEBUG_FATAL("RunStateMachine_WithLengthPlusStdVectorOfByteValue: write failed at address 8") g_state = Idle; } else { g_state = Written; } } break; case Written: g_state = Read; wait(1.0); // To prevent I2C bus capacity memeory break; case Read: { DEBUG("Reading datas...") std::vector<unsigned char> datas; if (!g_myFM24V10G.Read(8, datas)) { // Read bytes, including the lenght indication, buffer size is not set before the call #ifdef __DEBUG DEBUG_FATAL("RunStateMachine_WithStdVectorOfByteValue: write failed at address 8") #else // __DEBUG std::cout << "RunStateMachine_WithStdVectorOfByteValue: write failed at address 8\r" << std::endl; #endif // __DEBUG } else { std::cout << "RunStateMachine_WithLengthPlusStdVectorOfByteValue: Read bytes:\r" << std::endl; vector<unsigned char>::iterator it; for (it = datas.begin() ; it < datas.end(); it++) { std::cout << "0x" << std::setw(2) << std::setfill('0') << std::hex << *it << " "; } std::cout << "\r" << std::endl; } } g_state = Idle; break; default: std::cout << "RunStateMachine_WithLengthPlusStdVectorOfByteValue: Default!\r" << std::endl; g_state = Idle; break; } DEBUG_LEAVE("RunStateMachine_WithLengthPlusStdVectorOfByteValue") } void ReadStdStringValue(const int p_address) { DEBUG_ENTER("ReadStdStringValue: %d", p_address) DEBUG("Reading datas..."); std::string readtext; if (!g_myFM24V10G.Read(p_address, readtext)) { // Read the string, including the length indicator #ifdef __DEBUG DEBUG_FATAL("ReadStdStringValue: write failed at address 256") #else // __DEBUG std::cout << "ReadStdStringValue: write failed at address 256\r" << std::endl; #endif // __DEBUG } else { std::cout << "ReadStdStringValue: Read:'" << readtext << "'\r" << std::endl; } DEBUG_LEAVE("ReadStdStringValue") }