2012-02-05 11 views
4

以下のコードをIdeone.comでコンパイルし、次の警告が表示されました。属性warn_unused_resultで宣言[-Wunused-result]

rtctimer.c: In function 'rtctimer_next_tick': 
rtctimer.c:87.7: warning: ignoring return value of 'read', 
       declared with attribute warn_unused_result [-Wunused-result] 
#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <errno.h> 
#include <unistd.h> 
#include <poll.h> 
#include <sched.h> 
#include <fcntl.h> 
#include <math.h> 
#include <sys/ioctl.h> 
#include <linux/rtc.h> 
#include "rtctimer.h" 

struct rtctimer_s 
{ 
    int rtc_fd; 
    int current_hz; 
    int rtc_running; 
    int verbose; 
    int usecs; 
}; 

rtctimer_t *rtctimer_new(int verbose) 
{ 
    rtctimer_t *rtctimer = malloc(sizeof(rtctimer_t)); 
    if(!rtctimer) return 0; 

    rtctimer->verbose = verbose; 
    if(((rtctimer->rtc_fd = open("/dev/rtc", O_RDONLY)) < 0)) { 
     if(rtctimer->verbose) { 
      fprintf(stderr, "rtctimer: Cannot open /dev/rtc: %s\n", 
        strerror(errno)); 
     } 
     if((rtctimer->rtc_fd = open("/dev/misc/rtc", O_RDONLY)) < 0) { 
      if(rtctimer->verbose) { 
       fprintf(stderr, "rtctimer: Cannot open /dev/misc/rtc: %s\n", 
         strerror(errno)); 
      } 
      free(rtctimer); 
      return 0; 
     } 
    } 

    if(fcntl(rtctimer->rtc_fd, F_SETOWN, getpid()) < 0) { 
     if(rtctimer->verbose) { 
      fprintf(stderr, "rtctimer: Cannot set ownership of " 
          "/dev/rtc: %s\n", strerror(errno)); 
     } 
     close(rtctimer->rtc_fd); 
     free(rtctimer); 
     return 0; 
    } 

    rtctimer->rtc_running = 0; 
    rtctimer->current_hz = 0; 
    rtctimer->usecs = 0; 
    return rtctimer; 
} 

void rtctimer_delete(rtctimer_t *rtctimer) 
{ 
    rtctimer_stop_clock(rtctimer); 
    close(rtctimer->rtc_fd); 
    free(rtctimer); 
} 

int rtctimer_next_tick(rtctimer_t *rtctimer) 
{ 
    unsigned long rtc_data; 
    struct pollfd pfd; 
    pfd.fd = rtctimer->rtc_fd; 
    pfd.events = POLLIN | POLLERR; 

again: 
    if(poll(&pfd, 1, 100000) < 0) { 
     if(errno == EINTR) { 
      goto again; 
     } 

     if(rtctimer->verbose) { 
      fprintf(stderr, "rtctimer: poll call failed: %s\n", 
        strerror(errno)); 
     } 
     return 0; 
    } 

    read(rtctimer->rtc_fd, &rtc_data, sizeof(rtc_data)); 
    return 1; 
} 

int rtctimer_set_interval(rtctimer_t *rtctimer, int hz) 
{ 
    int restart; 

    if(hz == rtctimer->current_hz) { 
     return 1; 
    } 

    restart = rtctimer_stop_clock(rtctimer); 

    if(ioctl(rtctimer->rtc_fd, RTC_IRQP_SET, hz) < 0) { 
     if(rtctimer->verbose) { 
      fprintf(stderr, "rtctimer: Cannot set periodic interval: %s\n", 
        strerror(errno)); 
     } 
     return 0; 
    } 

    rtctimer->current_hz = hz; 
    rtctimer->usecs = (int) (((1000.0 * 1000.0)/hz) + 0.5); 

    if(restart) { 
     rtctimer_start_clock(rtctimer); 
    } 

    return 1; 
} 

int rtctimer_start_clock(rtctimer_t *rtctimer) 
{ 
    if(!rtctimer->rtc_running) { 
     if(ioctl(rtctimer->rtc_fd, RTC_PIE_ON, 0) < 0) { 
      if(rtctimer->verbose) { 
       fprintf(stderr, "rtctimer: Cannot start periodic " 
         "interrupts: %s\n", strerror(errno)); 
      } 
      return 0; 
     } 
     rtctimer->rtc_running = 1; 
    } 
    return rtctimer->rtc_running; 
} 

int rtctimer_stop_clock(rtctimer_t *rtctimer) 
{ 
    int was_running = rtctimer->rtc_running; 

    if(rtctimer->rtc_running) { 
     if(ioctl(rtctimer->rtc_fd, RTC_PIE_OFF, 0) < 0) { 
      if(rtctimer->verbose) { 
       fprintf(stderr, "rtctimer: Cannot stop periodic " 
         "interrupts: %s\n", strerror(errno)); 
      } 
      return rtctimer->rtc_running; 
     } 
     rtctimer->rtc_running = 0; 
    } 

    return was_running; 
} 

int rtctimer_get_resolution(rtctimer_t *rtctimer) 
{ 
    return rtctimer->current_hz; 
} 

int rtctimer_get_usecs(rtctimer_t *rtctimer) 
{ 
    return rtctimer->usecs; 
} 

int set_realtime_priority(int max) 
{ 
    struct sched_param schp; 

    memset(&schp, 0, sizeof(schp)); 
    if(max) schp.sched_priority = sched_get_priority_max(SCHED_FIFO); 
    else schp.sched_priority = sched_get_priority_max(SCHED_FIFO) - 1; 

    if(sched_setscheduler(0, SCHED_FIFO, &schp) != 0) { 
     return 0; 
    } 

    return 1; 
} 

int set_default_priority(void) 
{ 
    struct sched_param schp; 

    memset(&schp, 0, sizeof(schp)); 
    schp.sched_priority = 0; 
    if(sched_setscheduler(0, SCHED_OTHER, &schp) != 0) { 
     return 0; 
    } 

    return 1; 
} 

私が間違って何をしたのですか?

答えて

6

read()は、読み込んだバイト数を示す値を返します。警告は、コードがそれを無視していることを示しています。戻り値がread()であることを確認して、成功したことを確認してください。それ以外の場合は、rtc_dataが正しく入力されていないと仮定している可能性があります。

4

戻り値がreadであることを確認していません。これは、ただ待っているバグです。

ssize_t r = read(rtctimer->rtc_fd, &rtc_data, sizeof(rtc_data)); 
if (r == -1) { 
    // deal with failed read 
} else if (r != sizeof(rtc_data)) { 
    // you didn't read as much as you wanted to 
... 

あなたがリターンを読んで内容を確認していない場合は、チャンスは読み取りエラーが発生した場合、プログラムが予期せず失敗することが非常に高く、それはデバッグができなくなります。

通常、ライブラリ呼び出し、特にI/O呼び出しの戻り値は、通常の状況では失敗するため、チェックしてください。

1

ライン

read(rtctimer->rtc_fd, &rtc_data, sizeof(rtc_data)); 

結果、あなたはそれがどのような方法で使用していません(読み取り()の戻り値)を生成し、これはあなたに警告が表示されます。それは-Wunused-resultの目的です。

通常、read()の戻り値を無視することは非常に悪い考えです!