Просмотр сообщений
Страниц: [1] 2 3 ... 15
1  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Октября 20, 2018, 08:54:37 am
Цитировать
метод должен принадлежать классу (не иметь дополнительных каких либо смещений при ссылке на метод)

Про смещения - это уже проблема компилятора, как он будет искать этот метод. Если я вставил дверь в дом, отныне ручка двери принадлежит дому точно так же, как и двери. Это уже пусть сам компилятор ищет, где там этот метод у кого лежит. И жаль, что он такого не умеет.

Цитировать
Но нет никакой возможности вызывать непосредственно этот метод без указания типа (смещения) конкретного базового класса.

Правильно. В данном случае есть неопределённость и требуется указание, чей именно метод мы вызываем.

Цитировать
Компилятор не сможет различить полную сигнатуру (а именно именную сигнатуру) к каким методам будет применен вызов (на уровне  CErrors::ChangeState - это неизвестно). Он затрудняется гарантировать точные ваши намерения и принимает очевидное решение - сгенерировать ошибку компиляции. Гарантировано он может обеспечить работу только для собственных методов принадлежащих к CErrors (в примере это метод SetError)

Но опять-таки, это проблема компилятора. Во время выполнения он умеет работать с таблицами виртуальных функций, то есть, ничто ему не мешает так же выяснять и куда что перенаправляется.

Цитировать
И наличие конструктора - тут не причем.

Нет-нет, тут другой вопрос был. Итак, у нас есть два модуля.
В первом в *.h объявлен класс CErrors и в *.cpp написано так:

//глобальная переменная
char name[]="123";
//конструктор
CErrors::CErrors(void)
{
 printf("%s\r\n",name);
}

Во втором в *.h объявлен класс CMain и в *.cpp написано так:
//глобальная переменная
CMain cMain;
//конструктор
CMain::CMain(void)
{
 printf("CMain!\r\n");
 CErrors *cErrors_Ptr=new CErrors();
 delete(cErrors_Ptr);
}

Модули разные, поэтому порядок инициализации между ними произвольный. Пусть CMain инициализируется первым. Вопрос был в том, будет к этому моменту инициализирована переменная name или нет. Если name задать как std::string, то точно гарантий нет. А вот если задать массивом, то получается, что да.
2  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Октября 19, 2018, 07:29:25 pm
Цитировать
делайте что-ли упрощенные ссылки на уже компилируемый пример

А это мысль. Cool Я как-то про такую возможность не подумал.
Вот: http://coliru.stacked-crooked.com/a/5e8e0c4f76c7cb1a Но в этой системе такое даже не компилируется (вроде бы нигде не опечатался...). Smiley

Цитировать
Все это компилятору не нравится

Тут проблема веселее, как мне кажется. Вообще, обычно принято делать поведение системы предсказуемым и ожидаемым. В данном случае компилятор себя так не ведёт. Я вполне чётко ему обозначил, что я желаю унаследовать два класса (CErrorsACU и CErrorsAcs) и чтобы каждый из них мог вызывать определённую в их суперклассе (CErrorsBased) и переопределённую в их потомке (CErrors) функцию. Для этого я указал компилятору, что желаю иметь указатель на функцию потомка CErrors. Я ожидаю, что функция, на которую сделан указатель, пусть и определена в классе CErrorsAcs, но была унаследована CErrors и отныне она принадлежит именно ему. Вроде бы достаточно понятное и простое желание. Поэтому я никак не ожидаю от компилятора перенаправления вызова этой функции в класс CErrorsAcs с последующей потерей связи с его потомком CErrors. Всё-таки, какая мне разница, что за проблемы возникают при этом у компилятора?  Angry

Цитировать
Вообще на первый взгляд - вот так кот путать пользователя передачей обработчиков методов разного уровня наследования .. в данной реализации мне показалась сомнительной.

Да там всё просто. Был класс, в котором была куча функций типа "Включить ошибку устройства ..." и "А включена ли ошибка устройства ... ?". Эти функции записывали/считывали флаги большой структуры, которая через разделяемую память передавалась процессам имитации этих устройств. Но на этапе реализации оказалось, что этих функций будет пара сотен. Не, так неудобно. Поэтому я выделил устройства в классы с их функциями и хотел чтобы все те же их функции были просто унаследованы исходным классом. Дальше встал вопрос сделать триггерную функцию "если включено, то выключить, иначе включить". Я это сделал через указатели на функции этого класса. Тут-то компилятор и возопил. Smiley

Цитировать
объекты/переменные - чем отличаются в вашем контексте?

Тем, что для объектов вызывается конструктор, а переменные просто инициализируются из секций исполняемого файла.
То есть,
char name[]="123"; - инициализируется из секции .data
CErrors cErrors; - инициализируется вызовом конструктора.

Меня интересовал вопрос, инициализируются ли классы строго после все простых типов. Судя по тому, что написано, да.
3  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Октября 19, 2018, 08:16:04 am
Нашёл занятное описание проблемы с указателями на функции классов:

Цитировать
Жуткие сведения об указателях на функции-члены

Рассмотрим ограничения, накладываемые на указатели на функции-члены. Во-первых, нельзя использовать указатель на функцию-член для статического метода. В этом случае нужно использовать обычный указатель на функцию (так что название «указатель на функцию-член» несколько некорректно, на самом деле это «указатель на нестатическую функцию-член»). Во-вторых, при работе с классами-наследниками есть несколько особенностей. Например, следующий код будет скомпилирован на MSVC, если оставить комментарии:

class SomeClass
{
  public:
    virtual void some_member_func(int k, char* p)
    {
      printf(“In SomeClass”);  
    };
}

class DerivedClass : public SomeClass
{
  public:
// Если разкомментировать следующую строку, то код в строке * будет выдавать ошибку
// virtual void void some_member_func(int k, char* p) {printf(“In DerivedClass”); };
};

int main()
{
  // Объявляем указатель на функцию-член класса SomeClass
  typedef void (SomeClass::*SomeClassMFP)(int, char *);
  SomeClassMFP my_memfunc_ptr;
my_memfunc_ptr = &DerivedClass::some_member_func; // ----- строка (*)
}

Довольно любопытно, &DerivedClass::some_member_func являтся указателем на функцию-член класса SomeClass. Это не член класса DerivedClass! Некоторые компиляторы ведут себя несколько иначе: например, Digital Mars C++ считает в данном случае, что &DerivedClass::some_member_func не определен. Но если DerivedClass переопределяет some_member_func, код не будет скомпилирован, т.к. &DerivedClass::some_member_func теперь становится указателем на функцию-член класса DerivedClass!

Приведение между указателями на функции-члены – крайне темная область. Во время стандартизации С++ было много дискуссий по поводу того, разрешено ли приводить указатели на функции-члены одного класса к указателям на функции-члены базового класса или класса-наследника, и можно ли приводить указатели на функции-члены независимых классов. К тому времени, когда комитет по стандартизации определился в этих вопросах, различные производители компиляторов уже сделали свои реализации, причем их ответы на эти вопросы различались. В соответствии со стандартом (секция 5.2.10/9), разрешено использование reinterpret_cast для хранения указателя на член одного класса внутри указателя на член независимого класса. Результат вызова функции в приведенном указателе не определен. Единственное, что можно с ним сделать - это привести его назад к классу, от которого он произошел. Я рассмотрю это далее, т.к. в этой области Стандарт имеет мало сходства с реальными компиляторами.

На некоторых компиляторах происходят ужасные вещи, даже при приведении между указателями на члены базового и наследуемого классов. При множественном наследовании использование reinterpret_cast для приведения указателя на фукнцию-член наследуемого класса к указателю на функцию-член базового класса может скомпилироваться, а может и нет, в зависимости от того в каком порядке базовые классы перечислены в объявлении наследника! Вот пример:

class Derived: public Base1, public Base2  // случай А
class Derived2: public Base2, public Base1 // случай Б
typedef void (Derived::*Derived_mfp)();
typedef void (Derived2::*Derived2_mfp)();
typedef void (Base1::*Base1mfp)();
typedef void (Base2::*Base2mfp)();
Derived_mfp x;

В случае А, static_cast<Base1mfp>(x) отработает успешно, а static_cast<Base2mfp>(x) нет. В то время как для случая Б верно противоположное. Вы можете безопасно приводить указатель на функцию член класса-наследника к указателю на функцию-член только первого базового класса! Если вы попробуете все-таки выполнить приведение не к первому базовому классу, MSVC выдаст предупреждение C4407, а Digital Mars C++ выдаст ошибку. Оба будут протестовать против использования reinterpret_cast вместо static_cast, но по разным причинам. Некоторые же компиляторы будут совершенно счастливы, вне зависимости от того, что вы делаете. Будьте осторожны!

Также в Стандарте есть другое интересное правило: можно объявлять указатель на функцию-член класса, до того как этот класс определен. У этого правила есть непредвиденные побочные эффекты, о которых я расскажу позже.

Также стоит отметить, что Стандарт С++ предоставляет указатели на члены-данные. Они имеют те же операторы и некоторые из особенностей реализации указателей на функции-члены. Они используются в некоторых реализациях stl::stable_sort, но я не знаю других значимых применениях этих указателей.


http://rsdn.org/article/cpp/fastdelegate.xml

4  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Октября 18, 2018, 08:23:38 pm
Цитировать
Вам следует почитать и изучить вопрос, как хранятся данные при виртуальном наследовании. Тут на английском но все же примерно написано, что не так просто оперировать указателями на члены класса участвующих в таком наследовании.

Честно говоря, ни черта не понял, что там написано. Undecided
А так, чисто логически, непонятно, почему я не могу создать указатель на унаследованную функцию и вызвав эту функцию не получить преобразование к унаследованному классу.

Цитировать
И вообще, резюмируя - если вы пришли к виртуальному наследованию, то с вероятностью близкой к единице вы архитектурно неправильно представляете свое решение.

Это возможно. Ведь в конечном итоге я всё заменил агрегацией. Мне изначально нужно было, чтобы все классы работали с одной общей структурой и при этом совсем не хотелось передавать при инициализации ссылку на эту структуру в каждый класс, а также все функции этих классов были бы унаследованы объединяющим классом (делегирование делать плохо - этих функций сильно дофига, и я потому и разделил их на отдельные классы). Поэтому я определил структуру в базовом классе и от него унаследовал все остальные. Так как наследование было виртуальным, то базовый класс и эта структура в объединяющем классе CError находятся в единственном числе и все классы работают с одним и тем же экземпляром.

Цитировать
Все это можно почитать тут

О, спасибо!
Если я правильно понял,что там написано, гарантируется инициализация переменных до объектов.
5  Общее / Общение / Re: Платформенно-зависимые типы в C : Октября 11, 2018, 07:19:35 pm
Кстати, очень спорный сайт www.quizful.net. К примеру, приведена программа и предложено определить результат вычитания двух указателей. Про 32 битную плоскую модель памяти в тексте задачи нет ни слова. Один из вариантов "Это бессмысленно". Вот только верным считается не этот вариант (а размер массива, как результат), хотя давным-давно на том же хабре подробно разобрали, почему нельзя определять размер массива вычитанием указателей.
Ну и куча тестов на простую внимательность (пропустили в комментарии */ звёздочку - попробуй с первого раза заметь Smiley ). Ещё мне встретился массив неопределённой длины в структуре, который вообще-то, помнится, совсем не стандартны и просто фишка ряда компиляторов.
6  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Октября 11, 2018, 07:08:37 pm
Интересная штука получается.
Вот есть у меня базовый класс ошибок CErrorsBased вида:

Код:
class CErrorsBased
{
 public:  
  //конструктор
  CErrorsBased();
  //деструктор
  virtual ~CErrorsBased() {};
 protected:
  virtual void SetState(void)=0;//задать состояние в памяти
};

От этого класса унаследованы классы ошибок конкретного устройства:

Код:
class CErrorsAcs:virtual public CErrorsBased
{
 public:  
  //конструктор
  CErrorsAcs();
  //деструктор
  ~CErrorsAcs();
 public:
  void Acs_SetCANError(uint32_t index,bool state);//установить ошибку "отказ CAN"
  bool Acs_IsCANError(uint32_t index);//получить, задана ли ошибка "отказ CAN"
};
...
//----------------------------------------------------------------------------------------------------
//установить ошибку "отказ CAN"
//----------------------------------------------------------------------------------------------------
void CErrorsAcs::Acs_SetCANError(uint32_t index,bool state)
{
 cErrorsState.cAcs[index].CANError=state;
 SetState();
}
..

А от этих классов ошибок конкретного устройства унаследован общий объединяющий класс ошибок.

Код:
class CErrors:virtual public CErrorsACU,virtual public CErrorsAcs
{
 public:  
  //конструктор
  CErrors();
  //деструктор
  ~CErrors();
 public:
  void ChangeState(uint32_t index,void (CErrors::*set_function_ptr)(uint32_t,bool),bool (CErrors::*is_function_ptr)(uint32_t));//изменить состояние ошибки на противоположное
 protected:
  void SetState(void);//задать состояние в памяти
};

А вот дальше интересно. Функция ChangeState сделана так:

Код:
//----------------------------------------------------------------------------------------------------
//изменить состояние на противоположное
//----------------------------------------------------------------------------------------------------
void CErrors::ChangeState(uint32_t index,void (CErrors::*set_function_ptr)(uint32_t,bool),bool (CErrors::*is_function_ptr)(uint32_t))
{
 if ((this->*is_function_ptr)(index)==true) (this->*set_function_ptr)(index,false);
                                       else (this->*set_function_ptr)(index,true);                                      
 if ((this->*is_function_ptr)(index)==true) printf("true!\r\n");
 else printf("false!\r\n");
}

То есть, она требует два указателя на функции класса CErrors. Всё просто.
Вызываем: cErrors.ChangeState(index,&CErrors::Acs_SetCANError,&CErrors::Acs_IsCANError);

Компилятор напрягся:
Цитировать
pointer to member cast from virtual base 'CErrorsAcs'
will only work if you are very careful


Не понимаю, зачем он сделал это преобразование (а оно оказалось критичным). Эти методы унаследованы CErrors и в целом ему уже принадлежат.
Запускаем программу. И падаем. А дело в том, что функция класса CErrorsAcs вызывает SetState. Но SetState была определена в CErrorsBased и реализована в CErrors. А компилятор сделал преобразование к классу CErrorsAcs. И была вызвана функция без реализации.

Интересно, для чего компилятору понадобилось сделать такое вот преобразование?
Так-то я выбросил почти всё это наследование и сделал агрегацию, но стало интересно, почему же так получилось.

Кстати, что-то найти не могу порядок инициализации переменных (и массивов строк вида a[]="sdfdfsdf"; ) и классов и прочих сложных типов между модулями. Вот если в одном модуле класс создаётся глобально и в своём конструкторе вызывает динамическое создание другого класса, который в уже своём конструкторе желает взять строковую константу, то какие гарантии, что эта константа (определённая в том же модуле, где и конструктор её использующий) уже инициализирована? Для типа std::string - никаких, а вот для вида a[]="sdfdfsdf" есть ли гарантия, что сперва будут инициализированы все простые типы, а лишь потом сложные?. Я знаю, что порядок между модулями не определён, а внутри модуля в порядке описания (если не использовано явное указание компилятору на то, что должно был инициализировано сначала). Но тогда легко получается вышеописанная ситуация. В данном примере я заменил std:string на обычный массив и он стал инициализироваться перед инициализацией классов. В принципе, насколько я помню, секция .data как раз и хранит значения глобальных переменных, а секция .text константы. Следовательно, при запуске эти секции уже есть в программе и они уже инициализированы задолго до вызовов конструкторов любых сложных объектов.
7  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 14, 2018, 07:19:27 pm
я поставил Mate. Smiley Меня просто достала windows 7 (я мог бы и XP поставить, но решил в качестве эксперимента всё же перейти хотя бы на семёрку). Она просто неудобная. Тупой проводник без кнопки 'на уровень выше',часто забывающий переключать папку по одинарному щелчку. Тормоза Firefox. Испорченный Paint. Нет, пора на Linux возвращаться после десятилетнего перерыва. Smiley Правда, вот чего я в линуксах не люблю, так это постоянные изменения с каждым обновлением. Я всё же люблю стабильность... Ну и система пакетов меня раньше доводила до белого каления, когда в системе половина мусора, который используют 1.5 приложения, а этот мусор тащит свои зависимости разных версий. Ставишь из тарбола программу, а ей ещё 100 пакетов надо, а им ещё, а ещё один не совместим с тем, что уже есть. Тут хоть apt работает автоматически. Вроде бы. Smiley

Цитировать
Ну а окружений рабочего стола - пактически в любом линухе на любой вкус и цвет.

Игра в конструктор меня не прельщает. Потому я и не ставил gentoo. Smiley
8  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 14, 2018, 03:27:54 pm
Не, Debian такая же, как и Ubuntu.
Я Mint поставил. Он мне понравился. Smiley
9  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 13, 2018, 05:59:19 pm
Цитировать
Она была в dos.h, которого под unix-ами нет

Логично. Smiley Просто delay находится в unistd. А "<unistd.h> содержит различные основные функции и константы POSIX". Потому я и думал, что она везде, где POSIX есть должна быть.

Цитировать
Вы, наверное, с QNX 6.6 путаете, там как раз Photon нет.

Наверное. Я дальше 6.5 не смотрел. Smiley

Цитировать
Вероятно должно. На какие-то ЕС1866 ставится. Они же разные бывают по начинке, да?

Судя по буклету, по которому заказывали, там вариативность небольшая.
10  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 13, 2018, 02:21:21 pm
Цитировать
Зачем Вам знать про pkg-config и каталоги? Вопросы опять же риторические.

Не всегда ведь проект делается в IDE. Да и вот свежий пример: решил-таки Linux поставить. Смотрим, что у нас есть из популярного:
Fedora
Mint
Ubuntu
OpenSuSe
Mageia
Astra Linux

У всех (кроме Astra) перечисленных графика оформления в стиле современных мультфильмов - примитивизм в дизайне жуткий. Смотреть просто противно. Все эти градиенты чистых цветов просто уродство. Но я помню, 14 лет назад я сидел на Mandrake и Red Hat и там мне решительно нравились темы оформления окон в KDE и вообще общий дизайн. Жаль, больше они не работают на современных системах. А что за хрень штампуют сейчас? Убить этих дизайнеров.
Ubuntu 16.10 отказалась ставить mc по atp install! Не доверяет, говорит, репозиторию! И вылетает в ошибку сразу после загрузки на I5. Копирование на IDE-винчестер шло со скоростью 10...9...8...1.5 Мб/с. Это шутка такая? Windows 7 только что на этом винчестере летала. Ну и дурацкая панель вместо "пуск". То же и у Fedora.
Более-менее Mint нормально работает. Но дизайн всё равно отвратный.
Mageia 3 была ещё ничего. Но Mageia 6... всё тот же отвратный дизайн.
У Astra всё вроде бы есть, но что-то я задолбался её на Уране настраивать. То порты com не видит, то запись в lpt только root имеет (sudo не помогает).
Наверное, всё же Mint поставлю.

Цитировать
Во-первых, если бы Вы внимательно прочитали документацию,

Честно говоря, я поражаюсь памяти присутствующих. Smiley Я давно забыл, что где и как читал. И что там написано. А вы всё помните. Smiley Как вам это удаётся?! Roll Eyes А так, я был уверен, что delay штатная функция unix. Да она и в ms-dos вроде бы была...

Цитировать
Ну а, во-вторых, аналог delay() на POSIX вызовах делается за 5 минут с учётом гугления.

Сделать-то я сделал, но осадочек остался. Smiley

Цитировать
Вместо QNX 6.5 вам бы закупить ЗОСРВ «Нейтрино».

А ПО для QNX 6.3 на нём работает? Или там Qt и от фотона одни воспоминания? Smiley Ну и главная головная боль - ставится и работает ли оно на таком чуде, как бывшая ЕС-1866, а ныне Уран-2.

Хотя, написано "Технологии Qt, GTK, Photon".

Цитировать
Да и сравниваете Вы MSVS 6.0 и 2010 на современном железе под Windows и IDE Momentics 2.2 на урезанной Java под QNX.

Ну уж VC 6 у меня на совсем слабых системах работала гораздо быстрее, чем Momentics 2.2 на современном железе.

Цитировать
Недавно запускал свежий MSVS на виртуалке под Core i5 выделив ей 4 ядра и 8 гигов оперативки — работать нельзя

Это которой 40 ГБ надо? Нет, я такое не использую. К счастью. Потому и остановился на 2010 и Windows XP Smiley

Цитировать
из за особенностей реализации Java под QNX.

Честно говоря, плохо представляю, что там можно было сделать такого, чтобы сама Java ТАК отжирала процессор. И при этом скорость работы от процессора (начиная с определённых частот) почти переставала зависеть.  Roll Eyes
11  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 10, 2018, 07:56:55 pm
Цитировать
Ну, хочется человеку найтивно... А может, подругому никак...

Так для кросскомпиляции придётся таскать ещё отдельный компьютер. Настраивать его. Беречь от вирусов (а в QNX я спокойно сую любые флэшки и даже не задумываюсь). Да и, если честно, приятно в чистом UNIX работать. Просто приятно. Вот чисто эстетически. Smiley Можно, конечно, под Linux работать, но вот его-то я как раз не люблю: вот эти pkg-config --cflags libusb-1.0 в makefile появились потому, что в разных дистрибутивах библиотеки раскидывались в разные каталоги, что меня так просто выводит из себя. Ну и почему в unistd в linux нет delay я тоже понять не могу. Roll Eyes Портировали тут часть моей QNX-программы под Astra-Linux, релиз "Орёл". И оказалось, delay-то отсутствует в системе. Cool
Впрочем, вот купят QNX 6.5 и попробую кросскоспиляцию. (я надеюсь. А то есть подозрение, что QNX 6.5 вояки не разрешат. ГК, конечно, уверенно кричал, что поставим, что нам надо на ноутбуки (туда 6.3 и 6.4 не поставить), когда я его предупреждал под что будет написано ПО, но я думаю, он себя переоценил, и всё это зарубят на присвоении литеры. Переписывать под этот "Орёл" на QT программу с кучей фотоновской графики и специфических QNX-вещей - да проще послать их всех нафиг).

Цитировать
но второй, имхо, как-раз более понятный

Ну вот так получилось, что у меня наоборот. Smiley

Цитировать
Первое скорее всего кусок, который включится в какойто дефолтный makefale инклюдом.

Ну, не совсем. Там есть ещё cppexamp.mif (подключаемый в тот makefile):

Код:
# cppexamp.mif
#
# This file is always included by makefiles's in sample sub-directories.
#
# Note: the file includes local.mif from this directory; local.mif is empty
#       as shipped.  It can be used for any customization required in a
#       particular installation.
#


!include ../local.mif

.extensions:
.extensions: .exe .lnk .obj .cpp .c

!ifndef cpp_compiler
!   ifdef __NTAXP__
!       define cpp_compiler wppaxp
!       define c_compiler wccaxp
!   else
!       define cpp_compiler wpp386
!       define c_compiler wcc386
!   endif
!endif

!ifndef linker
!   define linker wlink
!endif

!ifndef link_cmds
!   define link_cmds linkpgm.lnk
!endif

!ifndef cpp_options
!   define cpp_options -zq -xs -d1
!   define c_options -zq -d1
!endif

.cpp.obj: .AUTODEPEND
    $(cpp_compiler) $(cpp_options) $[*

.c.obj: .AUTODEPEND
    $(c_compiler) $(c_options) $[*

pump.exe: $(objects) $(link_cmds)
    $(linker) @$(link_cmds)

linkpgm.lnk: $(__MAKEFILES__) ../local.mif
    @%create $^@
    @%append $^@ NAME    pump
    @%append $^@ OPTION  quiet, eliminate, map, show
    @%append $^@ DEBUG   all
    @for %i in ($(objects)) do @%append $^@ FILE    %i

clean: .SYMBOLIC
    @if exist *.exe del *.exe
    @if exist *.lnk del *.lnk
    @if exist *.obj del *.obj
    @if exist *.map del *.map
    @if exist *.err del *.err

Ну и запускает компиляцию wc.bat:

Код:
@echo off
set __opath=%path%
set path=c:\lang\watcom10\bin;c:\lang\watcom10\binw
set __oinc=%include%
set include=c:\lang\watcom10\h
set watcom=c:\lang\watcom10\.
del pump.exe
wmake

Вот и всё.

Но, впрочем, например, для приставки PSP я свои проекты собирал таким makefile:
Код:
TARGET = 3dengine
OBJS =ccontrol.o cdecorator_cisector.o cengine_base.o vram.o cengine_gportal.o cgraph.o ciengine.o cisector.o ckeyboard.o cmouse.o common.o cplayer.o csimplybridge.o csimplydoor.o csimplyplatform.o csimplysector.o csimplyteleport.o cswitchsector.o ctexturefollow.o cunit.o cvideo.o localmath.o cwallmap.o main.o
INCDIR =
CFLAGS = -O3 -G0 -Wall
CXXFLAGS = $(CFLAGS) -fno-exceptions -fno-rtti
ASFLAGS = $(CFLAGS)
LIBDIR =
LDFLAGS =
LIBS =-lpspgum -lpspgu -lm -lstdc++ -lpspaudiolib -lpspaudio -lpsprtc
EXTRA_TARGETS = EBOOT.PBP
PSP_EBOOT_TITLE = 3dengine
PSP_EBOOT_ICON = ICON.PNG
PSP_EBOOT_ICON1 =
PSP_EBOOT_UNKPNG = PIC.PNG
PSP_EBOOT_PIC1 =
PSP_EBOOT_SND0 =
PSPSDK=$(shell psp-config --pspsdk-path)
include $(PSPSDK)/lib/build.mak

В целом, он тоже мне почти понятен.

Цитировать
Во-первых, можете попробовать IDE 7.0 вместо IDE 4.7

А у меня в 6.3 версия IDE 2.2.  Cheesy

Цитировать
любая IDE будет тормозить, мне неизвестны не тормозящие IDE.

CodeBlocks не тормозит.  Roll Eyes Visual Studio 6 и 2010 (я выше не ставил) не тормозит. А IDE Momentics обожает замирать на минутку-другую, пытаясь разобрать файл исходника (чем больше в файле ошибок, тем больше она тормозит. Со временем она набирает кодовую базу что ли и тормозит уже меньше. А потом у неё сбой кодовой базы и приходится стирать один файлик в workspace. Тогда всё начинается заново. Причём, тормозит она больше всего на фотоновских приложениях - там, видно, куча библиотек;пока все обегаешь в поисках функций...). Изменил буковки, нажал Save и можно отдыхать. И это как бы на на хорошем таком промышленном компьютере. Smiley

Цитировать
Со времён 6.2 акцент разработки уже окончательно сместился в сторону кросс-разработки.


Есть у меня подозрение, что IDE тормозит из-за каких-то архитектурных особенностей именно QNX. Причём, компьютеры всё мощнее, а тормоза те же. Уж не связано ли это с блокировкой потоков на каком-либо объекте синхронизации, которая привязана с системному такту?
И я подозреваю, что невозможность запустить IDE с приемлемой скоростью и привели к кроссплатформенной разработке. Чтобы жалоб меньше было. Smiley
12  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 09, 2018, 08:55:00 pm
Так "про это" я с самого начала делал. Но этого оказалось мало.

Что касается своего makefile: здорово, наверное, быть знатоком UNIX-систем, но это не про меня от слова совсем. Smiley У меня от остального-то голова пухнет (да хотя бы от новых стандартов Си++ и непоняток, как всё-таки правильно по современным подходам писать ПО). То есть, makefile такого уровня, как в common.mk я не напишу никогда.
Вот пример доступного для меня по пониманию makefile для досовского Watcom 10:

Код:
# MEMBFUN

pump: .SYMBOLIC pump.exe

objects =main.obj &
cedit.obj &
cmain.obj &
cautomat.obj &
cbutton.obj &
vesa.obj &
ciodata.obj &
cwindow.obj &
font.obj &
cdevice.obj &
cgraphic.obj &
clistbox.obj &
ckbd.obj &
cvideo.obj &
clexeme.obj &
cla.obj &
csa.obj &
tga.obj

cpp_options = -s -5r -5s -fp3 -otiarnlm -bt=dos

!include ../cppexamp.mif

Вот его я понимаю. Smiley

А вот такое, уже слабо понимаю:

Код:
TARGET=$(shell basename `pwd`)
CC=g++
CFLAGS+=$(shell pkg-config --cflags libusb-1.0)
LDFLAGS=$(shell pkg-config --libs libusb-1.0)
SOURCES=main.cpp cflironecontrol.cpp tga.cpp
OBJECTS=$(SOURCES:.cpp=.o)
EXECUTABLE=flirone

all: $(SOURCES) $(EXECUTABLE)

$(EXECUTABLE): $(OBJECTS)
$(CC) $(LDFLAGS) -o $@ $(OBJECTS) $(LDFLAGS) -lm -Wall 

.cpp.o:
$(CC) $(CFLAGS) -c $< -o $@

clean:
rm -f cflironecontrol.o main.o tga.o flirone
13  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 08, 2018, 12:34:09 pm
Там не в этом дело, PoP. Там вся мякотка в том, что после указания каталога как дополнительного, IDE забывает про каталог src, который у неё был основной для исходников (до добавления отдельных каталогов, IDE с src работала). То есть, я-то думаю, что добавляю каталог к уже существующему в списке каталогов с исходниками src, а на самом деле src в список тоже надо после такого добавлять самому.
14  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 07, 2018, 07:18:41 pm
Всё оказалось очень просто. Настроить дополнительные папки можно прямо из IDE. Она сама заполняет EXTRA_SRCVPATH и EXTRA_INCVPATH.
НО (!) вот в чём фишка: при незаполненных EXTRA_INCVPATH компиляция идёт в каталоге $(PROJECT_ROOT)/src. Если же я добавляю папку, то почему-то про каталог src система забывает. А я-то думал, он изначально по-умолчанию указан как основной. Вот и вся проблема. Нужно просто указать так же в EXTRA_SRCVPATH и EXTRA_INCVPATH и каталог $(PROJECT_ROOT)/src. И всё начинает работать, как надо.

Я разбил проект по папкам с иерархией (41 папка) и теперь почему-то он автоматически компилирует и debug-реализацию, хотя в настройках проекта стоит только release.  Roll Eyes Как так вышло, ума не приложу.  Undecided

Upd. Оказалось, IDE на каком-то этапе создала makefile в папке, где формируется debug-реализация (o-g, там не было makefile). А убрать его в соответствии с настройками проекта она не пожелала.
15  Разработка / Перенос приложений в QNX / Re: CppUnit порт для QNX6 : Августа 06, 2018, 05:51:47 pm
Новая информация от kpda. Оказывается, не OBJ надо добавлять, а EXTRA_SRCVPATH+=$(PROJECT_ROOT)/ . Завтра проверю. И, надеюсь, заработает.
Страниц: [1] 2 3 ... 15