Qword ptr ассемблер что это
Что делает операция PTR
Что означает ptr в строке byte ptr[si],al
Что означает ptr в строке byte ptr,al Вот весь код, может понадобится Преобразование двоичного.
Что такое qword ptr gs
Есть инструкция jmp qword ptr gs: Каким образом мне понять куда она прыгает (конкретный.
Что означает mov byte ptr ds:[1], ‘b’?
Здравствуйте, обьясните пожалуйста фрагмент кода. mov byte ptr ds:, ‘a’ mov byte ptr.
Что за адрес в MOV EAX,DWORD PTR DS:[10008234]
Занимаюсь дизассемблированием одной софтинки в ollydbg. Встретилась такая команда MOV EAX,DWORD.
в последнем случае произходит обращение к процедуре с назначением типа ближнего обращения
Добавлено через 14 минут
p.s. кстати, по поводу полученного значения в первичном примере, все равно непонятно почему 3004h. Что это, смещение в сегменте данных, указывающее на второй операнд? И какой тип определен значением 03h?
Мдя. Первоапрельский троллинг не удался.:cry:
на правах оффтопа
это не страшно, всегда можно текущую дату сдвинуть в право на разницу между ней и 1ым апреля, и попробовать еще раз )))
и все же, как же по теме?) почему именно 3004h?
Сорри за глупый вопрос, что есть FPC? поиск на форуме ничего не дал (
Добавлено через 48 минут
в общем, в примере «$2» от «2» ничем не отличается в результате, и это точно не идентификатор переменной, поскольку вставленный впереди оператор
Добавлено через 42 минуты
странно, среди списка дизассемблеров нет отладчика OllyDbg
Добавлено через 7 минут
в отладчик не лазил, лень , видимо 3004h это адрес в сегменте данных, по которому лежат данные о типе и значении данных, я так это понял из темы, всем еще раз спасибо за участие)
значение операнда : результат:
0h : 0000h 0000 0000 0000 0000
1h : 0400h 0000 0100 0000 0000
2h : 3004h 0011 0000 0000 0100
3h : 3030h 0011 0000 0011 0000
4h : 3030h 0011 0000 0011 0000
5h : 3030h 0011 0000 0011 0000
6h : 0430h 0000 0100 0011 0000
7h : 3004h 0011 0000 0000 0100
8h : 3030h 0011 0000 0011 0000
9h : 3030h 0011 0000 0011 0000
Ah : 3130h 0011 0001 0011 0000
Bh : 0431h 0000 0100 0011 0001
Ch : 3004h 0011 0000 0000 0100
Dh : 3030h 0011 0000 0011 0000
Eh : 3130h 0011 0001 0011 0000
Fh : 3031h 0011 0000 0011 0001
вот такие интересные результаты) отмечу лишь, что их природа довольно не линейна;
мое резюме: возможно «косяк» Борланда, хотя я к ним отношусь с большим пиететом; но возможно и есть какое то объяснение, о понимании которого я чего-то не знаю.
Добавлено через 51 минуту
0! Интересный момент. Задал тип явно, с WORD вроде все понятно, результат как и раньше, но когда поставил BYTE, пришлось указать байт регистра; отрывок кода:
What does qword ptr [hexvalue] mean without a base register
I was debugging CLR code in assembly, and got to a line
I think qword ptr [ff4053c0h] refers to a string I’m interested in, but ff4053c0h is not a valid memory location. Reading about qword ptr it seems to reference an address based on a base register (e.g. qword ptr [rsp+30h] is 30 bytes into the stack), but I can’t find what it means with no base register.
3 Answers 3
When no base register is provided, it means data segment (http://www.osdata.com/system/physical/memory.htm). In your code, mov rax, qword ptr [ff4053c0h] means «take 8 bytes from data segment offset FF4053C0h and put them in RAX».
As you are pointing correctly, the presence of a base register like rsp clearly indicates stack segment. In your case, no base register means data segment.
Now, about the big number «FF4053C0h», which is «4 282 405 824», it’s perfectly possible to have 4Gb of addressable memory (http://wiki.osdev.org/Protected_Mode), which confirms that your line of code might be valid and it’s accessing offset FF4053C0h in a huge data segment (http://www.ece.unm.edu/
Without complicating the things for no good reason:
The address must be valid, check again.
The QWORD PTR is just a size specifier (redundant here, but it improves readability), it is not related with having a base register.
If you really are interested into the various addressing modes the CPU have, you can read the Intel Manuals (Google that).
You are moving a 64bit value from memory into the rax register. The value is read from the address ff4053c0h. qword ptr is a hint for the assembler to create a move op-code (machine code) using a 64bit constant address. The value that is provided is a 32bit value (8 hex-digits => 8 times a hex-digit/letter => 8 * 4bits => 32bit).
There are move op-codes that support 32bit operations but (most likely check the specs for the CPU/Mode) not for loading memory into a 64bit register. So qword is needed to ensure the assembler you really want to express a 64bit address.
For your comment about the address pointing to undefined memory (see comments for acepted answer), understand that nowadays every process has a virtual memory table assigned. Virtual memory basically maps a logical address to an address in real memory. It prevents processes from seeing and altering memory that does not belong to the process, providing a great deal of stability to a running system.
Having two processes both sharing a portion of memory, it is possible that each individual process see the very same physical memory at different logical addresses. The operating system decides what the virtual memory of each process looks like.
The mapping is provided on a per page level (e.g. page=4KB) and the processor does the actual mapping internally.
This concept is very true for mapping files to memory and sharing the memory between different processes. This way you can map a 2GB file into memory and have 10 processes concurrently working with the very same mapped file while only (at most) 2GB actual memory is consumed. It is the way file io-caching is mostly done on the OS-level.
Директивы Ассемблера
Группа директив для указания типа процессора
Директивы указания типа процессора задают набор используемых инструкций.
Директивы для указания сегментов
Директива SEGMENT
Определяет сегмент с заданным именем name. Если сегмент с таким именем уже был определен ранее, то данный сегмент интерпретируется как продолжение предыдущего.
BYTE | выравнивание не выполняется. Сегмент может начинаться с любого адреса памяти |
WORD | выравнивание на границу слова (2 байта) |
DWORD | выравнивание на границу двойного слова (4 байта) |
PARA | выравнивание по границе параграфа (16 байт). Используется по-умолчанию. |
PAGE | выравнивание на границу в 256 байт |
USE16 | сегмент с 16-разрядной адресацией. Максимальный размер сегмента 64 Кб |
USE32 | сегмент с 32-разрядной адресацией. Максимальный размер сегмента 4 Гб. В модели памяти FLAT используется по-умолчанию |
Директива ENDS
Определяет конец сегмента.
Директива ASSUME
Задает сегментный регистр, который будет использоваться для вычисления действующего адреса для всех меток и переменных, определенных для сегмента или группы сегментов с указанным именем.
Директивы для упрощенного указания сегментов
Директива .MODEL
Задает модель памяти для упрощенных директив определения сегментов.
C | Аргументы передаются через стек, справа налево. Стек очищает вызывающая программа. |
PASCAL, BASIC | Аргументы передаются через стек, слева направо. Стек очищает вызываемая подпрограмма. |
STDCALL | Аргументы передаются через стек, справа налево. Стек очищает вызываемая подпрограмма. |
Директива .CODE или CODESEG
Определяет начало сегмента кода. Если задали среднюю или большую модель памяти, то за директивой может следовать необязательное имя, которое указывает имя сегмента. По-умолчанию имя сегмента _TEXT.
Директива .DATA или DATASEG
Определяет начало инициализированного сегмента данных.
Директива .DATA?
Определяет в модуле начало неинициализированного сегмента данных.
Директива .CONST
Определяет начало сегмента данных-констант.
Сегменты .DATA, .DATA?, .CONST помещаются в одну группу с именем DGROUP
Директива .STACK или STACK
Определяет начало сегмента стека, выделяя количество байт, заданное параметром. Если размер не указывается, выделяется 1024 байт.
Группа директив для резервирования памяти
Резервирует область памяти, заданного директивой размера, с указанным именем, и инициализирует значением выражения. Выражение может быть числом, строкой символов, специальным символом «?«, а также выражением с использованием директивы DUP.
Повторяет операцию выделения памяти для указанных данных столько раз, сколько задано значением счетчика
Директива STRUC (STRUCT)
Определяет структуру данных с заданным именем, содержащую поля. В каждом поле для определения его размера используются обычные директивы выделения данных (DB, DW и т.д.). Поля структуры могут быть именованными или нет.
Директива ENDS
Определяет конец структуры.
Директива UNION
Группа директив модификации размера указателей
Используются когда возникает неоднозначность в размере операнда команды. Например когда в ячейку памяти записывается число, то компилятор не может определить число какого размера требуется записать, и в этом случае требуется укзать директиву модификации размера.
Директивы определения процедур
Директива PROC
Определяет начало процедуры с указанным именем.
Директива ENDP
Определяет окончание процедуры
Директива USES
Показывает, какие регистры или элементы данных, состоящие из одной лексемы, вы хотите занести в стек в начале охватывающей процедуры. Перед возвратом управления из процедуры эти регистры будут извлекаться из стека. Вы должны использовать эту директиву перед первой инструкцией, которая генерирует в процедуре реальный код.
Директива LOCAL
В процедуре директива LOCAL определяет имена, которые доступны в стеке через отрицательные смещения относительно регистра BP. Если указан идентификатор, то ему присваивается количество байт, выделенных на локальные переменные (размер всего блока локальных переменных в байтах).
Директивы для макроопределений
Директива MACRO
Определяет начало макроопределения с указанным именем. У макроопредения могут быть заданы необязательные параметры, которые будут использоваться при подстановке тела макроопределения в текст программы.
Директива ENDM
Определяет окончание макроопределения
Директива REPT
Повторяет блок операторов, заданный между директивами REPT и ENDM столько раз, сколько задается выражением. Блок операторов должен заканчиваться директивой ENDM.
Директива IRP
Повторяет блок операторов, заданный между директивой IRP и ENDM со строковой подстановкой. Аргументами может быть любой текст: символы, строки, числа и т.д. Для каждого указанного аргумента ассемблирование блока операторов выполняется только один раз. При каждом ассемблировании блока для каждого вхождения «параметра» в операторах подставляется следующий аргумент в списке.
Другие директивы
Директива COMMENT
Позволяет задать многострочный комментарий, ограниченный с начала и с конца заданным символом-ограничителем.
Директива EQU
Определяет имя как строку, псевдоним или число, содержащие результат вычисления выражения.
Директива END
Отмечает конец исполняемого модуля и задает начальный адрес, с которого будет исполняться программа.
Директива EVEN
Округляет счетчик адреса до следующего четного адреса
Директива SEG
Возвращается адрес сегмента выражения со ссылкой на память
Директива OFFSET
Возвращает смещение выражения в текущем сегменте (или в группе, которой принадлежит сегмент, если используются упрощенные директивы определения сегментов).
Директива ORG
Устанавливает счетчик инструкций в текущем сегменте в соответствии с адресом, задаваемым выражением.
Директива RADIX
Задает основание системы счисления для целочисленных констант (2, 8, 10 или 16)
Директива SIZE
Возвращает размер элемента данных, выделенного для переменной
Операнды в языке ассемблера
Операнд – объект, над которым выполняется машинная команда.
Операнды ассемблера описываются выражениями с числовыми и текстовыми константами, метками и идентификаторами переменных с использованием знаков операций и некоторых зарезервированных слов.
Операнды могут комбинироваться с арифметическими, логическими, побитовыми и атрибутивными операторами для расчета некоторого значения или определения ячейки памяти, на которую будет воздействовать данная команда или директива.
Способы адресации операндов
Под способами адресации понимаются существующие способы задания адреса хранения операндов:
Операнд задается на микропрограммном уровне (операнд по умолчанию): в этом случае команда явно не содержит операнда, алгоритм выполнения команды использует некоторые объекты по умолчанию (регистры, признаки и т.д.).
Операнд задается в самой команде (непосредственный операнд): операнд является частью кода команды. Для хранения такого операнда в команде выделяется поле длиной до 32 бит. Непосредственный операнд может быть только вторым операндом (источником). Операнд-получатель может находиться либо в памяти, либо в регистре.
Операнд находится в одном из регистров (регистровый операнд): в коде команды указываются именами регистров. В качестве регистров могут использоваться:
Прямая адресация : эффективный адрес определяется непосредственно полем смещения машинной команды, которое может иметь размер 8, 16 или 32 бита.
Косвенная адресация в свою очередь имеет следующие виды:
Косвенная базовая (регистровая) адресация. При такой адресации эффективный адрес операнда может находиться в любом из регистров общего назначения, кроме sp/esp и bp/ebp (это специфические регистры для работы с сегментом стека). Синтаксически в команде этот режим адресации выражается заключением имени регистра в квадратные скобки [].
Данный способ адресации позволяет динамически назначить адрес операнда для некоторой машинной команды и применяется при организации циклических вычислений и при работе со структурами данных, массивами.
Косвенная базовая (регистровая) адресация со смещением предназначена для доступа к данным с известным смещением относительно некоторого базового адреса, используется для доступа к элементам структур, когда смещение элементов известно заранее, на стадии разработки программы, а базовый (начальный) адрес структуры должен вычисляться динамически, на стадии выполнения программы. Модификация содержимого базового регистра позволяет обратиться к одноименным элементам различных экземпляров однотипных структур данных.
Косвенная индексная адресация. Для формирования эффективного адреса используется один из регистров общего назначения, но обладает возможностью масштабирования содержимого индексного регистра.
Значение эффективного адреса второго операнда вычисляется выражением mas+( esi *4) и представляет собой смещение относительно начала сегмента данных.
Наличие возможности масштабирования существенно помогает в решении проблемы индексации при условии, что размер элементов массива постоянен и составляет 1, 2, 4 или 8 байт.
Данный вид адресации также может использоваться со смещением.
Косвенная базовая индексная адресация. Эффективный адрес формируется как сумма содержимого двух регистров общего назначения: базового и индексного. В качестве этих регистров могут применяться любые регистры общего назначения, при этом часто используется масштабирование содержимого индексного регистра.
В случае использования косвенной базовой индексной адресация со смещением эффективный адрес формируется как сумма трех составляющих: cодержимого базового регистра, cодержимого индексного регистра и значения поля смещения в команде.
При использовании подобного выражения для перехода нельзя забывать о длине самой команды, в которой это выражение используется, так как значение счетчика адреса соответствует смещению в сегменте кода данной, а не следующей за ней команды. В приведенном выше примере команда jmp занимает 2 байта. Длина этой и некоторых других команд может зависит от того, какие в ней используются операнды. Команда с регистровыми операндами будет короче команды, один из операндов которой расположен в памяти. В большинстве случаев эту информацию можно получить, зная формат машинной команды.
Операторы в языке ассемблера
Операнды являются элементарными компонентами, из которых формируется часть машинной команды, обозначающая объекты, над которыми выполняется операция. В более общем случае операнды могут входить как составные части в более сложные образования, называемые выражениями . Выражения представляют собой комбинации операндов и операторов , рассматриваемые как единое целое. Результатом вычисления выражения может быть адрес некоторой ячейки памяти или некоторое константное (абсолютное) значение.
Выполнение операторов ассемблера при вычислении выражений осуществляется в соответствии с их приоритетами. Операции с одинаковыми приоритетами выполняются последовательно слева направо. Изменение порядка выполнения возможно путем расстановки круглых скобок, которые имеют наивысший приоритет.
Характеристика основных операторов.
Операторы сдвига выполняют сдвиг выражения на указанное количество разрядов. Например,
Операторы сравнения (возвращают значение истина или ложь) предназначены для формирования логических выражений. Логическое значение истина соответствует логической единице, а ложь – логическому нулю. Логическая единица – значение бита равное 1, логический ноль – значение бита, равное 0.
Назначение операторов сравнения приведено в таблице
Оператор | Условие |
eq | == |
ne | != |
lt | |
ge | >= |
Логические операторы выполняют над выражениями побитовые операции. Выражения должны быть константными. Например,
Индексный оператор [ ]. Транслятор воспринимает наличие квадратных скобок как указание сложить значение выражения за [] со значением выражения, заключенным в скобки. Например,
Наличие индексного оператора указывает транслятору, что необходимо получить значение по вычисленному адресу.
Оператор переопределения типа ptr применяется для переопределения или уточнения типа метки или переменной, определяемых выражением. Тип может принимать одно из следующих значений.
Тип | Пояснение | Назначение |
byte | 1 байт | переменная |
word | 2 байта | переменная |
dword | 4 байта | переменная |
qword | 8 байт | переменная |
tword | 10 байт | переменная |
near | ближний указатель | функция |
far | дальний указатель | функция |
В примере для сравнения значения по адресу esi с константой необходимо явно указать, данные какого типа будут сравниваться.
Оператор переопределения сегмента : (двоеточие) вычисляет физический адрес относительно конкретно задаваемой сегментной составляющей, в качестве которой могут выступать:
Оператор именования типа структуры . (точка) также заставляет транслятор производить определенные вычисления, если встречается в выражении.
Оператор получения сегментной составляющей адреса выражения seg возвращает физический адрес сегмента для выражения, в качестве которого могут выступать метка, переменная, имя сегмента, имя группы или некоторое символическое имя.
Оператор получения смещения выражения offset позволяет получить значение смещения выражения в байтах относительно начала того сегмента, в котором выражение определено. Например,
Оператор type возвращает число байтов, соответствующее определению указанной переменной:
Оператор width возвращает размер в битах объекта типа RECORD или его поля.