Задать вопрос
Ответы пользователя по тегу Assembler
  • Как найти длину массива?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    MaxSymb Db 9
    RealSymb Db ?
    StringT db 1 dup (' ')

    Здесь должно быть StringT db 9 dup (' '), иначе ввод затрёт то что там дальше в памяти лежит.

    я пытался и делать так mov cx, InBuff[0] , mov cx, InBuff[1] без разницы.

    Эти инструкции загружают 16-битный регистр из памяти, а значение длины -- 8-битное. Правильно было бы как-нибудь так: mov cl, [RealSymb]

    len equ $ - StringT - не выходит, тоже 1 выдаёт

    Это вообще определяет константу, значение которой равно разности текущего адреса и адреса StringT. Если это делать в твоей программе сразу следом за определением StringT, то 1 и получится, потому что длина StringT у тебя -- 1 байт.
    Ответ написан
    6 комментариев
  • NASM смещение в массиве (invalid effective address)?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Как в nasm можно выполнить смещение?
    [string + cx]
    invalid effective address

    дело не в ассемблере, а в устройстве процессора. x86 имеет в 16-битном режиме режим адресации "база + смещение", но базой могут выступать только регистры bx, si, di и bp. При этом di адресуется относительно сегментного регистра es, а bp адресуется относительно сегментного регистра ss.
    Это задокументировано в табличке 2-1 "16-Bit Addressing Forms with the ModR/M Byte" в томе 2А Intel Developer Manual'а, доступного, например, здесь.
    Ответ написан
  • Как сделать посекторную запись на диск?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Правильно ли я понимаю, что после того как биос загрузил загрузчик в память, тот в свою очередь должен посекторно считывать диск и загружать считанное в память.

    "Посекторно считывать диск" можно, например, понимая структуру файловой системы и читая файл с ядром ОС. Номера секторов при этом могут не идти друг за другом, а определяться какой-нибудь служебной таблицей файловой системы, например FAT. В этом случае ядро для загрузки можно будет записывать просто как файл на файловую систему.
    Ответ написан
    Комментировать
  • Есть ли у регистров адреса как у памяти?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Есть ли у регистров адреса как у памяти?

    Адреса есть (и эти адреса кодируются в инструкциях обращающихся к регистрам напрямую), но обычно не как у памяти. Наличие у регистров адресов как у памяти зависит от архитектуры. Кроме упомянутого AVR такая фича есть, например, у 8051.

    Почему нет?

    Потому что доступ к памяти и доступ к регистрам устроены сильно по-разному в серьёзных процессорах.
    Ответ написан
    Комментировать
  • Правильно ли я хочу использовать либы в ассемблере?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Это нормально так сочетать библиотеки с ассемблером?

    Вполне.
    Ответ написан
    Комментировать
  • Как правильно в регистр задать строку через at&t втроенным ассемблером?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Я вижу вот такой рабочий вариант (и при этом не уверен в том, какой порядок байт имеется в виду в оригинальной инструкции):
    movl    ((((('V' << 8) + 'M') << 8) + 'X') << 8) + 'h', %eax
    Ответ написан
  • Как перевести inline assembler в файл?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    компилятор ругается что
    mov esi, CPUInfo
    mov eax, InfoType
    undefined

    Ну правильно ругается. Это же не глобальные имена и их же нет в ассемблерном исходнике?
    Можно поправить определение функции getCpuID вот так: getCpuID PROC PUBLIC, CPUInfo, InfoType.
    И стоит прочитать вот это чтобы представлять, как параметры передаются в функции и что ещё нужно делать, чтобы всё работало.
    Ответ написан
    Комментировать
  • Почему function definition not found?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    у функии нет определения, хотя оно в asm-файле, как это можно исправить

    поменять в ассемблерном исходнике square PROC на square PROC PUBLIC.
    Убедиться, что ассемблерный исходник помпилируется и линкуется с проектом.
    Ответ написан
  • Почему не работает данная прога?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Почему не работает данная прога?

    Она на самом деле работает. Просто вывод попадает в точности на введённую строку, из-за чего непонятно, что он случился. Вот с таким изменением будет видно, что работает:

    ...
      call input
      mov dl, 0ah
      mov ah, 2
      int 21h
      call output
      ...
    Ответ написан
  • Как войти в виртуальный режим из защищенного?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    На OSDev Wiki прочитал что работать с pci невозможно из защищённого режима в котором я и "сижу".

    где именно прочитал? Прочитай внимательно ещё раз. Для взаимодействия с конфигспейсом PCI на x86 нужно использовать порты ввода/вывода 0xCF8 и 0xCFC. Через них можно настроить BARы PCI-устройства, т.е. разместить его регистры/память в физическом адресном пространстве.

    Как тогда войти в виртуальный режим?

    в какой "виртуальный" режим?
    Ответ написан
    Комментировать
  • Nasm - почему не загружается более одного сектора диска?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Загрузчик нормально работает при загрузке 1 сектора

    Вот я собрал твой загрузчик, записал его в бут-сектор, добил двумя секторами мусора и загрузил с такого диска qemu. Выглядит так, будто бы всё работает:
    $ nasm test.s -o test
    $ head -c 2b /dev/urandom >> test
    $ hexdump -Cv test | tail -n2
    000005f0  49 93 ad 56 25 97 25 82  61 1d d9 a1 66 2a cb 19  |I..V%.%.a...f*..|
    00000600
    $ qemu-system-i386 -hda test -gdb tcp::1235 -S

    В другом терминале, см этот ответ на вопрос "как в gdb посмотреть 16-битный код выполняющийся в qemu":
    $ wget https://gist.githubusercontent.com/MatanShahar/1441433e19637cf1bb46b1aa38a90815/raw/2687fb5daf60cf6aa8435efc8450d89f1ccf2205/target.xml


    Далее в том же терминале:
    $ gdb
    (gdb) set tdesc filename target.xml
    warning: A handler for the OS ABI "GNU/Linux" is not built into this configuration
    of GDB.  Attempting to continue with the default i8086 settings.
    
    (gdb) target remote :1235
    (gdb) set disassembly-flavor intel
    (gdb) b *0x7c32
    Breakpoint 2 at 0x7c32
    (gdb) c
    Continuing.
    
    Breakpoint 2, 0x00007c32 in ?? ()
    (gdb) x/2i $pc
    => 0x7c32:      int    0x13
       0x7c34:      jb     0x7c3e

    -- тут я остановился прямо перед командой чтения. Дальше:
    (gdb) tb *0x7c34
    Temporary breakpoint 3 at 0x7c34
    (gdb) c
    Continuing.
    
    Temporary breakpoint 3, 0x00007c34 in ?? ()
    (gdb) x/16x 0x13f0
    0x13f0: 0x49    0x93    0xad    0x56    0x25    0x97    0x25    0x82
    0x13f8: 0x61    0x1d    0xd9    0xa1    0x66    0x2a    0xcb    0x19

    прочитанные байты по адресу куда должен был попасть конец второго сектора совпадают со случайными данными которые я записал в конец образа диска.

    Ну и на экране всё мило, надпись "Loading kernel...." выводится, надпись "Kernel.bin not found!" не выводится.

    Но вообще, если начать придираться, то в процедуре read_sector не инициализирован dl, так что неизвестно, с какого именно устройства происходит попытка чтения в твоём неработающем случае. Можно добавить mov dl, 80h для выбора первого ЖД, для определённости.
    Ответ написан
    Комментировать
  • AT&T синтаксис доступен только GNU Assembler-y (gas)?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Как я понял GAS нельзя установить на Windows.

    Понял неправильно. Он есть и в составе mingw и в составе cygwin и несложно его кросс-компилировать под венду самому.
    Ответ написан
    Комментировать
  • Как вызвать из C++ программы функции на ассемблере?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Как вызвать из C++ программы функции на ассемблере?

    extern "C" void number1();
    …
    int main()
    {
    number1();
    }

    Именно так.
    Ответ написан
    Комментировать
  • Почему не обнуляется регистр cx?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Почему не обнуляется регистр cx?

    Сдаётся мне, ты совсем другой вопрос хочешь задать. Например, "почему подпрограмма A1 перевода строки в её числовое значение работает неправильно". Ответ на этот вопрос: потому что в следующем коде есть две ошибки:

    A1:
            push    ax
            push    cx
            push    dx
            push    di
            xor     cx, cx
    
            mov     di, 10
            mov     cx, [bx+2]

    - во-превых длина строки записана по смещению 1 в буфере, который заполняет функция 0ah прерывания 21h,
    - во-вторых, длина строки представлена одним байтом, а не словом, как ты читаешь.
    С учётом этого, код должен выглядеть вот так:
    A1:
            push    ax
            push    cx
            push    dx
            push    di
            xor     cx, cx
    
            mov     di, 10
            mov     cl, [bx+1]

    А буфер для ввода строки должен быть определён так:
    firstNum db 6,0,6 dup(?)

    Дальше, вот тут ты опять путаешь байты со словами и загружаешь в dx больше чем надо:
    .A2:
            xor     dx, dx
            mov     dx, [bx+si]
            sub     dx, '0'
            add     ax, dx

    должно быть
    .A2:
            xor     dx, dx
            mov     dl, [bx+si]
            sub     dl, '0'
            add     ax, dx


    Дальше у тебя какая-то ерунда с балансом стека:
    A1:
            push    ax
            push    cx
            push    dx
            push    di
    ...
            pop     si
            pop     di

    ты кладёшь в него одно, а снимаешь другое и в другом количестве. Но это не важно, потому что из функции A1 ты всё равно нигде не возвращаешься. Show_AX выглядит нормально.
    Ответ написан
    7 комментариев
  • Что такое Потоки на уровне ОС? В 1-ядерном процессоре же всего 1 поток?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    И К примеру выполняется такие команды, как пример инструкция чтения строки из stdin, почему вся ос не глохнет. Типа что в этот момент ожидания времени происходит, Или что ОС все 1000 потоков переключает там каждую 0.0001 секунды?

    Только готовые к выполнению потоки получают процессорное время. Потоки могут останавливаться в ожидании какого-либо примитива синхронизации, например семафора или мьютекса. Такие потоки не занимают процессор.
    Поток читающий из stdin может останавливаться, например, на семафоре, защищающем очередь данных stdin когда она пуста. Какой-то другой поток должен поместить новые данные в очередь stdin и открыть этот семафор, переведя ожидающий поток в состояние готовности к выполнению.
    Ответ написан
    Комментировать
  • Не компилится программа на ассемблере. Как исправить?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Приведённая программа -- для 32-битного ARM, ассемблер 32-битного ARM заметно отличается от ARM 64 и я не вижу у aarch64-*-as ключей которые бы говорили ему работать как 32-битный ассемблер. Ставь кросс-тулчейн для 32-битного ARM и пользуйся им.
    Ответ написан
    Комментировать
  • Ассемблер, я правильно понимаю что по умолчанию в регистрах 0x00?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    А если принять к факту, что по умолчанию в регистрах хранится значение 0x00

    Ничего в регистрах "по умолчанию" не хранится, кроме того, что в них в последний раз было записано.

    я попробовал ничего не записывать в регистр AH и вызвать прерывание 0x16, значит по умолчанию в регистре 0x00.

    Нет, это значит только то, что в этом месте твоей программы в этот раз в регистре AH был 0.

    в подпрограмме read_keyboard почему то не сохраняют регистр AX

    Потому что результат возвращают в нём.

    почему сохранили регистр BX - я не понял

    …а также cx, dx, si и di. При том, что функция 0 int 16 меняет только AX. Я думаю, что на всякий случай их сохранили, для надёжности.
    Ответ написан
    Комментировать
  • Как процессор распознает длину команды?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    как процессор может отличить длину команды (1, 2, и 3 байт), чтобы выполнить следующую команду ?

    По коду операции -- части команды, которая кодирует действие команды. В процессоре закодировано соответствие кода операции и длины команды. Код операции может полностью содержаться в первом байте команды (как в 8080), либо может быть распределён между несколькими байтами команды. В последнем случае часть кода операции находящаяся в первом байте должна отличаться от кода операции любой однобайтовой команды чтобы их можно было отличить.

    Почему кроме команды Остановить все команды занимают 3 байта?

    Если речь о 8080, то это утверждение неверно. В 8080 есть несколько однобайтовых команд (nop, битовые сдвиги и вращения, push/pop, и т.д.), несколько двухбайтовых (mvi и арифметика с непосредственными значениями -- adi, aci, и т.д.) и несколько трёхбайтовых (команды с прямой адресацией -- lda, sta, и т.д., переходы, вызовы подпрограмм и т.д.). Потому что значения, с которыми оперируют команды находятся в байтах следующих за первым -- в одном, если нужен 1-байтовый операнд и в двух если нужен 2-байтовый операнд или адрес.

    Как происходить выборка команды? Как найти логическую схему выборки команды?

    Можно посмотреть в исходники отреверсированного 8080.
    Ответ написан
    Комментировать
  • Как реализовать на с или assembler асинхронную выборку из RAM?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    Как реализовать на с или assembler асинхронную выборку из RAM?

    Например так. Это часть реализации memcpy для MIPS. Этот код не выглядит асинхронным, но написан именно так (сначала групповая загрузка в разные регистры, потом изменение базового адреса загрузки, потом групповое сохранение, потом изменение базового адреса сохранения) с рассчётом на то, что процессор сможет, в том числе, перекрыть во времени операции загрузки, арифметики и сохранения данных.
    Ответ написан
    2 комментария
  • Как происходит работа с short в asm?

    jcmvbkbc
    @jcmvbkbc
    "I'm here to consult you" © Dogbert
    00000234: xori r16,r16,32768
    00000238: addi r16,r16,-32768

    Это классическое расширение знакового бита, в данном случае для 16-битного числа: если бит 15 был установлен (число отрицательное), то после xor он будет сброшен (т.е. он и все биты старше него станут нулями), а после addi бит 15 и все старше него станут единицами. Если бит 15 был сброшен (число неотрицательное), то после xor он будет установлен, а после addi -- сброшен опять.

    Подскажите пожалуйста смысл таких преобразований?

    Знаковое расширение -- это часть short right = acum & 65535;. Оно нужно для того, чтобы работать с загруженными в регистры значениями не задумываясь об исходной ширине их типа данных. Т.е. (short)-1 в 64-битном регистре будет представлен как 0xffffffffffffffff, а не как 0xffff.
    Ответ написан
    Комментировать