This is how Print::print
prints from program memory in the Arduino library:
size_t Print::print(const __FlashStringHelper *ifsh)
{
const char PROGMEM *p = (const char PROGMEM *)ifsh;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
__FlashStringHelper*
is an empty class that allows for overloaded functions like print to differentiate a pointer to program memory from one to normal memory, as both are seen as const char*
by the compiler (see http://stackoverflow.com/questions/16597437/arduino-f-what-does-it-actually-do https://stackoverflow.com/questions/16597437/arduino-f-what-does-it-actually-do)
So you could overload the print
function for your LCD display so that it takes a __FlashStringHelper*
argument, lets call it LCD::print
, and then use lcd.print(F("this is a string in progmem"));' to call it.
F()` is a macro that ensures the string is in program memory.
To predefine the string (to be compatible with built-in Arduino print) I have used:
const char firmware_version_s[] PROGMEM = {"1.0.2"};
__FlashStringHelper* firmware_version = (__FlashStringHelper*) firmware_version_s;
...
Serial.println(firmware_version);
I think an alternative would be something like
size_t LCD::print_from_flash(const char *pgms)
{
const char PROGMEM *p = (const char PROGMEM *) pgms;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
which would avoid the __FlashStringHelper
cast.
This is how Print::print
prints from program memory in the Arduino library:
size_t Print::print(const __FlashStringHelper *ifsh)
{
const char PROGMEM *p = (const char PROGMEM *)ifsh;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
__FlashStringHelper*
is an empty class that allows for overloaded functions like print to differentiate a pointer to program memory from one to normal memory, as both are seen as const char*
by the compiler (see http://stackoverflow.com/questions/16597437/arduino-f-what-does-it-actually-do)
So you could overload the print
function for your LCD display so that it takes a __FlashStringHelper*
argument, lets call it LCD::print
, and then use lcd.print(F("this is a string in progmem"));' to call it.
F()` is a macro that ensures the string is in program memory.
To predefine the string (to be compatible with built-in Arduino print) I have used:
const char firmware_version_s[] PROGMEM = {"1.0.2"};
__FlashStringHelper* firmware_version = (__FlashStringHelper*) firmware_version_s;
...
Serial.println(firmware_version);
I think an alternative would be something like
size_t LCD::print_from_flash(const char *pgms)
{
const char PROGMEM *p = (const char PROGMEM *) pgms;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
which would avoid the __FlashStringHelper
cast.
This is how Print::print
prints from program memory in the Arduino library:
size_t Print::print(const __FlashStringHelper *ifsh)
{
const char PROGMEM *p = (const char PROGMEM *)ifsh;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
__FlashStringHelper*
is an empty class that allows for overloaded functions like print to differentiate a pointer to program memory from one to normal memory, as both are seen as const char*
by the compiler (see https://stackoverflow.com/questions/16597437/arduino-f-what-does-it-actually-do)
So you could overload the print
function for your LCD display so that it takes a __FlashStringHelper*
argument, lets call it LCD::print
, and then use lcd.print(F("this is a string in progmem"));' to call it.
F()` is a macro that ensures the string is in program memory.
To predefine the string (to be compatible with built-in Arduino print) I have used:
const char firmware_version_s[] PROGMEM = {"1.0.2"};
__FlashStringHelper* firmware_version = (__FlashStringHelper*) firmware_version_s;
...
Serial.println(firmware_version);
I think an alternative would be something like
size_t LCD::print_from_flash(const char *pgms)
{
const char PROGMEM *p = (const char PROGMEM *) pgms;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
which would avoid the __FlashStringHelper
cast.
This is how Print::print
prints from program memory in the Arduino library:
size_t Print::print(const __FlashStringHelper *ifsh)
{
const char PROGMEM *p = (const char PROGMEM *)ifsh;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
__FlashStringHelper*
is an empty class that allows for overloaded functions like print to differentiate a pointer to program memory from one to normal memory, as both are seen as const char*
by the compiler (see http://stackoverflow.com/questions/16597437/arduino-f-what-does-it-actually-do)
So you could overload the print
function for your LCD display so that it takes a __FlashStringHelper*
argument, lets call it LCD::print
, and then use lcd.print(F("this is a string in progmem"));' to call it.
F()` is a macro that ensures the string is in program memory.
To predefine the string (to be compatible with built-in Arduino print) I have used:
const char firmware_version_s[] PROGMEM = {"1.0.2"};
__FlashStringHelper* firmware_version = (__FlashStringHelper*) firmware_version_s;
...
Serial.println(firmware_version);
I think an alternative would be something like
size_t LCD::print_from_flash(const char *pgms)
{
const char PROGMEM *p = (const char PROGMEM *) pgms;
size_t n = 0;
while (1) {
unsigned char c = pgm_read_byte(p++);
if (c == 0) break;
n += write(c);
}
return n;
}
which would avoid the __FlashStringHelper
cast.