stringtranslate.com

Нести флаг

В компьютерных процессорах флаг переноса (обычно обозначаемый как флаг C ) — это один бит в регистре состояния системы / регистре флага, используемый для указания того, когда арифметический перенос или заем были сгенерированы из старшей битовой позиции арифметико-логического устройства (АЛУ). Флаг переноса позволяет складывать/вычитать числа, превышающие ширину одного АЛУ, путем переноса (добавления) двоичной цифры из частичного сложения/вычитания в младшей битовой позиции старшего слова. Это обычно программируется пользователем процессора на уровне ассемблера или машинного кода, но может также происходить внутренне в некоторых процессорах, через цифровую логику или микрокод , где некоторые процессоры имеют более широкие регистры и арифметические инструкции, чем (комбинаторное или «физическое») АЛУ. [1] Он также используется для расширения битовых сдвигов и поворотов аналогичным образом на многих процессорах (иногда делается через выделенный флаг). Для вычитающих операций используются два (противоположных) соглашения, поскольку большинство машин устанавливают флаг переноса при заимствовании, в то время как некоторые машины (например, 6502 и PIC ) вместо этого сбрасывают флаг переноса при заимствовании (и наоборот).

Использует

Флаг переноса зависит от результата большинства арифметических (и обычно нескольких битовых) инструкций и также используется в качестве входных данных для многих из них. Некоторые из этих инструкций имеют две формы, которые либо считывают, либо игнорируют перенос. В языках ассемблера эти инструкции представлены мнемоникой, такой как ADD/SUB, ADC/SBC( ADD/SUBвключая перенос), SHL/SHR( сдвиги битов ), ROL/ROR(повороты битов), RCR/RCL(поворот через перенос) и т. д. [2] Использование флага переноса таким образом позволяет выполнять многословные операции сложения, вычитания, сдвига и поворота.

Примером может служить то, что произойдет, если сложить 255 и 255 с использованием 8-битных регистров. Результат должен быть 510, что является 9-битным значением 111111110в двоичном формате. 8 младших бит, всегда хранящихся в регистре, будут 11111110двоичными (254 в десятичном формате), но поскольку есть перенос бита 7 (восьмой бит), перенос устанавливается, указывая, что результату нужно 9 бит. Допустимый 9-битный результат является конкатенацией флага переноса с результатом.

Для x86 ALU размером 8 бит, интерпретации 8-битного дополнения до двух, операция сложения 11111111+ 11111111приводит к 111111110, Carry_Flagустановке, Sign_Flagустановке и Overflow_Flagочистке.

Если 11111111представляет собой знаковое целое число в формате дополнения до двух −1 ( ADD al,-1), то интерпретация результата равна -2, поскольку Overflow_Flagясна, и Carry_Flagигнорируется. Знак результата отрицательный, поскольку Sign_Flagзадано. 11111110— знаковое целое число в формате дополнения до двух −2.

Если 11111111представляет собой беззнаковое целое двоичное число 255 ( ADD al,255), то интерпретация результата будет 254, что неверно, поскольку самый старший бит результата попал в Carry_Flag, который, следовательно, нельзя игнорировать. Overflow_FlagИ Sign_Flagигнорируются.

Другим примером может служить 8-битный регистр с битовой комбинацией 01010101и установленным флагом переноса; если мы выполним инструкцию поворота влево через перенос , результатом будет 10101011очищенный флаг переноса, поскольку старший бит (бит 7) был повернут в перенос, а перенос — в младший бит (бит 0).

Ранние микропроцессоры Intel 4004 и Intel 8008 имели специальные инструкции для явной установки и сброса флага переноса. Однако более поздние Intel 8080 (и Z80 ) не включали явный код операции сброса переноса, поскольку это можно было сделать одинаково быстро с помощью одной из побитовых инструкций AND, OR или XOR (которые не используют флаг переноса).

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

Против заимствования флага

Хотя флаг переноса хорошо определен для сложения, существуют два распространенных способа использования флага переноса для операций вычитания.

Первый использует бит как флаг заимствования, устанавливая его, если a < b при вычислении ab , и заимствование должно быть выполнено. Если ab , бит очищается. Вычитание с инструкцией заимствования ( SBB) вычислит abC = a −( b + C ), в то время как вычитание без заимствования ( SUB) действует так, как если бы бит заимствования был очищен. Семейства 8080 , 6800 , Z80 , 8051 , x86 [2] и 68k (среди прочих) используют бит заимствования.

Второй использует тождество, что − x = ( not x )+1 напрямую (т. е. без сохранения инвертированного бита переноса) и вычисляет ab как a +( not b )+1. Флаг переноса устанавливается в соответствии с этим сложением, а вычитание с переносом вычисляет a + not( b )+ C , в то время как вычитание без переноса действует так, как если бы бит переноса был установлен. Результатом является то, что бит переноса устанавливается, если ab , и очищается, если a < b . Процессоры System/360 , [3] 6502 , MSP430 , COP8 , ARM и PowerPC используют это соглашение. 6502 является особенно известным примером, поскольку у него нет операции вычитания без переноса, поэтому программисты должны гарантировать, что флаг переноса установлен перед каждой операцией вычитания, где заем не требуется. [4]

Чаще всего первую альтернативу называют «вычитанием с заемом», а вторую — «вычитанием с переносом». Однако есть исключения в обоих направлениях; архитектуры VAX , NS320xx и Atmel AVR используют соглашение о заемном бите, но называют свою операцию abC «вычитанием с переносом» ( SBWC, SUBCи SBC). Архитектуры PA-RISC и PICmicro используют соглашение о переносном бите, но называют свою операцию a +not( b )+ C «вычитанием с заемом» ( SUBBи SUBWFB).

Микроконтроллеры ST6 8-бит, пожалуй, самые запутанные из всех. Хотя у них нет инструкции "вычитать с переносом", у них есть бит переноса, который устанавливается инструкцией вычитания, а соглашение зависит от модели процессора. Процессор ST60 использует соглашение "перенос", тогда как процессоры ST62 и ST63 используют соглашение "заимствовать". [5]

Смотрите также

Ссылки

  1. ^ Примерами таких процессоров являются, среди многих других, хорошо известные Z80 и 68000.
  2. ^ ab "Руководство разработчика программного обеспечения для архитектуры Intel, том 2: Справочное руководство по набору инструкций" (PDF) . Получено 25.10.2007 .
  3. ^ Принципы работы IBM System/360 (PDF) . стр. 28. Форма IBM A22-6821-0.
  4. ^ Тан, BTG (май 1983 г.). "Инструкции SBC, TSX и TXS для 6800 и 6502" (PDF) . Журнал доктора Добба (79): 67–68.
  5. ^ "ST6 Family Programming Manual" (PDF) . Версия 2.0. STMicroelectronics . Октябрь 2004. С. 21–22, 42. Получено 28.02.2017 .

Внешние ссылки