Сейчас на форуме: UniSoft, bartolomeo (+6 невидимых)

 eXeL@B —› Программирование —› нестандартное поведение препроцессора msvc
Посл.ответ Сообщение

Ранг: 36.1 (посетитель), 11thx
Активность: 0.020
Статус: Участник

Создано: 23 января 2011 14:40
· Личное сообщение · #1

дано:
#define __drv_out(annotes) __post __$drv_group(##__drv_nop(annotes))
макрос используется например из етого места
Code:
  1. SDK v7.0A winnt.h
  2. typedef
  3. __drv_sameIRQL
  4. <b>__drv_functionClass(EXCEPTION_ROUTINE)</b>
  5. EXCEPTION_DISPOSITION
  6. NTAPI
  7. EXCEPTION_ROUTINE (
  8.     __inout struct _EXCEPTION_RECORD *ExceptionRecord,
  9.     __in PVOID EstablisherFrame,
  10.     __inout struct _CONTEXT *ContextRecord,
  11.     __in PVOID DispatcherContext
  12.     );

вопрос:
что сделает первее pp msvc - раскроет макрос __drv_nop или выполнит склеивание?




Ранг: 199.6 (ветеран), 12thx
Активность: 0.10
Статус: Участник
www.uinc.ru

Создано: 26 января 2011 05:22
· Личное сообщение · #2

На сколько мне известно, препроцессор С так до конца и не стандартизировали.
По идее, на мой взгляд (и, похоже, наивным ожиданиям),оно должно тупо подставляться согласно скобкам, т.е. первым должна идти склейка.
С другой стороны, я никогда не был действительным разработчиком, но уже повидал 100500 багов в самых промышленных компиляторах. Компилеры тоже люди пишут, как не крути.



Ранг: 36.1 (посетитель), 11thx
Активность: 0.020
Статус: Участник

Создано: 26 января 2011 07:13 · Поправил: Jonny
· Личное сообщение · #3

Спасибо за ответ. Со стандартизацией там в порядке.
например и в 9899:1990(5.1.1.2), и в 9899:1999(5.1.1.2) трансляция исходного кода состоит из 8 шагов, где первые 6 касаются исключительно препроцессора. На 7 шаге токены препроцессора превращаются в токены лексического анализатора.
А то что нас касается, выполняется на шаге 4, где происходит раскрытие макросов и выполнение директив препроцессора. На входе который принимает исключительно токены препроцессора(pp-tokens). Определения pp-tokens указаны в главе 6.4
Code:
  1. preprocessing-token:
  2. header-name
  3. identifier
  4. pp-number
  5. character-constant
  6. string-literal
  7. punctuator
  8. each non-white-space character that cannot be one of the above


Скорее всего, у pp msvc после склейки ошибка в алгоритме последующих действий.
во - первых, по стандарту полученная строка должна являться pp-token`ом. В реализации строка заново сканируется(проходит шаги трансляции от 1 до 3).
если на выходе после этого не формируется pp-token или формируется больше 1 токена - ошибка.

Вообщем, я прихожу к выводу, что pp msvc не проверяет количество полученных токенов после сканирования склеенной строки.
Практически, данная ошибка встречается в файле windows psdk drvspecs.h



Ранг: 36.1 (посетитель), 11thx
Активность: 0.020
Статус: Участник

Создано: 26 января 2011 07:35 · Поправил: Jonny
· Личное сообщение · #4

Также есть следующий общеизвестный баг msvc pp.
psdk : WTypes.h
Code:
  1. #if !__STDC__ && (_MSC_VER <= 1000)
  2.  
  3. /* For backward compatibility */
  4. typedef VARIANT_BOOL _VARIANT_BOOL;
  5.  
  6. #else
  7. /* ANSI C/C++ reserve bool as keyword */
  8. #define _VARIANT_BOOL    /##/
  9. #endif

если используется ms компилятор, у которого определено ключевое слово bool, то после макроподстановки _VARIANT_BOOL bool; (Propidl.h, OAidl.h) получается комментарий.

Но если смотреть с точки зрения стандарта, то после склейки мы должны получить pp-token, но `//`
в их число не входит.




Ранг: 199.6 (ветеран), 12thx
Активность: 0.10
Статус: Участник
www.uinc.ru

Создано: 28 января 2011 05:13 · Поправил: DrGolova
· Личное сообщение · #5

Размер типа "bool" так никто и не удосужился стандартизировать. Причем в MS компилере сей тип ведет себя по разному в з0висимости от окружения. Если это С++, то bool - это 1 байт, а если это ANSI-C - то это int (бага/фича компилера? в оригинальном C вобще нет типа bool, хотя все они понимают его без всяких редефайнов)
посему все, кто пробуют использовать данный тип в публичных интерфейсах (а уж тем более в структурах), подвергаются анальной каре, и увольняются нахуй без права голоса.
Это я типа про всякие титан-энжины, на сорцы которых без слез невозможно смотреть.



Ранг: 33.4 (посетитель), 24thx
Активность: 0.020
Статус: Участник

Создано: 28 января 2011 15:57 · Поправил: redlord
· Личное сообщение · #6

DrGolova пишет:
бага/фича компилера? в оригинальном C вобще нет типа bool, хотя все они понимают его без всяких редефайнов


ISO/IEC 9899:1999:

1 The header <stdbool.h> defines four macros.
2 The macro
bool
expands to _Bool.

An object declared as type _Bool is large enough to store the values 0 and 1.
The type
_Bool and the unsigned integer types that correspond to the standard signed integer
types are the standard unsigned integer types.

а с размером - плохо



Ранг: 251.3 (наставник), 81thx
Активность: 0.140.11
Статус: Участник

Создано: 28 января 2011 16:07
· Личное сообщение · #7

С вашим подходом в стандарте вообще всё плохо, т.к. размер явно не указан ни для одного из базовых типов, есть только ряд ограничений.



Ранг: 33.4 (посетитель), 24thx
Активность: 0.020
Статус: Участник

Создано: 28 января 2011 16:13
· Личное сообщение · #8

cppasm пишет:
размер явно не указан ни для одного из базовых типов


An object declared as type signed char occupies the same amount of storage as a
‘‘plain’’ char object. A ‘‘plain’’ int object has the natural size suggested by the
architecture of the execution environment (large enough to contain any value in the range
INT_MIN to INT_MAX as defined in the header <limits.h>).

сложно сказать


 eXeL@B —› Программирование —› нестандартное поведение препроцессора msvc
:: Ваш ответ
Жирный  Курсив  Подчеркнутый  Перечеркнутый  {mpf5}  Код  Вставить ссылку 
:s1: :s2: :s3: :s4: :s5: :s6: :s7: :s8: :s9: :s10: :s11: :s12: :s13: :s14: :s15: :s16:


Максимальный размер аттача: 500KB.
Ваш логин: german1505 » Выход » ЛС
   Для печати Для печати