Причина использования бит переноса и бит переполнения

Я беру введение в класс встраиваемых систем. Читая, я столкнулся с интересным вопросом о реализациях бита переноса и бита переполнения.

Я знаю, что такое бит переноса и бит переполнения, однако я не могу представить себе ситуацию, в которой кто-то мог бы использовать бит переноса. Одна из причин, по которой я подумал, заключалась в том, чтобы выровнять память. Кто-нибудь может пролить свет на этот вопрос, пожалуйста?


person chaitanya.varanasi    schedule 04.10.2012    source источник


Ответы (3)


Флаг переноса полезен для эффективного выполнения арифметических и логических операций с данными, которые шире, чем аккумулятор или регистры процессора. Это может не беспокоить современный 64-битный процессор, но ранние микропроцессоры и некоторые современные микроконтроллеры могут по-прежнему иметь только 8-битный или 16-битный аккумулятор. Бит переноса позволяет добавлять / вычитать и сдвигать / вращать любую длину, состоящую из нескольких слов, с помощью одного аккумулятора. Помимо базовых инструкций сложения, вычитания, сдвига и поворота (чтобы начать операцию с данными из нескольких слов), были бы добавление с переносом, вычитание с заимствованием, сдвиг с переносом и инструкции поворота с переносом (для работы с последующими словами). И для облегчения таких кодовых последовательностей инструкции INC reg и DEC reg (для модификации указателя и счетчика циклов) не будут изменять (и, следовательно, сохранять) флаг переноса, даже если они являются арифметическими инструкциями.

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

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

person sawdust    schedule 04.10.2012

Бит переноса используется в машинных инструкциях для проверки условий less_than / more_than для беззнаковых переменных, например, или условия завершения цикла, поскольку вычитание 1 из 0 приводит к установке бита переноса.

Также в языке ассемблера перенос арифметических операций, таких как сложение, можно использовать для простой реализации арифметики произвольной точности.

Бит переноса не всегда виден программисту на языках более высокого уровня.

Бит переполнения используется редко, но, как показывает семантика, он может и должен использоваться научными алгоритмами, правильность которых должна быть гарантирована в указанном диапазоне целых чисел со знаком. add reg1, reg2; JO exception_handler позволяет эффективно тестировать, дает ли алгоритм, работающий с целыми числами со знаком, правильные результаты. То же самое относится к вычитанию и целочисленному умножению (IMUL), но не к целочисленному делению, после которого все (арифметические) флаги не определены.

person Aki Suihkonen    schedule 04.10.2012
comment
Бит переполнения используется редко - редко используется сам по себе, но используется все время как часть условий сравнения со знаком, например x86 jg прыгает, если SF == OF. Проверка OF необходима в случае, если вычитание, выполняемое cmp a,b, переполняется, в результате чего SF оказывается перевернутым по сравнению с математическим результатом бесконечной точности. - person Peter Cordes; 11.11.2020

Вот простой пример кода, в котором используется флаг переноса:

int main (void)
{
    unsigned int smallnum;
    unsigned int largenum;
    unsigned int temp_num;

    printf("Enter a number: ");
    scanf("%d", &smallnum);
    printf("Enter a bigger number: ");
    scanf("%d", &largenum);

    temp_num = smallnum - largenum;

    if  (smallnum < largenum)
    {
        printf("Carry Flag SET!");
    }
    else
    {
        printf("Carry Flag CLEAR!");
    }

    return(EXIT_SUCCESS);
}

Если мы посмотрим на файл листинга, мы увидим следующее:

  48:carry.c       ****     if  (smallnum < largenum)
  82                    .loc 1 48 0
  83 0090 8B542418      movl    24(%esp), %edx
  84 0094 8B442414      movl    20(%esp), %eax
  85 0098 39C2          cmpl    %eax, %edx
  86 009a 730E          jae L2

Таким образом, оператор if компилируется для сравнения двух операндов, за которым следует jae или «Перейти, если больше или равно». Тест, используемый в команде jae, должен проверить, равен ли флаг переноса 0. См. этот справочник, чтобы узнать, какие флаги для каких условных переходов проверяются. .

Когда вы пишете код, создайте файл листинга и просмотрите все условные переходы. Многие из них проходят тестирование, чтобы проверить состояние флага переноски.

person embedded.kyle    schedule 04.10.2012