Возникают трудности с пониманием программы на С ++, смены и

0

В моем классе машинного языка мы должны перевести c++ в mips, проблема в том, что я мало знаю c++, просто базовые вещи, поэтому у меня возникают проблемы с занижением этой функции:

void IPtoDD(int arg0, char *arg1)
{
  int temp, numChar, shift = 24;

  for (int i=0; i<4; i++) {
    temp = arg0 >> shift;
    temp = temp & 0x000000ff;
    numChar = byteToDec(temp,arg1);
    arg1 += numChar;
    *arg1++ = '.';
    shift -= 8;
  }

В частности

    temp = arg0 >> shift;
    temp = temp & 0x000000ff;
Теги:
shift

4 ответа

2

Оператор >> является "оператором сдвига справа". Он сдвинет двоичное представление значения слева на x бит справа, где x - число справа. Как это выглядит? Вот некоторые примеры:

decimal: 128                   >> 1 == 64
binary:  0b0000 0000 1000 0000 >> 1 == 0b0000 0000 0100 0000

decimal: 64                    >> 1 == 32
binary:  0b0000 0000 0100 0000 >> 1 == 0b0000 0000 0010 0000

Обратите внимание, как 1 в больших двоичных числах сдвигается вправо на 1. В вашем коде вы arg0 по shift, где arg0 - это некоторый ввод, а shift - 24, 16, 8, затем 0, поскольку вы зацикливаете. Это означает, что первый цикл проходит, вы сдвигаете arg0 вниз на 24 бита, а затем сохраняете его в темпе.

Второй оператор является поразрядным И, который сравнивает каждый бит левой стороны с каждым соответствующим битом правой руки. Если оба бита равны 1, результирующий бит в том же положении равен 1, в противном случае - 0. Вот несколько примеров:

decimal: 7      & 15     == 7
binary:  0b0111 & 0b1111 == 0b0111

decimal: 5      & 12     == 4
binary:  0b0101 & 0b1100 == 0b0100

В ваших выражениях И выполняется с правым боковым значением 0x000000FF которое является шестнадцатеричным эквивалентом 255, в десятичной форме.

Что делают ваши два заявления, представляющие интерес, извлечения каждого "байта" или "8-битного куска" из входного arg0:

temp = arg0 >> shift;
temp = temp & 0x000000ff;

Input:  arg0 = 0x12345678, shift = 24
Output: temp = 0x12

Input:  arg0 = 0x12345678, shift = 0
Output: temp = 0x78

ДОБАВЛЕНИЕ О СЪЕМКЕ ПРАВО:

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

Арифметический сдвиг вправо:

decimal: -128                  >> 1 == -64
binary:  0b1111 1111 1000 0000 >> 1 == 0b1111 1111 1100 0000

Логический сдвиг вправо:

decimal: -128                  >> 1 == 32704
binary:  0b1111 1111 1000 0000 >> 1 == 0b0111 1111 1100 0000

Обратите внимание, как арифметический сдвиг вправо "дублирует" верхний бит, где "логический сдвиг вправо" приносит нуль. Это определенная платформа, как это интерпретируется на самом деле, поэтому старайтесь держаться подальше от нее, если это возможно, и придерживайтесь смещения целых чисел без знака.

0
temp = arg0 >> shift

Это немного смещение. Целочисленное значение arg0 будет смещено вправо по числу shift бит.

Например, если shift = 8 и arg0 = 0x1234, то temp будет назначен 0x12.

В вашем коде, если arg0 = 0x12345678 со сдвигом = 24, тогда temp становится 0x123456.

temp = temp & 0x000000ff;

Это побитовое and операция. Шестнадцатеричный номер 0x0000000ff используется для маскировки младшего значащего байта перед его передачей в byteToDec().

Итак, в последнем примере, где arg0 = 0x12345678, temp смещается 24 до = 0x123456, затем замаскировано до 0x00000056.

Что касается MIPS, то для сдвига будет использоваться инструкция Shift Right Logical Variable (SRLV)

SRLV $d, $t, $s

Где $ d - регистр назначения, $ t - регистр источника, а $ s - регистр, содержащий значение числа сдвигов. Стоит понять, что этот сдвиг вводит нули слева и изменит значение целого числа со знаком, которое является отрицательным, но поскольку применяется маска, которая применяет нули для всех, кроме наименее значимого байта, это нормально и сохранит вам некоторые инструкции.

0
temp = arg0 >> shift

Это делает двоичный сдвиг справа от содержимого arg0. Он делает это shift число раз. Так как shift = 24, он будет смещать arg0 вправо 24 раза.

temp = temp & 0x000000ff;

Это маскирует наиболее важные байты того, что содержится в temp. Последний байт остается, так как все, & "й изда с f только отражает исходное значение.

0

В этой строке

temp = arg0 >> shift;

значение arg0 смещается от большинства значащих бит к самому низкому (будьте осторожны, это может быть слева направо или справа налево зависит от сущности ЦП) в значении сдвигов (первый раз 24, затем 16, затем 8)

temp = temp & 0x000000ff;

Двоичный И применяется к темпам, т.е. Все, кроме менее значительных 8 бит, сбрасываются до 0, менее значимые 8 бит не изменяются. Если вам нужно реализовать это в сборке, вам может не понадобиться делать двоичный файл AND, но вместо этого получить правильный байт.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню