Почему gcc4 предупреждают и как этого избежать - PullRequest
2 голосов
/ 14 апреля 2010

У меня есть функция, объявленная как:

void    event_add_card (EventAddr addr, EventType type, unsigned char card);

и союз

typedef union EventData
{
    float           money;      /**< money info */
    unsigned char   card;       /**< new card */
}
EventData;

Когда я компилирую следующий код:

EventData data = {};

event_add_card (0,0, data.card);

с включенным предупреждением -Wconversion Я получаю следующее предупреждение:

player-stud.c|71| warning: passing argument 3 of 'event_add_card' with different width due to prototype

Почему gcc4 неудачный и как это исправить ???

Ответы [ 2 ]

3 голосов
/ 15 апреля 2010

В версиях gcc до 4.3, -Wconversion выдает предупреждение, когда поведение может отличаться в зависимости от того, находится ли прототип в области действия. В приведенном вами примере аргумент 3 (data.card) имеет значение unsigned char; если прототип для event_add_card() находится в области видимости, он будет передан как unsigned char, но если прототип не находится в области видимости, он будет передан как int из-за целочисленных правил продвижения C - отсюда и предупреждение.

Это не очень полезно, за исключением процесса преобразования старого кода в стиле K & R для использования прототипов. Таким образом, если вы используете более старую версию gcc, этот параметр обычно не используется для включения.

Начиная с gcc 4.3, поведение изменилось: теперь он предупреждает о любом неявном преобразовании, которое может изменить значение (скажем, между целыми числами со знаком и без знака или целыми числами и числами с плавающей запятой). Это значительно полезнее. (Тем не менее, предыдущая функциональность не исчезла: она все еще доступна, но переименована в -Wtraditional-conversion.)

(подробнее на http://gcc.gnu.org/wiki/NewWconversion.)

1 голос
/ 14 апреля 2010

Проблема в том, что вы используете -Wconversion

В вашем коде нет ничего плохого, и вы ничего не можете сделать, чтобы -Wconversion не выдавал это предупреждение.

Пример:

void someFunction(unsigned char foo);
...
unsigned char bar = 'f';
someFunction(bar);

Это приведет к той же ошибке, если вы скомпилируете и используете -Wconversion

-Wconversion предназначен для выявления проблем при конвертации между K & R и ISO C, которые вы не делаете.

...