2010-11-04 21 views
10

Hãy xem xét hai macro sau:Đàn áp "ISO C99 đòi hỏi đối số còn lại sẽ được sử dụng"

#define PNORM(v, s, ...) { \ 
    if(VERBOSITY_CHECK(v)) { \ 
    if((errno = pthread_mutex_lock(&server.output_mutex))) { \ 
     PERROR_LOCKFREE(normal, "\tpthread_mutex_lock failed on output_mutex.\r\n") ; \ 
    } \ 
    fprintf(stdout, s, ## __VA_ARGS__) ; \ 
    fflush(stdout) ; \ 
    if((errno = pthread_mutex_unlock(&server.output_mutex))) { \ 
     PERROR_LOCKFREE(normal, "\tpthread_mutex_unlock failed on output_mutex.\r\n") ; \ 
    } \ 
    } \ 
} 

#define PERROR_LOCKFREE(v, s, ...) { \ 
    if(VERBOSITY_CHECK(v)) { \ 
    PERRNO ;\ 
    fprintf(stderr, s, ## __VA_ARGS__) ; \ 
    fflush(stderr) ; \ 
    } \ 
} 

Bây giờ hãy xem xét một ví dụ về sử dụng sau đây:

PNORM(verbose, "\tSomeText [%d] More [%p]\r\n", 0, ptr) ; 

Khi biên soạn với các tùy chọn -pedantic và -std = c99 Tôi gặp lỗi này nhiều lần:

mycode.c:410:112: warning: ISO C99 requires rest arguments to be used 

Người khiếu nại có quyền phàn nàn về điều này nhưng có cách nào tôi có thể ngăn chặn cảnh báo này vì tôi không quan tâm đến nó?

Trả lời

9

Kết hợp đối số s với đối số variadic để bạn luôn có ít nhất một đối số như một phần của dấu ba chấm. Điều này cũng cho phép bạn tránh sử dụng phần mở rộng ,## của GCC:

#define PNORM(v, ...) { \ 
    if(VERBOSITY_CHECK(v)) { \ 
    if((errno = pthread_mutex_lock(&server.output_mutex))) { \ 
     PERROR_LOCKFREE(normal, "\tpthread_mutex_lock failed on output_mutex.\r\n") ; \ 
    } \ 
    fprintf(stdout, __VA_ARGS__) ; \ 
    fflush(stdout) ; \ 
    if((errno = pthread_mutex_unlock(&server.output_mutex))) { \ 
     PERROR_LOCKFREE(normal, "\tpthread_mutex_unlock failed on output_mutex.\r\n") ; \ 
    } \ 
    } \ 
} 

#define PERROR_LOCKFREE(v, ...) { \ 
    if(VERBOSITY_CHECK(v)) { \ 
    PERRNO ;\ 
    fprintf(stderr, __VA_ARGS__) ; \ 
    fflush(stderr) ; \ 
    } \ 
} 
1

Bạn có thể disable cảnh báo ngay xung quanh các macro của mình hoặc tắt hoàn toàn cảnh báo cụ thể với pragma Warnings trong GCC. Bạn cũng có thể không sử dụng -pedantic, vì nó là, tốt, pedantic.

+2

Thận trọng là một tính năng rất tốt để sử dụng để bắt lỗi nhỏ trong mã của bạn. Cảnh báo không phải là một cái gì đó để được bỏ qua. –

+0

@ David: Chắc chắn, nhưng câu hỏi là "làm cách nào để bỏ qua cảnh báo này". '-pedantic' thực sự chỉ hữu ích khi bắt các phụ thuộc gcc. '-Wall' sẽ bắt được gần như tất cả các lỗi có thể bị phát hiện bởi các cảnh báo. – nmichaels

+0

Câu trả lời này thực sự không giúp chỉ vô hiệu hóa cảnh báo đó. Theo truyền thống, ít nhất phiên bản gcc của tôi KHÔNG hỗ trợ 'pragma Warnings'. –

2

Mã thông báo ## kết hợp với __VA_ARGS__ là một tiện ích mở rộng gcc không thuộc ISO C99. Đó là lý do tại sao bạn nhận được cảnh báo.

1

Phụ thuộc vào những gì đơn giản cho bạn. Trong P99 có P99 conditionals mà sẽ cho phép bạn làm điều gì đó như

#define USER_MACRO(...) P99_IF_DEC_LE(P99_NARG(__VA_ARGS__),2)(USER_MACRO2(__VA_ARGS__))(USER_MACRO3(__VA_ARGS__)) 

Vì vậy, với điều đó không có nhu cầu sử dụng phần mở rộng ,## của gcc.

+0

Đây phải là câu trả lời được chấp nhận. Xa thanh lịch hơn. – Barry

Các vấn đề liên quan