Введение

Множественные имена для одного и того же местоположения данных

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

Алиасованные указатели

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

Конфликты с оптимизацией

Оптимизаторы часто вынуждены делать консервативные предположения о переменных, когда возможна алиасинг (совпадение адресов). Например, знание значения переменной (например, x = 5) обычно позволяет выполнять определенные оптимизации (например, распространение констант). Однако компилятор не может использовать эту информацию после присваивания значения другой переменной (например, в C, *y = 10), поскольку существует вероятность, что *y является алиасом x. Это может произойти после присваивания, такого как y = &x. В результате этого присваивания *y, значение x также может измениться, поэтому распространение информации о том, что x равно 5, в последующих выражениях после *y = 10 может быть ошибочным (если *y действительно является алиасом x). Однако, если имеется информация об указателях, процесс распространения констант может задать вопрос: может ли x быть алиасом *y? Если ответ отрицательный, то x = 5 можно распространять безопасно. Другая оптимизация, на которую влияет алиасинг, – это переупорядочивание кода. Если компилятор определит, что x не является алиасом *y, то код, использующий или изменяющий значение x, можно переместить перед присваиванием *y = 10, если это улучшит планирование или позволит выполнить больше оптимизаций циклов. Чтобы обеспечить такую оптимизацию предсказуемым образом, стандарт ISO для языка программирования C (включая более новую редакцию C99, см. раздел 6.5, пункт 7) определяет, что (за некоторыми исключениями) незаконно обращаться к одному и тому же участку памяти, используя указатели разных типов. Компилятор, следовательно, может предполагать, что такие указатели не являются алиасами. Это правило, известное как правило строгого алиасинга, иногда позволяет значительно повысить производительность, но известно, что оно приводит к некорректной работе некоторого в противном случае допустимого кода. Несколько программных проектов намеренно нарушают эту часть стандарта C99. Например, Python 2.x сделал это для реализации подсчета ссылок и потребовал внесения изменений в основные структуры объектов в Python 3 для обеспечения этой оптимизации. Ядро Linux поступает так же, поскольку строгий алиасинг вызывает проблемы с оптимизацией встроенного кода. В таких случаях, при компиляции с помощью gcc, используется опция -fno-strict-aliasing для предотвращения нежелательной оптимизации, которая может привести к неожиданному коду.