[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[avr-gcc-list] Possible bug in avr-gcc 4.3.2?

From: Zoran Rilak
Subject: [avr-gcc-list] Possible bug in avr-gcc 4.3.2?
Date: Sat, 23 May 2009 12:09:07 -0400

Hi all,

I am fairly new to the world of uC programming.  I've been using avr-gcc
4.3.2 with ATmega168 and stumbled upon something rather peculiar.
Please consider the following code snippet (the crux of the matter is in
the last block of code):

#include "lcd.c"

// Day-of-week names
char dow0[] PROGMEM = "Ned";
char dow1[] PROGMEM = "Pon";
char dow2[] PROGMEM = "Uto";
char dow3[] PROGMEM = "Str";
char dow4[] PROGMEM = "Stv";
char dow5[] PROGMEM = "Pia";
char dow6[] PROGMEM = "Sob";

// Days of week in an array.
PGM_P dow[] PROGMEM = { dow0, dow1, dow2, dow3, dow4, dow5, dow6 };

// Time struct from BQ3285
typedef struct {
  // time values
  uint8_t sec;      // seconds (0..59)
  uint8_t min;      // minutes (0..59)
  uint8_t hour;     // hours (0..11, or 0..23 if BQ_HF is set in BQ_REG_B)

  // calendar values
  uint8_t dow;      // day of week (1..7, 1 = Sunday)
  uint8_t day;      // day of month (1..31)
  uint8_t month;    // month (1..12)
  uint8_t year;     // year (0..99)
} bq_time_t;

// current time
volatile bq_time_t now;

// ...

/* called from interrupt handler */
  // write the day of week
  uint8_t k = 1;
  uint8_t l = now.dow;
  lcd_write_int16(k); lcd_putc(',');        // outputs: 1
  lcd_write_int16(l); lcd_putc(',');        // outputs: 1 (now.dow is inited to 
1 outside)
  lcd_write_int16(k==l); lcd_putc(',');     // outputs: 1 (as it should)
  lcd_write_int16(dow[k]); lcd_putc(',');   // outputs: address in dow[1] in 
pgm. space
  lcd_write_int16(dow[l]); lcd_putc(',');   // outputs: 0  (?!)

Whenever I try to index the dow[] array using a value from now.dow, I
get zero.  This is all the more interesting, because the following
block, albeit unreasonable, works just as advertised:

switch (now.dow-1) {
  case 0: lcd_write_string_P(dow[0]); break;
  case 1: lcd_write_string_P(dow[1]); break;
  case 2: lcd_write_string_P(dow[2]); break;
  case 3: lcd_write_string_P(dow[3]); break;
  case 4: lcd_write_string_P(dow[4]); break;
  case 5: lcd_write_string_P(dow[5]); break;
  case 6: lcd_write_string_P(dow[6]); break;
  default: lcd_write_string_P(PSTR("???")); break;
// But this doesn't: lcd_write_string_P(dow[now.dow-1]);

Any help would be more than appreciated.


reply via email to

[Prev in Thread] Current Thread [Next in Thread]