Как стать автором
Обновить
2
0

Пользователь

Отправить сообщение
В примере XeTeX имеются три ошибки. Всё-таки код надо проверять перед публикацией.

В общем же действительно стоит обращать внимание на XeTeX и LuaTeX, а то многие работают по старинке и даже не знают, что где-то есть Unicode по умолчанию и поддержка TrueType/OpenType шрифтов.
Сам спросил, сам ответил — dbp-consulting.com/StrictAliasing.pdf показывает, как это можно делать и в C, и в C++.
Отличная статья!

Мне всегда было интересно, как же поступать в случае, если надо обработать двоичный пакет, пришедший по сети. Предположим, есть буфер char buf[12], где хранится пакет, и описание того, что в нём должно быть:
struct packet {
  int a, b;
  char s[4];
};

Код типа const struct packet *p = (const struct packet *)buf; не прокатывает по вышеописанным причинам. Но, получается, всё будет хорошо, если buf скопировать в
union {
  char buf[12];
  struct packet p;
} u;

и далее работать с u.p? (При условии, конечно, что данные в пакете осмысленные и не являются trap representation.)
Конечно, сейчас использовать make стоит только для маленьких (из пары-тройки исходных файлов) проектов или для развлечения. Если же пытаться применить make к чему-то большему, то в итоге получится тот же autotools или CMake, только вот с наполовину меньшим функционалом и кучей ошибок.
www.gnu.org/software/make/manual/html_node/Implicit-Variables.html — иначе получается, что компилировать C++ мы можем только командой g++, C — почему-то тоже этой же командой, а файлы удалять — только rm.
Панель закладок тоже исчезла вместе со строкой состояния?
Если выделить на каждый процессор ровно по одному потоку сборки, то можеть получиться так, что в какое-то время процессор будет простаивать, ожидая ответа от жёсткого диска или другого устройства. Если же количество потоков будет чуть больше, чем количество процессоров, то высока вероятность, что во время таких вынужденных простоев ждущий процесс будет вытеснен другим, которому есть, что вычислять.

+1 — не единственный вариант; например, при наличии системы с 8 процессорами имеет смысл выбрать от 2 до 4 дополнительных потоков (конечно, если хватает памяти).
Лучше чрезмерно не увлекаться различными флагами и оптимизациями, а то может получиться и «может привести к неработоспособности бинарников», и хуже. Если бы какая-то опция давала очевидное преимущество, то включалась бы вместе с -O2. Того, что написано в http://en.gentoo-wiki.com/wiki/Safe_Cflags, вполне хватает.

Советую также почитать http://funroll-loops.info/.
Нет, всё так. Первый раз исходный код собирается host-компилятором, который сам может и не быть gcc, в итоге получается т. н. stage1. Потом stage1 собирает stage2, а stage2 собирает stage3. В конце stage2 и stage3 сравниваются, и, если они совпадают, делается вывод, что и host-компилятор, и сборка gcc на этой платформе работают правильно, после чего stage3 считается готовым к установке.
Дональд Кнут уже давно это применяет (правда, тут у соискателей премии интерес скорее спортивный): en.wikipedia.org/wiki/Knuth_reward_check
Мрачно, надеюсь, в реальности всё будет не так.
Верно, xmalloc(), как правило, больше используется в программах, просто обрабатывающих данные, например, cp или gcc.

Ещё как вариант вместо exit() можно писать abort(), это приведёт к сигналу SIGABRT, который можно поймать и обработать.
Для некоторых программирование — творчество. Для некоторых — всего лишь способ заработать денег.
Никто же не сказал, что xmalloc() надо вызывать на каждом шаге.
… которые появляются только при работе с неблокирующимися файловыми дескрипторами (O_NONBLOCK), которых здесь нет :)
Чего стоит скорость, если программа может работать неправильно? Сначала следует написать работающий код, а потом его оптимизировать.

Что же касается потерь производительности, то такая версия по сути является дополнительным if'ом, что есть мелочь даже для embedded-систем:

#include <stdlib.h>

static inline void *xmalloc (size_t size)
{
    void *p = malloc(size);

    if (p)
        return p;
    else
    {
        fprintf(stderr, "error: not enough memory\n");
        exit(EXIT_FAILURE);
    }
}


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

void* operator new(std::size_t, const std::nothrow_t&) throw();

, кстати, возвращает. Пример:

#include <new>

int *p = new (std::nothrow) int;
if (p == NULL)
    cerr << "memory allocation failure\n";
Потому что все используют xmalloc().

Информация

В рейтинге
Не участвует
Откуда
Рига, Латвия, Латвия
Зарегистрирован
Активность