Common Intermediate Language и системное программирование в Microsoft.Net. Макаров А.В - 56 стр.

UptoLike

Преобразование значения с плавающей запятой к типу float32
может вызывать потерю точности. Кроме того, если это значе-
ние слишком велико для float32, то результатом преобразова-
ния является +inf или -inf.
Инструкция conv.r.un интерпретирует целое значение, лежащее
на вершине стека, как не имеющее знака и преобразует его к ве-
щественному типу (либо float32, либо float64 в зависимости от
значения).
Если переполнение возникает при преобразовании значения
одного целого типа к другому целому типу, то обрезаются стар-
шие биты значения.
В таблице 3.16 приведены инструкции для преобразования значений,
имеющих знак, к целым типам с контролем переполнения. В случае воз-
никновения переполнения эти инструкции генерируют исключение
OverflowException.
Инструкции, представленные в таблице 3.17, используются для пре-
образования беззнаковых значений к нужному типу и генерируют исклю-
чение OverflowException в случае переполнения.
Common Intermediate Language
99
3.2.2.2. Унарные арифметические операции
В таблице 3.13 приведены две инструкции, выполняющие унарные
арифметические операции. Диаграмма стека для унарных операций вы-
глядит следующим образом:
... , value -> ... , result
Инструкция neg применима как для целых чисел, так и для чисел с
плавающей запятой и обладает двумя особенностями:
Результатом применения этой инструкции к наименьшему от-
рицательному целому числу (такое число не имеет «парного»
положительного числа) является само это наименьшее отрица-
тельное число. Для того чтобы иметь возможность перехватить
эту ситуацию, необходимо вместо инструкции neg использовать
sub.ovf.
Результатом применения этой инструкции к NaN является NaN.
3.2.2.3. Инструкция ckfinite
Инструкция ckfinite (см. таблицу 3.14) генерирует исключение
ArithmeticException, если число с плавающей запятой, находящееся на
вершине стека вычислений, равно NaN, +inf или -inf. Если исключение
не генерируется, то стек вычислений не меняется, поэтому диаграмма сте-
ка выглядит следующим образом:
... , value -> ... , value
Таблица 3.14. Инструкция ckfinite
3.2.2.4. Преобразование значений
Инструкции преобразования значений потребляют один операнд со
стека вычислений и преобразуют его к нужному типу. Диаграмма стека для
этих инструкций выглядит следующим образом:
... , value -> ... , result
Базовые инструкции преобразования представлены в таблице 3.15.
Они обладают следующими особенностями:
Преобразование чисел с плавающей запятой к целому типу обре-
зает дробную часть числа. Если при этом возникает переполнение,
то возвращаемый результат неопределен (зависит от реализации).
98
CIL и системное программирование в Microsoft .NET
Код Инструкция Встроенный Описание
операнд
0xC3 ckfinite –Проверка того, что число с пла-
вающей запятой является ко-
нечным
Код Инструкция Встроенный Описание
операнд
0x67 conv.i1 Преобразовать к int8
0x68 conv.i2 Преобразовать к int16
0x69 conv.i4 Преобразовать к int32
0x6A conv.i8 Преобразовать к int64
0x6B conv.r4 Преобразовать к float32
0x6C conv.r8 Преобразовать к float64
0x6D conv.u4 Преобразовать к unsigned int32
0x6E conv.u8 Преобразовать к unsigned int64
0x76 conv.r.un Преобразовать беззнаковое це-
лое число в число с плавающей
запятой
0xD1 conv.u2 Преобразовать к unsigned int16
0xD2 conv.u1 Преобразовать к unsigned int8
0xD3 conv.i Преобразовать к native int
0xE0 conv.u Преобразовать к unsigned native int
Таблица 3.15. Преобразование значений без контроля переполнения.
98                           CIL и системное программирование в Microsoft .NET   Common Intermediate Language                                                 99


3.2.2.2. Унарные арифметические операции                                               Таблица 3.15. Преобразование значений без контроля переполнения.
     В таблице 3.13 приведены две инструкции, выполняющие унарные
                                                                                 Код      Инструкция            Встроенный   Описание
арифметические операции. Диаграмма стека для унарных операций вы-
глядит следующим образом:                                                                                       операнд
     ... , value -> ... , result                                                 0x67     conv.i1               –            Преобразовать к int8
     Инструкция neg применима как для целых чисел, так и для чисел с             0x68     conv.i2               –            Преобразовать к int16
плавающей запятой и обладает двумя особенностями:                                0x69     conv.i4               –            Преобразовать к int32
         • Результатом применения этой инструкции к наименьшему от-              0x6A     conv.i8               –            Преобразовать к int64
           рицательному целому числу (такое число не имеет «парного»
                                                                                 0x6B     conv.r4               –            Преобразовать к float32
           положительного числа) является само это наименьшее отрица-
           тельное число. Для того чтобы иметь возможность перехватить           0x6C     conv.r8               –            Преобразовать к float64
           эту ситуацию, необходимо вместо инструкции neg использовать           0x6D     conv.u4               –            Преобразовать к unsigned int32
           sub.ovf.                                                              0x6E     conv.u8               –            Преобразовать к unsigned int64
         • Результатом применения этой инструкции к NaN является NaN.            0x76     conv.r.un             –            Преобразовать беззнаковое це-
                                                                                                                             лое число в число с плавающей
3.2.2.3. Инструкция ckfinite
                                                                                                                             запятой
     Инструкция ckfinite (см. таблицу 3.14) генерирует исключение
ArithmeticException, если число с плавающей запятой, находящееся на              0xD1     conv.u2               –            Преобразовать к unsigned int16
вершине стека вычислений, равно NaN, +inf или -inf. Если исключение              0xD2     conv.u1               –            Преобразовать к unsigned int8
не генерируется, то стек вычислений не меняется, поэтому диаграмма сте-          0xD3     conv.i                –            Преобразовать к native int
ка выглядит следующим образом:                                                   0xE0     conv.u                –            Преобразовать к unsigned native int
     ... , value -> ... , value

      Таблица 3.14. Инструкция ckfinite                                                  • Преобразование значения с плавающей запятой к типу float32
                                                                                           может вызывать потерю точности. Кроме того, если это значе-
Код           Инструкция Встроенный Описание                                               ние слишком велико для float32, то результатом преобразова-
                         операнд                                                           ния является +inf или -inf.
0xC3          ckfinite   –          Проверка того, что число с пла-                      • Инструкция conv.r.un интерпретирует целое значение, лежащее
                                    вающей запятой является ко-                            на вершине стека, как не имеющее знака и преобразует его к ве-
                                                                                           щественному типу (либо float32, либо float64 в зависимости от
                                    нечным
                                                                                           значения).
                                                                                         • Если переполнение возникает при преобразовании значения
3.2.2.4. Преобразование значений                                                           одного целого типа к другому целому типу, то обрезаются стар-
     Инструкции преобразования значений потребляют один операнд со                         шие биты значения.
стека вычислений и преобразуют его к нужному типу. Диаграмма стека для                В таблице 3.16 приведены инструкции для преобразования значений,
этих инструкций выглядит следующим образом:                                      имеющих знак, к целым типам с контролем переполнения. В случае воз-
     ... , value -> ... , result                                                 никновения переполнения эти инструкции генерируют исключение
     Базовые инструкции преобразования представлены в таблице 3.15.              OverflowException.
Они обладают следующими особенностями:                                                Инструкции, представленные в таблице 3.17, используются для пре-
         • Преобразование чисел с плавающей запятой к целому типу обре-          образования беззнаковых значений к нужному типу и генерируют исклю-
           зает дробную часть числа. Если при этом возникает переполнение,       чение OverflowException в случае переполнения.
           то возвращаемый результат неопределен (зависит от реализации).