Компилятор: static or extern declaration without type

 
class c1
{
   c2* _C2;
};

class c2
{
   c1* _C1;
};
Выскакивает ошибка компилятора, т.к на момент определения переменной _C2 компилятор не знает про класс c2. Можно ли это как-то обойти?
 

Можно:

class c1
{
   //c2* _C2;
};

class c2
{
   c1* _C1;
};
class c3:c1
{
   c2* _C2;
};

 

Этого я и опасался. 

Хотелось бы видеть в компиляторе такую возможность как forward declaration:

class c2;

class c1
{
   c2* _C2;
};

class c2
{
   c1* _C1;
};

 

 
GarF1eld:

Этого я и опасался. 

Хотелось бы видеть в компиляторе такую возможность как forward declaration:

 

Обсуждается.
 
mql5:
Обсуждается.

До сих пор?

Вроде бы несколько месяцев назад собирались уже ввести forward declaration.
Вещь достаточно базовая в архитектуре языка, а до сих пор "обсуждается"?

Коль скоро язык уже сделан объектно-ориентированным...
С перегрузкой функций, их виртуальностью, наследованием и прочими "сложняками"...
То какой теперь смысл пытаться запретить механизм forward declaration?

Или проблема не в этом, а в сложностях реализации?

 

От forward declaration решили отказаться по соображениям безопасности и упрощения реализации.

У форвардных определений в реализации есть ряд неприятных подводных камней, особенно в межмодульном взаимодействии с возможностью подмены на кастинге типов. Грубо говоря, теоретически можно будет проводить атаки, подсовывая через ссылки фейковые классы с другими функциями (например, вместо виртуальной функции подсунуть переменную с физическим адресом) ради срыва стека или передачи прямого управления куда угодно. В существующей модели подсунуть фейковый класс нельзя из-за жесткой сигнатурной модели классов/структур/функций. Для противодействия обману конечно же можно серьезно усложнить контроль, но это не имеет практического смысла.

Преимущества форвардных определений не перевешивают важности жесткой модели безопасности.

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

 
Renat:

От forward declaration решили отказаться по соображениям безопасности и упрощения реализации.

У форвардных определений в реализации есть ряд неприятных подводных камней, особенно в межмодульном взаимодействии с возможностью подмены на кастинге типов. Грубо говоря, теоретически можно будет проводить атаки, подсовывая через ссылки фейковые классы с другими функциями (например, вместо виртуальной функции подсунуть переменную с физическим адресом) ради срыва стека или передачи прямого управления куда угодно. В существующей модели подсунуть фейковый класс нельзя из-за жесткой сигнатурной модели классов/структур/функций. Для противодействия обману конечно же можно серьезно усложнить контроль, но это не имеет практического смысла.

Преимущества форвардных определений не перевешивают важности жесткой модели безопасности.

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


Значит ли это, что проблема в этом случае заключается в отключении сигнатурного контроля в момент вызова?
Но раз язык MQL5 - свой, то что мешает его доработать и потребовать, чтобы в момент вызова типы всех параметров были полностью определены, то есть, все forward declaration для параметров в этой точке перестали быть forward (что и позволит сохранить существующий ныне контроль)?

Это немного ограничит свободу применения forward declaration, но при этом не уничтожит полностью те возможности, ради которых forward declaration и придумывался.

Без forward declaration люди будут уродовать язык, пользоваться им неестественным образом.

Кстати, возможны ли атаки, связанные с подсовыванием fake'овых классов, но основанные на наследовании и приведении к производному классу?

 

Сигнатурный контроль жесткий и никогда не отключается. Мы не хотим вводить форвардные описания, чтобы не делать исключений.

При неотключенном сигнатурном контроле атаку с подсовыванием фейковых классов провести практически нельзя (если только не подобрать очень и очень хитрую цепочку).

Кстати, форвардные описания в коде чаще появляются от лени, а не от великих замыслов.

 
Renat:

Кстати, форвардные описания в коде чаще появляются от лени, а не от великих замыслов.

Реально не хватает forward declaration

Начинаются танцы с бубном ((CChildren*)(object)).Method(), что явно снижает читабельность кода и вносит доп. риски при ошибочном переопределении типов

P.S.

  Сам по себе ООП появился как раз от лени )))

 
yu-sha:

Реально не хватает forward declaration

Начинаются танцы с бубном ((CChildren*)(object)).Method(), что явно снижает читабельность кода и вносит доп. риски при ошибочном переопределении типов

P.S.

  Сам по себе ООП появился как раз от лени )))

Пожалуйста, потерпите немного, forward declaration вводится.
 
mql5:
Пожалуйста, потерпите немного, forward declaration вводится.
Отлично! К следующему билду успеете или придется еще подождать?
Причина обращения: