Pull to refresh
2
0
Send message
В чем проблема слать себе сигналы? Это стандартный POSIX интерфейс, с четкой семантикой.
Речь идет про POSIX сигналы. Никакого завершения тредов не происходит. Нужно установить обработчик сигнала, так же, как делает sigaction(3) (предположительно, в go есть для этого интерфейс), а потом послать заблокированному треду сигнал, например SIGINTR. В случае, если чтение идет с терминала это эквивалентно нажатию ^C пользователем. Системный вызов read немедленно вернется с EINTR.
Сигнал (man 2 kill) прерывает заблокированный системный вызов, тот возвращается с errno == EINTR.
Пошлите соответствующему треду сигнал, на который установлен обработчик.
Есть метод «quality attribute workshop», разработанный SEI/CMU (http://www.sei.cmu.edu/architecture/tools/establish/qaw.cfm), в котором процесс выявления и ранжирования требований основан на анализе use cases.
Дейкстра (вместе с Хоаром и Флойдом) основал формальную верификацию, как дисциплину. «Дисциплина программирования» собственно про это: weakest (liberal) precondition (https://en.wikipedia.org/wiki/Predicate_transformer_semantics). Архив его EWD заметок, с отсканированными рукописными оригиналами есть на http://www.cs.utexas.edu/~EWD/.
А может быть и не отказались. Сейчас посмотрел Solaris Internals, в v10 еще были. В Солярисе, вообще (было) много интересных вещей с многопоточностью: N:M треды с scheduler activations по Андерсону et at., треды, которые могли прыгать между адресными пространствами (doors).
Да. Плюс в прерывании можно использовать все обычные синхронизационные примитивы, и нет нужды разбивать обработку на top-half vs. bottom-half. Но Сан в конце концов отказался, кажется, от этой схемы, не помню почему.
В Солярисе так (были?) реализованы interrupt threads. Там прерывания обрабатывлись не поверх стека текущего треда, как в традиционном Юниксе, а в специальных пре-аллоцированных тредах. Но вначале, при возникновении прерывания, такой тред не был полноценным, и не был видем планировщику. Только если interrupt thread блокировался, например, на мьютексе, он отлеплялся от ядерного треда, который он прервал, и становился полноценным.
Старый добрый Fluke с неблокирующимися системными вызовами: https://www.usenix.org/legacy/events/osdi99/full_papers/lepreau/lepreau.pdf, плюс еще и ядерных стеков не надо.
Кстати, ext* может быть создана без флага filetype (mkfs -O ^filetype). Этом случае всегда возвращается DT_UNKNOWN.
Oдно ограничение вашего кода (и исходного и модифицированного), которого нет у find(1), это невозможность работать с деревом, в котором длина путей превышает MAXPATHLEN. Поэтому find делает fchdir в директорию и из нее. Ну и при DT_UNKNOWN делать stat. У find есть еще одна оптимизация: от смотрит на nlink *родительской* директории. Это число на 1 больше числа поддиректорий (из-за dotdot). Поэтому если nlink == 1, то поддиректорий гарантировано нет (это самый распространенный случай — большинство директорий листьевые) и делать stat в случае DT_UNKNOWN не нужно.
Update: все-таки опишу.
Для каждого номера бита i, от 0 до 31, найдем сумму всех элементов массива, у которых i-й бит установлен (s[i][1]) и сумму элементов, у которых i-й бит не установлен (s[i][0]), все суммы по модулю 2. Всякий парный элемент участвует точно в тех же суммах, что и его пара и, таким образом, общий вклад от пары во всякой сумме равен 0.
Предположим, сначала, что непарные элементы A и В отличны от нуля. Тогда отличны от нуля только те суммы s[i][j], в которых участвует один или оба непарных элемента. Но непарные элементы отличаются хотя бы одним битом (иначе они были бы парой) k, тогда один из них равен s[k][0], а другой — s[k][1].
Если же один из непарных элементов равен нулю, то для любого k, s[k][0] и s[k][1] и дают искомые числа.
Проще, наверное, показать код, чем описать:
Скрытый текст
static void findunique(int nr, uint32_t *a)
{
    uint32_t s[32][2] = {};
    int      i;
    int      j;
    for (i = 0; i < nr; ++i)
        for (j = 0; j < 32; ++j)
            s[j][!!(a[i] & (1 << j))] ^= a[i];
    for (j = 0; j < 32; ++j)
        if (s[j][0] != 0 && s[j][1] != 0)
            printf("%u %u\n", s[j][0], s[j][1]);
}

Nitpick: площадь (фигуры) будет Area.
Вы посвятили С++ большую часть жизни...
Вопрос вы выделен.
> Да-да, явное лучше чем неявное, но все же?

Наверное проблема в том, что использование []FancyInt как []Stringy некорректно?
Иначе в Join можно было бы сделать
items[0] = new FancyRune;

У массивов нет нетривиального subtyping-а про типу элемента, это вроде как общеизвестно.
А как обрабатывается засыпание потоков операционной системы в остальных случаях, например, при page fault?
Device в Duff's device это все-таки «прием» (как, например, rhetorical device — риторический прием), а не «устройство».

Information

Rating
Does not participate
Registered
Activity