Pull to refresh
170
0
Андрей @apangin

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

Send message
Ага, интересная штука. Хотя применять не доводилось. А тебе? И внутри JDK, похоже, нигде не используется.
Отвечу комментариями к исходникам:
Cleaners are a lightweight and more robust alternative to finalization. They are lightweight because they are not created by the VM and thus do not require a JNI upcall to be created, and because their cleanup code is invoked directly by the reference-handler thread rather than by the finalizer thread. They are more robust because they use phantom references, the weakest type of reference object, thereby avoiding the nasty ordering problems inherent to finalization.

Cleaners may also be invoked directly; they are thread safe and ensure that they run their thunks at most once.
В Java есть понятия политики безопасности и пермиссий. Когда вы запускаете java локально, SecurityManager выключен, поэтому вам и позволены все эти хаки. Теперь попробуйте запустить java с параметром -Djava.security.manager и тут же получите java.security.AccessControlException: access denied (java.lang.RuntimePermission accessClassInPackage.sun.misc). Java — безопасная платформа (для аплетов, например, SecurityManager всегда включен), но она не ограничивает возможности тех, кто знает, что делает.
Тоже не совсем верно. Бывает и наоборот, когда одной инструкцией на RISC делается то, для чего на CISC потребуется 5.
Сравните, например, ARM:
addeq R0, R1, R2, lsl R3

и x86:
jnz @skip
mov eax, ebx
mov ecx, esi
shl eax, cl
add eax, edx
@skip:
Есть простой, честный и потокобезопасный способ написать exceptions на макросах в Си, хоть и не столь элегантный, как в статье. Именно такой метод используется в HotSpot JVM:
#define TRAPS           Thread* _thread
#define CHECK_(x)       _thread); if (_thread->has_exception()) return x; (0
#define CHECK_0         CHECK_(0)
#define THROW_(msg, x)  { _thread->set_exception(msg, __FILE__, __LINE__); return x; }
#define THROW_0(msg)    THROW_(msg, 0)
#define CATCH(ex)       for (Exception* ex = _thread->exception(); ex != NULL && _thread->clear_exception(); ex = NULL)

int this_function_may_throw(int x, float y, TRAPS) {
    ...
    THROW_0("Exception message");
    ...
}

int main() {
    this_function_may_throw(x_arg, y_arg, CHECK_0);
    ...
    return 1;
}

Когда дампы >10GB? Вряд ли.
На самом деле, составить полный и понятный отчет об ошибке довольно трудоемко. Взять, к примеру, уже упомянутые исходники HotSpot JVM — там целый модуль посвящен генерации hs_err.log в случае падения приложения. И есть свои тонкости. Например, надо учитывать, что код обработчика надо исполнять на отдельном стеке, т.к. ошибка могла быть вызвана переполнением стека; а еще, что SEGV могут возникать и внутри самого обработчка и т.д.
Сможем с помощью sigaction(). Тогда в обработчик будет передана подробная информация о SIGSEGV, включая адрес инструкции, на которой свалилась программа, адрес памяти, по которому обратились, а также контекст со значениями регистров процессора в момент падения.
Использовать sigaction() вместо signal(). Тогда в обработчик сигнала будет передан указатель на контекст, содержащий помимо прочего значения регистров в момент исключения. Изменив в контексте значение регистра PC, по возвращении из обработчика можно попасть в любую точку программы.
Можно не только теоретически, но и на практике это широко применяется в системном программировании. Например, в HotSpot JVM обработка SIGSEGV используется для ликвидации проверок на null, для ускоренной проверки на StackOverflow, для Safepoint-поллинга, для эмуляции memory barrier и для разных спекулятивных ловушек, связанных с обработкой особых ситуаций виртуальной машины без генерации дополнительного кода для обычных быстрых путей. Думаю, напишу об этих приемах отдельную статью.
Не спасает. В статье пример «2 Double Checked Locking & volatile» написан неправильно.
При вызове статического метода есть проверка (так называемый class initialization barrier): если receiver класс не инциализирован, то вызывается его инициализация. §2.17.5 JVM specification говорит о том, что при инициализации класса в первую очередь происходит синхронизация на объекте java.lang.Class, представляющем этот класс.

Однако фокус состоит в том, что в процессе исполнения Java-приложения после инициализации класса JVM может заново перекомпилировать метод, вызывающий getInstance(), избавившись от ненужного class initialization barrier и оптимизировав таким образом вызов статического метода.
Чтение volatile поля в Java на x86 архитектуре ничем не отличается от чтения обычного поля. Отличается только запись volatile поля, которая сопровождается инструкцией lock add [esp], 0, служащей эффективным memory-barrier'ом. И то, это совсем далеко от того, что делается при синхронизации с помощью synchronized. В общем, не слушайте тех, кто говорит, что volatile равносилен synchronized. В HotSpot VM накладные расходы на доступ к volatile полям очень маленькие, и то только на запись.
Это распространенное заблуждение. Объект создастся не тогда, когда загрузится класс, а когда класс будет инициализирован. А инициализация класса произойдет в момент первого доступа к INSTANCE. А если у класса-синглтона вызывают прочие статические методы, которым не нужен этот самый instance, на мой взгляд, это говорит о недоработке в проектировании.
Правильный Singleton пишется без 'e' на конце.
И чем же, по-вашему, вариант с enum не «ленивый»?
Да, раз уж я упомянул tutorial, надо писать все грамотно. Дописал, спасибо.
Вообще-то речь идет о Java. Там newLen += allowedChars[ch] выльется как минимум в два сравнения (range check). Да даже для C эта оптимизация не имеет смысла: newLen += (ch >= ' ') будет быстрее. Условных переходов в сгенерированном коде нет.
Она не лишняя :) В Java это беззнаковый сдвиг в отличие от знакового >>.
При >> мы получим 0 или -1, а при >>> 0 или 1.
Byte[] намного меньше, т.к. новые объекты типа Byte не создаются — их всего 256, и они все закэшированы.
Объекты типа Short, Integer, Long занимают одинаково по 16 байт (на 32-битной платформе), т.к. заголовок объекта в HotSpot состоит из 8 байт, и сами объекты аллоцируются с выравниванием в 8 байт.

Information

Rating
Does not participate
Location
Санкт-Петербург, Санкт-Петербург и область, Россия
Works in
Registered
Activity