Ru-Board.club
← Вернуться в раздел «Прикладное программирование»

» Assembler

Автор: akaGM
Дата сообщения: 20.04.2013 00:21

Цитата:
и еще можно вопросец, вот к примеру сегмент данных:
.DATA

DATA1 DW DATA2
DW DATA3
а можно весь код где определены дата2-3?
Автор: 1234567890qwe
Дата сообщения: 22.04.2013 00:45

Цитата:
весь код где определены дата2-3?

это из головы взял... а что метод их определения может как то повлиять на их объявление?

вот нашел только здесь вместо DATAх, TEMP(DATA1) и ONE(DATA2), TWO(DATA3), THREE(здесь как метки):


или вот еще здесь уже сразу как непосредственные значения, здесь вместо DATA2 и DATA3 рассматриваем непосредственные значения:
Автор: mynologin
Дата сообщения: 22.04.2013 01:58
1234567890qwe
Просто у masm такой дурацкий синтаксис. Хотели сделать с претензией на некоторую высокоуровневость, а получилась неконсистентность: иногда имя означает адрес, а иногда значение по адресу. Пользуйтесь fasm, где синтаксис более единообразный: имя (метки/переменной) — это всегда адрес, а имя в квадратных скобках — всегда значение по адресу.
Автор: ne_viens
Дата сообщения: 22.04.2013 13:01
Нормальный синтаксис:
offset metka всегда будет адрес, a dword ptr[metka] всегда будет переменная.
Кому-то просто было лень много букв писать.
Автор: 1234567890qwe
Дата сообщения: 22.04.2013 13:31

Цитата:
offset metka всегда будет адрес, a dword ptr[metka] всегда будет переменная.

я может и ошибаюсь, но это уже при определении в коде(.CODE) а в сег. данных(.DATA) так ведь не объявишь?...
Автор: ne_viens
Дата сообщения: 22.04.2013 14:16
Там тоже всё просто:
.data
metka2 dd 11223344h
metka1 dd offset metka2

Автор: 1234567890qwe
Дата сообщения: 22.04.2013 14:36

Цитата:
Там тоже всё просто:

metka1[metka2] -> metka2[11223344h] -> 11223344h
я правильно понял?
Автор: ne_viens
Дата сообщения: 22.04.2013 14:56
В переменной metka1 находится адрес метки2, а в переменной metka2- число 11223344h
Я неудачные названия выбрал- всё что в .data, это переменные.
Автор: akaGM
Дата сообщения: 22.04.2013 15:31
.data
metka2 dd 11223344h
metka1 dd offset metka2

эквивалент

.data
metka1 label dword
metka2 dd 11223344h
Автор: MERCURY127
Дата сообщения: 22.04.2013 17:06
вы таки думаете, что ему полегчало?
Автор: akaGM
Дата сообщения: 22.04.2013 17:10
по-моему, чел учится плавать в бассейне без воды...
Автор: mynologin
Дата сообщения: 22.04.2013 21:10
ne_viens

Цитата:
offset metka всегда будет адрес, a dword ptr[metka] всегда будет переменная

К сожалению, синтаксис masm достаточно контринтуитивен, чтобы этой информации было недостаточно для экстраполяции на аналогичные случаи.

Например, по аналогии можно подумать, что чтение данных с адреса, заданного числом, возможно таким образом: mov eax,dword ptr[403000h]. На самом же деле masm'у глубоко по-барабану на скобки и ptr'ы, и он и глазом не моргнув соберёт mov eax,403000h.
А как же правильно читать данные по адресу 403000h? А правильно, оказывается, так: mov eax,ds:403000h.
Мало того, даже общеупотребимое естественное правило подстановки здесь не сработает. Если принять, что offset metka, как Вы говорите, всегда равносильно адресу, то естественным заключением было бы (по аналогии с предыдущим примером), что прочитать данные с этого адреса можно таким образом: mov eax,ds:offset metka (можно даже offset metka в скобки запихать). Авотхрен. ds: будет молча проигнорировано и собрано в mov eax,offset metka .
Автор: 1234567890qwe
Дата сообщения: 22.04.2013 22:21

Цитата:
вы таки думаете, что ему полегчало?

Ок, вроде все встало на свои места(у всех видимо просто свои методы объявлений, определений и.т.п. это путаницу вносит, для меня), наверное нужно больше примеров изучать! спасибо всем, за ваши диалоги...))
Автор: Maria93
Дата сообщения: 02.05.2013 00:34
Помогите написать процедуру, выводящую на экран сумму 4-х двузначных чисел в десятичной системе счисления. Проблема в том, что сумма может быть и трёхзначной(больше 256).

После собственно сложения у меня есть массив нам из трёх элементов, в котором хранятся цифры, которыми записывается сумма. В нам[0] хранятся сотни, в нам[1] - десятки, в нам[2] - единицы. А как дальше делать? Я написала так, но это не работает:


Код:
MOV AH, 0
MOV AL, NUM[0]; вносим в AL цифру сотен
MOV BL, 100;
MUL BL; умножаем на 100
MOV DX, AX; записываем в DX ответ
MOV AL, NUM[1]
MOV BL, 10
MUL BL; то же самое с десятками
ADD DX, AX; складываем сотни с десятками
MOV AL, NUM[2]
MOV AH, 0
ADD DX, AX; складываем всё

Автор: Zarkon06
Дата сообщения: 02.05.2013 01:44
Maria93
Примерно так (если пишем под DOS):

Код:
...
mov ah, 2 ; функция вывода символа
mov dl, NUM[0]
add dl, 30h ; первый символ
int 21h
mov dl, NUM[1]
add dl, 30h ; второй символ
int 21h
mov dl, NUM[2]
add dl, 30h ; третий символ
int 21h
mov ax, 4c00h
int 21h
Автор: Maria93
Дата сообщения: 03.05.2013 18:49
Zarkon06, большое спасибо. А если бы я всё-таки хотела получить настоящее число, чтобы с ним работать дальше?
Автор: bomzzz
Дата сообщения: 03.05.2013 19:51
оно и есть настоящее
Автор: mozillafox777
Дата сообщения: 10.06.2013 21:44
Как переслать содержимое регистра AX в восьмой элемент третьей строки двумерного массива??
Автор: ne_viens
Дата сообщения: 10.06.2013 22:45
.686
.model flat, stdcall
option casemap:none

.data?
_arr word 12 dup (12 dup (?)) ;array 12x12 words

.code
start:
mov ax, 666h
mov ecx, 8
mov edx, 3
lea edx, [edx*2 + edx]
lea edx, [edx*4 + ecx] ;3*12 + 8

mov _arr[edx*2], ax ;_arr + (3*12 + 8)*2
ret
END start
Автор: MihaNix
Дата сообщения: 21.06.2013 16:23
Задание было такое:
Пусть в сегменте кодов определена строковая переменная с помощью команды DB 'Personal Computer'. Напишите программу преобразующую строчные буквы данного слова в заглавные и наоборот, и записывающую результат в сегменте данных по смещению 0;
Все написали подобно этому:
mov ax,70
mov [0],ax
mov ax,65
mov [1],ax
mov ax,72
mov [2],ax
mov ax,73
mov [3],ax
mov ax,6f
mov [4],ax
mov ax,6e
mov [5],ax
mov ax,61
mov [6],ax
mov ax,6c
mov [7],ax
mov cx,8
mov bx,0
mov ax,[bx]
sub ax,20
mov [bx],ax
inc bx
loop 36
nop

Вопрос возник - почему не работает такое:

mov ax,7065
mov [0],ax
mov ax,7273
mov [1],ax
mov ax,6f6e
mov [2],ax
mov ax,616c
mov [3],ax
mov cx,4
mov bx,0
mov ax,[bx]
sub ax,2020
mov [bx],ax
inc bx
loop 1e
nop

В чем ошибка?
Хотел схалявить - столько инструкций в дебагере не вводить и в итоге нерабочую программу получил.
Автор: Abs62
Дата сообщения: 21.06.2013 17:38
MihaNix

Цитата:
В чем ошибка?

А посмотреть в отладчике, что и куда пишется с таким алгоритмом, не судьба?
Сразу стало бы ясно, что если пишешь сразу по два байта, а не по одному, то и адрес надо увеличивать не на единицу, а на двойку.
Автор: kkuuhhaa
Дата сообщения: 15.12.2013 20:59
Растолкуйте пожалуйста с адресацией (профессор, я учил). Надо поменять порядок байт в большом количестве.
int kol; // количество чисел для swap
char *mem;
__asm
{mov cx,kol
loop:
mov eax,mem
bswap eax
mov mem,eax
loop loop
}
Как здесь перейти к следующему числу? (VS10)
Автор: ne_viens
Дата сообщения: 15.12.2013 21:38
Для этого есть intrinsic ф-я, ассемблер тут лишний:

for(j = 0; j < kol; ++j)
arr[j] = _byteswap_ulong(arr[j]);
Автор: kkuuhhaa
Дата сообщения: 15.12.2013 22:11
ne_viens
эт знаю, но оно работает вроде как медленнее, надо переводить в ulong
Автор: ne_viens
Дата сообщения: 15.12.2013 22:35
Оно работает быстрее, так как не нарушает оптимизацию кода,
в отличии от asm вставки:

__asm {
mov ecx, OFFSET mem
xor eax, eax
L0:
mov edx, [ecx+eax*4]
bswap edx
mov [ecx+eax*4], edx
add eax, 1
cmp eax, kol
jb L0
}
Автор: akaGM
Дата сообщения: 16.12.2013 00:24
ne_viens

а точно
add eax, 1
одинаково по скорости с
inc eax ?
Автор: ne_viens
Дата сообщения: 16.12.2013 07:53
По Фогу (Agner Fog) add быстрее но больше места занимает.
Да и на грабли можно наступить, так как inc немодифицирует C флаг.

Забыл align в примере:
;...
align 16
L0:
;...
Автор: kkuuhhaa
Дата сообщения: 16.12.2013 08:26
ne_viens
Со вставкой, пожалуй, ваша правда. Но тогда надо это оформить подпрограммой. Но тут опять пробелы у меня
.globl swapLong
swapLong:
??? Откуда брать параметры?
mov ecx, OFFSET mem
....

ret
Может проще разбить на пару потоков?
Автор: ne_viens
Дата сообщения: 16.12.2013 10:08
////////////////////////////////////////////////////////////////////////////////////////
__declspec(inline) void invertEndian(int* mem, int len)
{
    __asm {
        mov ecx, mem
        xor eax, eax
align 16
L0:
        mov edx, [ecx+eax*4]
        bswap edx
        mov [ecx+eax*4], edx
        add eax, 1
        cmp eax, len
        jb L0
    }
}

int _mem[] = {0x11223344, 0x55667788, 0x99aabbcc, 0xddeeff00};
////////////////////////////////////////////////////////////////////////////////////////
main()
{
    invertEndian(_mem, sizeof(_mem) / 4);
}


Но советую всё-таки пользоватся интринсиком в форе- мороки меньше, код быстрее и портабельнее (на x64, например) будет.
Автор: JFK2005
Дата сообщения: 02.03.2014 02:48
Подходящей темы не нашёл. Вопрос из разряда "знал, да забыл".

Обязательно ли нужно добавлять релокейшены для 32-битных exe-файлов, которые запускаются под Windows Vista/7/8 ?

В этих системах есть механизм ASLR (Address Space Layout Randomization). То есть, по идее, при загрузке кода в память может быть выбран случайный адрес, и все абсолютные смещения придут в негодность. Какой флаг в заголовке exe задает принудительную загрузку по фиксированному адресу?

Например. Есть у нас exe-файл, одна из функций которого находится по абсолютному адресу 0x1589798. При загрузке exe по фиксированному значению адрес функции не изменится. Если бы это был не exe, а dll (которые могут грузиться по любому адресу), выделенные значения байтов изменились бы согласно релокейшену. Всегда ли необходимо прописывать релокейшены и для exe-файлов, если они запускаются под ОС выше Windows XP?


Страницы: 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384

Предыдущая тема: .NET GUI компоненты


Форум Ru-Board.club — поднят 15-09-2016 числа. Цель - сохранить наследие старого Ru-Board, истории становления российского интернета. Сделано для людей.