Skip to content
Snippets Groups Projects
Commit e1d736c6 authored by Sergi Hernandez's avatar Sergi Hernandez
Browse files

Added functions to read and erase the eeprom memory.

parent a925a2d5
No related branches found
No related tags found
No related merge requests found
......@@ -8,11 +8,14 @@
#include <string.h>
#include <stdio.h>
#include <iostream>
#include <fstream>
const unsigned char bootloader_ping='#';
const unsigned char bootloader_ack='\n';
const unsigned char bootloader_load='l';
const unsigned char bootloader_go='g';
const unsigned char bootloader_dump='d';
const unsigned char bootloader_clear='c';
typedef enum {original_protocol=0,new_protocol=1} protocol_t;
......@@ -28,6 +31,8 @@ void show_help(char *name)
std::cout << " devices supported by the new protocol:" << std::endl;
std::cout << " - cm510" << std::endl;
std::cout << " - mx servo family" << std::endl;
std::cout << " -c clear eeprom memory" << std::endl;
std::cout << " -r eeprom_file read eeprom memory to file" << std::endl;
std::cout << " -h shows this help" << std::endl;
}
......@@ -41,7 +46,7 @@ int main(int argc,char *argv[])
long int num_data=0,i=0;
bool end=false;
int option;
std::string opt_device,opt_fw_file;
std::string opt_device,opt_fw_file,eeprom_file;
protocol_t protocol;
// binary file variables
unsigned char binary_file[MEMORY_MAXSIZE];
......@@ -52,7 +57,11 @@ int main(int argc,char *argv[])
// bootloader variables
unsigned char bootloader_data[MEMORY_MAXSIZE];
bool bootloader_connected=false;
bool write_fw=false;
unsigned char checksum=0x00;
// eeprom variables
std::ofstream ee_file;
bool read_eeprom=false,clear_eeprom=false;
// configuration information for the serial device
serial_config.baud=57600;
......@@ -63,7 +72,7 @@ int main(int argc,char *argv[])
memset(binary_file,0xFF,MEMORY_MAXSIZE);
// parse the input arguments
while((option = getopt(argc, argv, "hd:f:p:")) != -1)
while((option = getopt(argc, argv, "hd:f:p:cr:")) != -1)
{
switch(option)
{
......@@ -76,6 +85,9 @@ int main(int argc,char *argv[])
break;
case 'f':// select firmware file
std::cout << "Firmware file: " << optarg << std::endl;
write_fw=true;
read_eeprom=false;
clear_eeprom=false;
opt_fw_file=std::string(optarg);
break;
case 'p':// select protocol
......@@ -91,79 +103,115 @@ int main(int argc,char *argv[])
return 0;
}
break;
case 'c':
write_fw=false;
read_eeprom=false;
clear_eeprom=true;
break;
case 'r':// read eeprom memory
write_fw=false;
read_eeprom=true;
clear_eeprom=false;
eeprom_file=std::string(optarg);
break;
}
}
// check that the two arguments have been entered
if(opt_device.size()!=0)
{
if(opt_fw_file.size()==0)
{
std::cout << "No firmware file has been specified" << std::endl;
show_help(argv[0]);
return 0;
}
else
{
try{
// open the serial port
serial_port.open((void *)&opt_device);
// configure the serial port
serial_port.config(&serial_config);
// get the recevice event
events.push_back(serial_port.get_rx_event_id());
// convert the hex file to a binary file
if(opt_fw_file.size()!=0)
{
if(hex2bin((char *)opt_fw_file.c_str(), binary_file, &start_address, &binary_size) == false)
try{
// open the serial port
serial_port.open((void *)&opt_device);
// configure the serial port
serial_port.config(&serial_config);
// get the recevice event
events.push_back(serial_port.get_rx_event_id());
// connect to the bootloader
std::cout << "Switch off device power and turn it on" << std::endl;
while(!bootloader_connected)
{
try{
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,100);
num_data=serial_port.get_num_data();
serial_port.read((unsigned char *)bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
fflush(stdout);
for(i=0;i<num_data;i++)
{
serial_port.close();
std::cout << "Error converting the firmware hex file" << std::endl;
return 0;
if(protocol==new_protocol)
{
if(bootloader_data[i]=='#')
{
count++;
if(count==5)
bootloader_connected=true;
}
}
else
{
if(bootloader_data[i]=='*')
{
count++;
if(count==5)
bootloader_connected=true;
}
}
}
}catch(CEventTimeoutException &e){
// do nothing and retry
serial_port.write((unsigned char *)&bootloader_ping, 1);
}
std::cout << "Switch off device power and turn it on" << std::endl;
// ping the device
while(!bootloader_connected)
}
// ping the device
if(protocol==new_protocol)
{
/* send acknowledgment to the device*/
serial_port.write((unsigned char *)&bootloader_ack, 1);
end=false;
while(!end)
{
try{
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,20);
event_server->wait_all(events,300);
num_data=serial_port.get_num_data();
serial_port.read((unsigned char *)bootloader_data,num_data);
serial_port.read(bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
fflush(stdout);
for(i=0;i<num_data;i++)
{
if(protocol==new_protocol)
{
if(bootloader_data[i]=='#')
{
count++;
if(count==5)
bootloader_connected=true;
}
}
else
{
if(bootloader_data[i]=='*')
{
count++;
if(count==5)
bootloader_connected=true;
}
}
}
}catch(CEventTimeoutException &e){
// do nothing and retry
serial_port.write((unsigned char *)&bootloader_ping, 1);
end=true;
}
}
if(protocol==new_protocol)
}
sleep(1);
// convert the hex file to a binary file
if(write_fw)
{
if(opt_fw_file.size()==0)
{
std::cout << "No firmware file has been specified" << std::endl;
show_help(argv[0]);
return 0;
}
else
{
/* send acknowledgment to the device*/
serial_port.write((unsigned char *)&bootloader_ack, 1);
if(opt_fw_file.size()!=0)
{
if(hex2bin((char *)opt_fw_file.c_str(), binary_file, &start_address, &binary_size) == false)
{
serial_port.close();
std::cout << "Error converting the firmware hex file" << std::endl;
return 0;
}
}
// start the download
serial_port.write((unsigned char *)&bootloader_load,1);
if(protocol==new_protocol)
serial_port.write((unsigned char *)&bootloader_ack,1);
end=false;
while(!end)
{
try{
......@@ -175,17 +223,91 @@ int main(int argc,char *argv[])
printf("%s",bootloader_data);
fflush(stdout);
}catch(CEventTimeoutException &e){
// the flash has been properly erased
end=true;
}
}
// compute the binary file checksum
for(i=0;i<binary_size;i++)
checksum+=binary_file[start_address+i];
// send the binary file in 64 byte segments
while(downloaded_size < binary_size)
{
usleep(1000);
block_size=binary_size-downloaded_size;
if(block_size>64)
block_size=64;
serial_port.write(&binary_file[start_address+downloaded_size],block_size);
downloaded_size+=block_size;
printf("\rDownloading Firmware (%ld/%ld byte)", downloaded_size, binary_size);
fflush(stdout);
}
usleep(1000);
// send the checksum
serial_port.write(&checksum,1);
std::cout << std::endl << "Download complete" << std::endl;
end=false;
while(!end)
{
try{
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,300);
// there has been an error
num_data=serial_port.get_num_data();
serial_port.read(bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
}catch(CEventTimeoutException &e){
// no error to report
end=true;
}
}
}
}
else if(read_eeprom)
{
if(eeprom_file.size()==0)
{
std::cout << "No file has been specified" << std::endl;
show_help(argv[0]);
return 0;
}
sleep(1);
// start the download
serial_port.write((unsigned char *)&bootloader_load,1);
else
{
ee_file.open (eeprom_file.c_str(), std::ofstream::out | std::ofstream::trunc);
if(ee_file.fail())
{
std::cout << "Imposible to create eeprom file" << std::endl;
return 0;
}
else
{
serial_port.write((unsigned char *)&bootloader_dump,1);
if(protocol==new_protocol)
serial_port.write((unsigned char *)&bootloader_ack,1);
end=false;
while(!end)
{
try{
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,1000);
num_data=serial_port.get_num_data();
serial_port.read(bootloader_data,num_data);
ee_file.write((char *)bootloader_data,num_data);
}catch(CEventTimeoutException &e){
end=true;
}
}
ee_file.close();
}
}
}
else if(clear_eeprom)
{
serial_port.write((unsigned char *)&bootloader_clear,1);
if(protocol==new_protocol)
serial_port.write((unsigned char *)&bootloader_ack,1);
// wait for the command ack
end=false;
while(!end)
{
try{
......@@ -197,69 +319,67 @@ int main(int argc,char *argv[])
printf("%s",bootloader_data);
fflush(stdout);
}catch(CEventTimeoutException &e){
// the flash has been properly erased
end=true;
}
}
// compute the binary file checksum
for(i=0;i<binary_size;i++)
checksum+=binary_file[start_address+i];
// send the binary file in 64 byte segments
while(downloaded_size < binary_size)
{
usleep(1000);
block_size=binary_size-downloaded_size;
if(block_size>64)
block_size=64;
serial_port.write(&binary_file[start_address+downloaded_size],block_size);
downloaded_size+=block_size;
printf("\rDownloading Firmware (%ld/%ld byte)", downloaded_size, binary_size);
fflush(stdout);
}
usleep(1000);
// send the checksum
serial_port.write(&checksum,1);
std::cout << std::endl << "Download complete" << std::endl;
// wait for the command to end
end=false;
while(!end)
{
try{
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,300);
// there has been an error
event_server->wait_all(events,5000);
num_data=serial_port.get_num_data();
serial_port.read(bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
fflush(stdout);
end=true;
}catch(CEventTimeoutException &e){
// no error to report
std::cout << "Erase operation did not finish in time" << std::endl;
end=true;
}
}
// start the loaded program
serial_port.write((unsigned char *)&bootloader_go,1);
if(protocol==new_protocol)
serial_port.write((unsigned char *)&bootloader_ack,1);
// read any remaining data
end=false;
while(!end)
{
try{
event_server->wait_all(events,300);
// there has been an error
if((num_data=serial_port.get_num_data()==0))
event_server->wait_all(events,300);
num_data=serial_port.get_num_data();
serial_port.read(bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
fflush(stdout);
}catch(CEventTimeoutException &e){
// no error to report
end=true;
}
}
serial_port.close();
}catch(CException &e){
/* handle exceptions */
std::cout << e.what() << std::endl;
}
// start the loaded program
serial_port.write((unsigned char *)&bootloader_go,1);
if(protocol==new_protocol)
serial_port.write((unsigned char *)&bootloader_ack,1);
end=false;
while(!end)
{
try{
event_server->wait_all(events,300);
// there has been an error
num_data=serial_port.get_num_data();
serial_port.read(bootloader_data,num_data);
bootloader_data[num_data]='\0';
printf("%s",bootloader_data);
}catch(CEventTimeoutException &e){
// no error to report
end=true;
}
}
serial_port.close();
}catch(CException &e){
/* handle exceptions */
std::cout << e.what() << std::endl;
}
}
else
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment