Release 2017.11.4

EEPROM用のユーティリティスケッチ

EEPROMライブラリの使い方について書きましたが、EEPROMの中身はその都度コードを書いていかないと、中身を見たり、いじることは出来ません。そこで、EEPROM内容を操作することに特化したスケッチを書いてみました。

シリアルモニタの「送信」を使って操作するので、Arduino本体とPCさえあればOKです。

  • EEPROMの中身をリスト表示
  • 特定のアドレス、或いは全部を書き換える

が出来ます。

スケッチ

プロジェクトファイルをダウンロードするか、下記のコードをコピペしてArduinoに書き込んで使ってください。

click to download – EEPROM Utility ver 1.0

//                                   version 1.0
//            << EEPROM utility >>
//   2017.11.3                   by jumbleat.com
//
#include <EEPROM.h>
#define BPS 38400
char cmd;
long input_val;
long tgt_val[4];
byte menu;
int  eep_size;
bool error;
#define RET_IS_CMD 1
#define RET_IS_VAL 2
#define M_HOME   0
#define M_LIST   1
#define M_LISTAL 2
#define M_VALUE  3
#define M_VALUES 4
#define M_VALALL 5
#define MENU_SIZE 6
#define M_TXT_NUM 17
char command_menu[MENU_SIZE + 1][M_TXT_NUM] {
"HOME",
"EEPROM List",
"EEPROM List All",
"Set a Value",
"Set Values",
"Set Vaule to All",
"Back to menu"
};
const byte m_crn [MENU_SIZE + 1] = {12, 5, 1, 5, 6, 0, 4};
#define CUR_MODE   0
#define ASK_ADRS   1
#define ASK_VAL    2
#define ASK_S_ADRS 3
#define ASK_E_ADRS 4
char msg_parts[4][8] {
/*0*/  "value",
/*1*/  "command",
/*2*/  "mode",
/*3*/  "address"
};
char command_alp[MENU_SIZE + 1] = {'0', 'l', 'a', 'v', 's', 'r', 'z'};
char icons [5] = {' ', '>', '[', ']', ':'};
char pros[2][11] = {"processing", "done"};
void SET_MENU() {
menu = M_HOME;
Serial.println();
PRINT_MENU();
PRINT_CD();
PRINT_CURSOR(CUR_MODE);
}
boolean CHECK(int val_low, int val_high, byte dist_array) {
if (tgt_val[dist_array] >= val_low && tgt_val[dist_array] <= val_high && !error)
{
menu++;
Serial.println();
return true;
} else {
if (!error) PRINT_ERROR(0);
}
return false;
}
boolean SET_ADD(int dist_array, byte msg) {
if (CHECK (0, eep_size - 1, dist_array))
{
if (dist_array == 2)
{
if (tgt_val[1] > tgt_val[2])
{
int temp = tgt_val[1];
tgt_val[1] = tgt_val[2];
tgt_val[2] = temp;
}
}
return true;
} else {
PRINT_CURSOR(msg);
return false;
}
}
boolean SET_VAL(int dist_array, byte msg, bool limit) {
if (CHECK (0, 255, dist_array))
{
return true;
} else {
PRINT_CURSOR(msg);
return false;
}
}
void WRITE_VAL(int ads_low, int ads_high, long val) {
int times = ads_high - ads_low;
Serial.println();
Serial.print("address :");
Serial.print(ads_low);
if (times > 1)
{
Serial.print("-");
Serial.print(ads_high);
}
Serial.println();
Serial.print("value   :");
Serial.print(val);
Serial.println();
delay(1500);
for (int i = ads_low ; i <= ads_high ; i++)
{
for (byte ii = 0 ; ii < 2 ; ii++)
{
LIST(i, i);
Serial.print(" - ");
delay(30);
Serial.println(pros[ii]);
if (ii == 0) EEPROM[i] = val;
}
}
delay(1000);
SET_MENU();
}
void WRITE_VAL_ALL(int val) {
Serial.print("-write ");
Serial.print(val);
Serial.print(" to all address");
Serial.print("    ");
delay(500);
Serial.print(pros[0]);
for (int i = 0 ; i < eep_size ; i++)
{
EEPROM[i] = val;
if ((i % (eep_size / 3)) == 0)
{
Serial.print(".");
delay(50);
}
}
Serial.println(pros[1]);
delay(1000);
Serial.println();
LIST(0, eep_size);
Serial.println();
Serial.println();
delay(1000);
SET_MENU();
}
byte SERIAL_VAL() {
if (Serial.available() > 0)
{
delay(20);
byte data_size = Serial.available();
byte buf[data_size], degree = 1;
long recv_data = 0, dub = 1;
bool minus = 0;
for (byte i = 0 ; i < data_size ; i++)
{
buf[i] = Serial.read();
if (buf[i] >= '0' && buf[i] <= '9') buf[i] -= '0';
else {
if (buf[0] == '-') minus = 1;
else {
cmd = buf[i];
degree = 0;
}
}
}
if (degree == 1) degree = data_size - minus;
for (byte i = 0 ; i < degree ; i++)
{
recv_data += buf[(data_size - 1) - i] * dub;
dub *= 10;
}
if (minus) recv_data *= -1;
if (degree != 0)
{
input_val = recv_data;
return RET_IS_VAL;
} else {
return RET_IS_CMD;
}
}
return 0;
}
void PRINT_SPACE(byte times) {
for (byte spc = 0 ; spc < times ; spc++) Serial.print(icons[0]);
}
void PRINT_CD() {
Serial.print(msg_parts[2]);
for (byte i = 0 ; i < 2 ; i++) Serial.print(icons[4]);
Serial.print(command_menu[menu / 10]);
Serial.println();
delay(500);
}
void PRINT_CURSOR(byte msg) {
if (msg == CUR_MODE) Serial.print("select command");
if (msg == ASK_VAL)
{
Serial.print("set value");
Serial.print(" (0-255) ");
}
else if (msg >= ASK_ADRS)
{
if (msg == ASK_ADRS)  Serial.print("set address");
if (msg == ASK_S_ADRS) Serial.print("set start address");
if (msg == ASK_E_ADRS) Serial.print("set end address");
Serial.print(" (0-");
Serial.print(eep_size - 1);
Serial.print(")");
}
PRINT_SPACE(1);
for (byte i = 1 ; i <= 2 ; i++) Serial.print(icons[i % 2]);
}
void PRINT_MENU() {
Serial.println();
for (byte i = 1 ; i <= MENU_SIZE ; i++)
{
Serial.print(icons[2]);
Serial.print(command_alp[i]);
Serial.print(icons[3]);
Serial.print(command_menu[i]);
PRINT_SPACE(m_crn[i]);
if (i == 3) Serial.println();
else PRINT_SPACE(3);
}
Serial.println();
}
void PRINT_ERROR(byte types) {
Serial.print(" - Invalid ");
Serial.print(msg_parts[types]);
Serial.print(" !");
Serial.println();
delay(700);
}
void LIST(int s_pos, int e_pos) {
for (int i = s_pos ; i <= e_pos ; i++)
{
byte val = EEPROM[i];
Serial.print(icons[2]);
// fill by 0
for (byte zro = 1; zro < 4; zro++) if (i < pow(10, zro)) Serial.print("0");
Serial.print(i);          // address number
Serial.print(icons[3]);
// fill by 0
for (byte zro = 1; zro < 3; zro++) if (val < pow(10, zro)) Serial.print("0");
Serial.print(val);  // value
if (((i - s_pos  + 1) % 10) == 0) Serial.println();
else PRINT_SPACE(2);
}
}
void SHOW_LIST(int s_val, int e_val, bool pattern) {
Serial.println();
if (pattern)
{
Serial.print("-List from ");
Serial.print(tgt_val[1]);
Serial.print(" to ");
Serial.println(tgt_val[2]);
delay(700);
}
LIST(s_val, e_val);
Serial.println();
delay(1000);
SET_MENU();
}
void DISP_ROMSIZE() {
Serial.print("EEPROM size:");
Serial.println(eep_size);
delay(1000);
}
void setup() {
Serial.begin(BPS);
Serial.print("<< EEPROM utility  version 1.0 >>");
PRINT_SPACE(1);
Serial.print("by jumbleat.com");
PRINT_SPACE(3);
Serial.println("2017.11.3");
Serial.println();
eep_size = EEPROM.length();
DISP_ROMSIZE();
SET_MENU();
}
void loop() {
byte ret = SERIAL_VAL();
if (ret > 0)
{
if (ret == RET_IS_VAL)
{
Serial.print(input_val);
tgt_val[menu % 10] = input_val;
} else if (ret == RET_IS_CMD) {
Serial.print(cmd);
if (cmd == command_alp[1]) menu = M_LIST * 10;
else if (cmd == command_alp[2]) menu = M_LISTAL * 10;
else if (cmd == command_alp[3]) menu = M_VALUE * 10;
else if (cmd == command_alp[4]) menu = M_VALUES * 10;
else if (cmd == command_alp[5]) menu = M_VALALL * 10;
else if (cmd == command_alp[6]) menu = M_HOME;
else
{
error = true;
PRINT_ERROR(1);
}
}
if (menu == M_HOME)
{
if (ret == RET_IS_VAL) PRINT_ERROR(0);
SET_MENU();
} else if (menu >= 10) {
if ((menu % 10) == 0)
{
Serial.println();
Serial.println();
PRINT_CD();
}
input_val = 0;
// set all values in EEPROM
if (menu >= (M_VALALL * 10))
{
if (menu == (M_VALALL * 10))
{
PRINT_CURSOR(ASK_VAL);
menu++;
} else if (menu == ((M_VALALL * 10) + 1)) {
if (SET_VAL (1, ASK_VAL, 1)) WRITE_VAL_ALL(tgt_val[1]);
}
// set values to pointed address
} else if (menu >= (M_VALUES * 10)) {
if (menu == (M_VALUES * 10))
{
PRINT_CURSOR(ASK_S_ADRS);
menu++;
} else if (menu == ((M_VALUES * 10) + 1)) {
if (SET_ADD (1, ASK_S_ADRS)) PRINT_CURSOR(ASK_E_ADRS);
} else if (menu == ((M_VALUES * 10) + 2)) {
if (SET_ADD (2, ASK_E_ADRS))
{
Serial.println();
LIST(tgt_val[1], tgt_val[2]);
Serial.println();
PRINT_CURSOR(ASK_VAL);
}
} else if (menu == ((M_VALUES * 10) + 3)) {
if (SET_VAL (3, ASK_VAL, 1)) WRITE_VAL(tgt_val[1], tgt_val[2], tgt_val[3]);
}
// set value to single EEPROM address
} else if (menu >= (M_VALUE * 10)) {
if (menu == (M_VALUE * 10))
{
PRINT_CURSOR(ASK_ADRS);
menu++;
} else if (menu == ((M_VALUE * 10) + 1)) {
if (SET_ADD (1, ASK_ADRS))
{
LIST(tgt_val[1], tgt_val[1]);
PRINT_CURSOR(ASK_VAL);
}
} else if (menu == ((M_VALUE * 10) + 2)) {
if (SET_VAL (2, ASK_VAL, 1)) WRITE_VAL(tgt_val[1], tgt_val[1], tgt_val[2]);
}
// display list of all EEPROM value
} else if (menu >= (M_LISTAL * 10)) {
SHOW_LIST(0, eep_size - 1, 0);
// display list of pointed EEPROM address
} else if (menu >= (M_LIST * 10)) {
if (menu == (M_LIST * 10))
{
PRINT_CURSOR(ASK_S_ADRS);
menu++;
} else if (menu == ((M_LIST * 10) + 1)) {
if (SET_ADD (1, ASK_S_ADRS)) PRINT_CURSOR(ASK_E_ADRS);
} else if (menu == ((M_LIST * 10) + 2)) {
if (SET_ADD (2, ASK_E_ADRS)) SHOW_LIST(tgt_val[1], tgt_val[2], 1);
}
}
}
}
error = false;
}

一通りの動作確認はしましたが、ひょっとしたら、まだバグがあるかもしれません。悪しからず。

使い方

使い方は至って単純です。シリアルモニタの入力フィールドに文字・数値を入れ、送信することで操作します。

後は、コメントに沿って、アドレスや値の入力をして決定していきます。

数値は範囲を超えての入力が出来ないようにしています。例えば、アドレスであればEEPROMの容量を超えたサイズ、入力値であれば255以上を入れることは出来ません。

シリアル通信のボーレートは「38400」に設定しているので、シリアルモニタの設定を合わせてください。或いは、最初に書かれているdefine定義値で変更することも出来ます。

#define BPS 38400

機能(モード)

ショートカットコマンド(カッコ内のアルファベット)を送信することでモードが切り替わります。また、コマンドは、入力途中でも、キャンセル・移行することが出来ます。

EEPROM List [ l ]

指定したアドレス範囲の保存値を一覧表示します。始まりと終わりのアドレスを入力してください。

EEPROM List All [ a ]

使用しているArduinoのEEPROM内全ての保存値を一覧表示します。

Set a Value [ v ]

特定アドレスの値(1つ)を書き換えます。アドレスと書き換えたい数値を入力してください。

Set Values [ s ]

特定のアドレス範囲を、全て指定した値に書き換えます。始まりと終わりのアドレス、変更したい値を入力してください。

Set Vaule to All [ r ]

使用しているArduinoのEEPROM内全ての保存値を、指定した値に書き換えます。書き換えたい値を入力してください。

Back to menu [ z ]

メニュー表示に戻ります。各モードで入力中にキャンセルしたい場合などに使ってください。

 

こういったものって探しても意外にないと思うので、結構活用してもらえると思います。お役立てください。

コメントを残す

このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください