Time.h compiling error

I’ve found a few instances of this already on the forums by searching, but none are the same as what I’m seeing.

I won’t post my code because I’m just trying to output the time from the sample sketch that comes with the library. The Time library folder is in the library folder, where it belongs, I even tried copying the .cpp and .h files to the root of the the library folder as that was suggested in another thread, but to no avail. Basically any sketch with #include <Time.h> throws errors when I compile. Here are those errors:

In file included from /home/lappy/sketchbook/libraries/Time/DateStrings.cpp:10:0:
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:18:18: error: variable ‘monthStr1’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr1[] PROGMEM = "January";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:19:18: error: variable ‘monthStr2’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr2[] PROGMEM = "February";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:20:18: error: variable ‘monthStr3’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr3[] PROGMEM = "March";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:21:18: error: variable ‘monthStr4’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr4[] PROGMEM = "April";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:22:18: error: variable ‘monthStr5’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr5[] PROGMEM = "May";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:23:18: error: variable ‘monthStr6’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr6[] PROGMEM = "June";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:24:18: error: variable ‘monthStr7’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr7[] PROGMEM = "July";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:25:18: error: variable ‘monthStr8’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr8[] PROGMEM = "August";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:26:18: error: variable ‘monthStr9’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr9[] PROGMEM = "September";
                  ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:27:19: error: variable ‘monthStr10’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr10[] PROGMEM = "October";
                   ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:28:19: error: variable ‘monthStr11’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr11[] PROGMEM = "November";
                   ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:29:19: error: variable ‘monthStr12’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthStr12[] PROGMEM = "December";
                   ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:31:22: error: variable ‘monthNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 PGM_P monthNames_P[] PROGMEM = 
                      ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:37:26: error: variable ‘monthShortNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char monthShortNames_P[] PROGMEM = "ErrJanFebMarAprMayJunJulAugSepOctNovDec";
                          ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:39:16: error: variable ‘dayStr0’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr0[] PROGMEM = "Err";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:40:16: error: variable ‘dayStr1’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr1[] PROGMEM = "Sunday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:41:16: error: variable ‘dayStr2’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr2[] PROGMEM = "Monday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:42:16: error: variable ‘dayStr3’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr3[] PROGMEM = "Tuesday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:43:16: error: variable ‘dayStr4’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr4[] PROGMEM = "Wednesday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:44:16: error: variable ‘dayStr5’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr5[] PROGMEM = "Thursday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:45:16: error: variable ‘dayStr6’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr6[] PROGMEM = "Friday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:46:16: error: variable ‘dayStr7’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayStr7[] PROGMEM = "Saturday";
                ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:48:20: error: variable ‘dayNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 PGM_P dayNames_P[] PROGMEM = { dayStr0,dayStr1,dayStr2,dayStr3,dayStr4,dayStr5,dayStr6,dayStr7};
                    ^
/home/lappy/sketchbook/libraries/Time/DateStrings.cpp:49:24: error: variable ‘dayShortNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 char dayShortNames_P[] PROGMEM = "ErrSunMonTueWedThrFriSat";

As the errors say “variable needs to be const” I tried changing all the char lines in the .cpp file to const. Didn’t work. I’m hoping this is something really easy, and I’m only missing it because it’s 11pm and I’ve had a few bourbons. Thanks in advance.

/yes, my laptop’s name is lappy.

I won't post my code because I'm just trying to output the time from the sample sketch that comes with the library

I don't think that is a good reason not to post the code and a link to where you got the library.

I got the Time.h from here:
http://playground.arduino.cc/Code/Time

On that page there are two links. One takes you to the external page with Time.h, TimeAlarms.h and DS1307RTC.h (all as individual zip files). The other is a link to a single zip file that contains all three of those. I’ve tried both. I get the same errors with both.

Any new sketch I create with #include <Time.h> spits out those errors, even if it’s a blank sketch with only that line. However, for the sake of completeness, here is the full code of my “test” project, straight from the web.

#include <Time.h>


void setup()
{
  Serial.begin(9600);
  setTime(12,0,0,1,1,11); // set time to noon Jan 1 2011
}

void loop()
{
  digitalClockDisplay();
  delay(1000);
}

void digitalClockDisplay(){
  // digital clock display of the time
  Serial.print(hour());
  printDigits(minute());
  printDigits(second());
  Serial.print(" ");
  Serial.print(day());
  Serial.print(" ");
  Serial.print(month());
  Serial.print(" ");
  Serial.print(year());
  Serial.println();
}

void printDigits(int digits){
  // utility function for clock display: prints preceding colon and leading 0
  Serial.print(":");
  if(digits < 10)
    Serial.print('0');
  Serial.print(digits);
}

However, for the sake of completeness, here is the full code of my “test” project, straight from the web.

For the sake of completeness, I compiled your code using 1.0.5 for the Arduino Uno. Here are the error messages I get:

Binary sketch size: 4,390 bytes (of a 32,256 byte maximum)

Now, perhaps you could strive for completeness.

Newer compiler versions require PROGMEM declarations to be constant. Which one do you use, 1.5.7?

In front of all the lines in the errors just add 'const'.

The just released 1.5.7 says:

Upgraded AVR toolchain: gcc 4.8.1, avr-libc 1.8.0

So you definitely need const, as will every other usage of non const PROGMEM ( pretty much all PROGMEM code written over the last 9 years ).

PaulS:
For the sake of completeness, I compiled your code using 1.0.5 for the Arduino Uno

Exactly the same as I’m using. But it isn’t compiling.

pYro_65:
Newer compiler versions require PROGMEM declarations to be constant. Which one do you use, 1.5.7?

In front of all the lines in the errors just add ‘const’.

The just released 1.5.7 says:

Upgraded AVR toolchain: gcc 4.8.1, avr-libc 1.8.0

So you definitely need const, as will every other usage of non const PROGMEM ( pretty much all PROGMEM code written over the last 9 years ).

Right now I’m using 1.0.5. But, after reading your post, I downloaded 1.5.7. Same compiler errors.
So I went in to the offending DateStrings.cpp file and made the month and day strings const chars. Now I get the following:

In file included from /home/lappy486/sketchbook/libraries/Time/DateStrings.cpp:11:0:
/home/lappy486/sketchbook/libraries/Time/DateStrings.cpp:41:22: error: variable ‘monthNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 PGM_P monthNames_P[] PROGMEM = 
                      ^
/home/lappy486/sketchbook/libraries/Time/DateStrings.cpp:58:20: error: variable ‘dayNames_P’ must be const in order to be put into read-only section by means of ‘__attribute__((progmem))’
 PGM_P dayNames_P[] PROGMEM = { dayStr0,dayStr1,dayStr2,dayStr3,dayStr4,dayStr5,dayStr6,dayStr7};

I’m not sure what PGM_P is, but when I changed it, I got even more errors.

Thanks for all the help so far, it’s appreciated.

I am not an expert on progmem, but don't you have to #include some other avr library to make it work ? Did you do that ?

Exactly the same as I'm using. But it isn't compiling.

In the interest of complete disclosure, I'm using Win7 64 bit. You?

Linux - Ubuntu x64

I have a Windows 7 PC that I haven't turned on in ages. I can give it a shot on that and see what happens.

Download and use the Arduino tarball. Or edit the source to comply with the requirements of whatever version of the compiler Ubuntu furnished. The Ubuntu repository install and the Arduino tarball will coexist.

Something must be different on the Windows vs Linux IDE 1.5.7 I get this error as well on linux using the 32bit linux IDE 1.5.7 tarball from: http://arduino.cc/en/Main/Software That 1.5.7 tar ball comes with gcc 4.8.1 and it appears to not like it when an array of progmem const character pointers is not const itself. So I had to change the declarations in DateStrings.cpp to get it to compile with gcc 4.8.1 I had to change these:

PGM_P monthNames_P[] PROGMEM = 

PGM_P  dayNames_P[] PROGMEM =

to theses:

PGM_P const monthNames_P[] PROGMEM =

PGM_P const dayNames_P[] PROGMEM =

and then it works on both 4.8.1 and pre 4.8.1 (IDE 1.5.7 and pre IDE 1.5.7)

I'm surprised it works on the Windows 1.5.7 release. Did the windows version of 1.5.7 come with gcc 4.8.1 ??? Can you verify the version by running:

 avr-gcc --version

on the avr-gcc down in {installdir}/hardware/tools/avr/bin

BTW, I'm using the Time library from here:

https://www.pjrc.com/teensy/td_libs_Time.html

and you can see the issue if you compile the included TimeSerial example. --- bill

bperrybap: I'm surprised it works on the Windows 1.5.7 release. Did the windows version of 1.5.7 come with gcc 4.8.1 ??? Can you verify the version by running:

 avr-gcc --version

on the avr-gcc down in {installdir}/hardware/tools/avr/bin

Can't on mine, need Cygwin, but the exe is a dead giveaway "avr-gcc-4.8.1.exe". Once I have cygwin setup I can post what it reports. Anyway I was using C++11 last night in the IDE. Your sketch can now look like this ( with C++11 enabled ):

auto setup() -> void {

}

auto loop() -> void {

}

michinyon: I am not an expert on progmem, but don't you have to #include some other avr library to make it work ? Did you do that ?

I recall having to do this once upon a time, I think this changed when 1.0 was released, the include is now included with Arduino.h

pYro_65: Can't on mine, need Cygwin, but the exe is a dead giveaway "avr-gcc-4.8.1.exe". Once I have cygwin setup I can post what it reports. Anyway I was using C++11 last night in the IDE.

Cygwin comes with the Windows package. The needed dlls are up in the root of the install directory. You will have to run the command from there. i.e. cd to the install directory then run the command: hardware\tools\avr\bin\avr-gcc --version

(It works. I just did it on my XP vm and it reports 4.8.1)

The bigger issue is that I just installed the windows 1.5.7 from the zip image on XP and it has exactly the same issue with the Time library as it does on linux.

I downloaded the Windows 1.5.7 IDE from this page: http://arduino.cc/en/Main/Software Under the paragraph titled: Arduino 1.5.7 BETA (with support for Arduino Yún and Arduino Due boards) From the line that says: Windows: ZIP file (for non-administrator install) Which resolves to this link/image: http://downloads.arduino.cc/arduino-1.5.7-windows.zip

And the Time library I'm using is from here. https://www.pjrc.com/teensy/td_libs_Time.html

So for me, this issue is completely reproducible on Windows XP and on Linux and the changes I described earlier fix the issue.

What Windows image and Time library are you using?

--- bill

The bigger issue is that I just installed the windows 1.5.7 from the zip image on XP and it has exactly the same issue with the Time library as it does on linux.

That is the one I have. Didn't bother with cygwin cos I already know its 4.8.1. C++11 features just cause errors in 1.5.6. I have been avidly following the progress on github and google groups.

As I mentioned before, its the compiler requiring it, not a bug of the OS. The decision was made to make flash elements constant. Which is what I recommended the OP change in code too.

pYro_65: As I mentioned before, its the compiler requiring it, not a bug of the OS. The decision was made to make flash elements constant. Which is what I recommended the OP change in code too.

I was not thing it was an OS issue but rather that it was an issue of the 1.5.7 IDE release for a particular OS. For some reason I was thinking that someone had said that the Time library examples were compiling for them on Win7, but after going back and re-reading the thread I see that this was totally in my imagination :blush:

pYro_65: Newer compiler versions require PROGMEM declarations to be constant. Which one do you use, 1.5.7?

In front of all the lines in the errors just add 'const'.

But isn't always that simple. In the case of a progmem array containing an array of const progmem pointers, like what is being used in the Timer library DateStrings.cpp not only do the pointers in the array have to be const but the array itself has to be const. The PGM_P macro takes of adding the const for the pointers but an additional const has to be added to the declaration to make the array itself const.

Luckily once the declaration is corrected, it works for the new and the older compilers.

I'll go send a message to Paul and try to get the Time library on his site updated so others don't have to deal with this for the Time library.

The sad part is that the examples on the Arduino web pages for how to use AVR PROGMEM have been broken/wrong for years. Several bug reports have been filed but the corrections/updates have not yet been done.

--- bill

PGM_P const monthNames_P[] PROGMEM =

PGM_P const dayNames_P[] PROGMEM =

I did that. It got rid of some of the errors. So, I checked to see if it would compile on my Windows box. Worked with no errors. So after spending far far far too much time trying to troubleshoot on my linux machine, I just compiled and uploaded the code from the Windows box, and it works.

Thanks for all the help. I'll get back to trying to fix the issue on my Linux machine whenever I start my next project.

Something odd is going on. Maybe the 64 bit linux release is different from the 32 bit? I'm not using the 64 bit Linux (I don't see the value of 64bit, given linux supports PAE mode)

--- bill

Hi

I had same issue and I solved it in this way. My code was working in Windows, once I switched to my Ubuntu and using IDE installed from Software Center, it did not worked. I downlaoded the 64bit version of IDE from Arduino website. Using this toterial installed the IDE: https://www.youtube.com/watch?v=0ZF_XRZZt_c

Everything worked. Then I replaced the installed version in /usr/share/arduino folder content with new downloaded from arduino website and everything works fine

Just in case it’s useful, here’s the complete corrected DateStrings.cpp. Tested under 1.5.7.

/* DateStrings.cpp
 * Definitions for date strings for use with the Time library
 *
 * No memory is consumed in the sketch if your code does not call any of the string methods
 * You can change the text of the strings, make sure the short strings are each exactly 3 characters 
 * the long strings can be any length up to the constant dt_MAX_STRING_LEN defined in Time.h
 * 
 */
 
#include <avr/pgmspace.h> 
#include "Time.h"
 
// the short strings for each day or month must be exactly dt_SHORT_STR_LEN
#define dt_SHORT_STR_LEN  3 // the length of short strings

static char buffer[dt_MAX_STRING_LEN+1];  // must be big enough for longest string and the terminating null

const char monthStr1[] PROGMEM = "January";
const char monthStr2[] PROGMEM = "February";
const char monthStr3[] PROGMEM = "March";
const char monthStr4[] PROGMEM = "April";
const char monthStr5[] PROGMEM = "May";
const char monthStr6[] PROGMEM = "June";
const char monthStr7[] PROGMEM = "July";
const char monthStr8[] PROGMEM = "August";
const char monthStr9[] PROGMEM = "September";
const char monthStr10[] PROGMEM = "October";
const char monthStr11[] PROGMEM = "November";
const char monthStr12[] PROGMEM = "December";

PGM_P const monthNames_P[] PROGMEM =
{
    "",monthStr1,monthStr2,monthStr3,monthStr4,monthStr5,monthStr6,
	monthStr7,monthStr8,monthStr9,monthStr10,monthStr11,monthStr12
};

const char monthShortNames_P[] PROGMEM = "ErrJanFebMarAprMayJunJulAugSepOctNovDec";

const char dayStr0[] PROGMEM = "Err";
const char dayStr1[] PROGMEM = "Sunday";
const char dayStr2[] PROGMEM = "Monday";
const char dayStr3[] PROGMEM = "Tuesday";
const char dayStr4[] PROGMEM = "Wednesday";
const char dayStr5[] PROGMEM = "Thursday";
const char dayStr6[] PROGMEM = "Friday";
const char dayStr7[] PROGMEM = "Saturday";

PGM_P const dayNames_P[] PROGMEM = { dayStr0,dayStr1,dayStr2,dayStr3,dayStr4,dayStr5,dayStr6,dayStr7};
const char dayShortNames_P[] PROGMEM = "ErrSunMonTueWedThrFriSat";

/* functions to return date strings */

char* monthStr(uint8_t month)
{
    strcpy_P(buffer, (PGM_P)pgm_read_word(&(monthNames_P[month])));
	return buffer;
}

char* monthShortStr(uint8_t month)
{
   for (int i=0; i < dt_SHORT_STR_LEN; i++)      
      buffer[i] = pgm_read_byte(&(monthShortNames_P[i+ (month*dt_SHORT_STR_LEN)]));  
   buffer[dt_SHORT_STR_LEN] = 0;
   return buffer;
}

char* dayStr(uint8_t day) 
{
   strcpy_P(buffer, (PGM_P)pgm_read_word(&(dayNames_P[day])));
   return buffer;
}

char* dayShortStr(uint8_t day) 
{
   uint8_t index = day*dt_SHORT_STR_LEN;
   for (int i=0; i < dt_SHORT_STR_LEN; i++)      
      buffer[i] = pgm_read_byte(&(dayShortNames_P[index + i]));  
   buffer[dt_SHORT_STR_LEN] = 0; 
   return buffer;
}

go with adding the const in front of every char and re run the program. I had to do it a couple times until fixed :)