· Начало · Отвђтить · Статистика · Поиск · FAQ · Правила · Установки · Язык · Выход · WASM.RU · Noir.Ru ·

 WASM Phorum —› WASM.ASSEMBLER —› улучшение макроса

. 1 . 2 . 3 . >>

Посл.отвђт Сообщенiе


Дата: Июл 14, 2004 13:15:40

Я, абсолютно не ориентируясь в написании макросов, написал следуюший макрос:

_if MACRO p
invoke p
.if eax!=0
endm

_endif MACRO
.endif
endm

Ну и пользую его примерно так:

_if <GetDlgItemText,hWin,psw_str,addr buff,255>
;чего-то делаем с текстом
_endif

Как избавится от скобок? Нужно разбирать VARARG и ручками пушить всё кроме первого? Или может у кого-нибудь есть макрос получше?


Дата: Июл 15, 2004 19:09:08

Дык, тебе надобно указать все передаваемые парамметры.

_if MACRO p,a,s,d,f,g,h
invoke p,a,s,d,f,g,h
.if eax!=0
endm
_endif MACRO
.endif
endm


Дата: Июл 16, 2004 15:48:36

Дык параметров для разных функций разное количество.


Дата: Июл 16, 2004 23:13:45 · Поправил: Asterix

__Ranger
Пишем макрос:
$invoke MACRO vars:VARARG
     invoke vars
     EXITM <eax>
ENDM


После этого возможна следующая запись:
.IF $invoke(GetModuleHandle, NULL) == 0
  .........
.ELSE
  .........
.ENDIF

Или такая:
.IF !($invoke(GetModuleHandle, NULL))
  .........
.ELSE
  .........
.ENDIF


p.s. S_T_A_S_, в fasm'е возможен такой макрос? ;-)


Дата: Июл 17, 2004 01:51:57

Понятно. Не в ту сторону думал.


Дата: Июл 17, 2004 10:13:38

Asterix > „в fasm'е возможен такой макрос?“

Макрофункций там как таковых нет, но подобные вещи делать можно:
	mov	[.WC.hCursor],	invoke	LoadCursor,ebx,IDC_ARROW

Я сейчас думаю над тем, что бы invoke из подобных выражений совсем убрать :)


Дата: Июл 17, 2004 10:49:02

S_T_A_S_
Что-то у меня не получается, а так можно?
mov ebx, invoke LoadCursor, ebx, IDC_ARROW

что-то у меня fasm ругается..


Дата: Июл 17, 2004 12:01:58

Asterix

Это из-за того, что у тебя mov обычный.
Надо переопределить его как макрос:
invoke	equ	; это должно быть перед определением макроса invoke
include '%fasminc%\win32a.inc' 

macro	mov	destination, [source]
{
common	if _#source eq _invoke source
		source
		if ~ destination eq eax
			mov	destination, eax
		end if
	else
		mov	destination, source
	end if
}

mov ebx, invoke LoadCursor, ebx, IDC_ARROW
Тут есть ещё некоторая оптимизация, что бы не генерировался код:
mov eax, eax


ЗЫ
Когда-нибудь возможно свёже доделаю нормальную библиотеку макросов и примеры, а пока можно высказывать пожелания :).


Дата: Июл 17, 2004 12:19:42 · Поправил: Asterix

S_T_A_S_
Мда.., и после этого ты утверждаешь что fasm лучше masm'а, смотри каким маленьким макросом решается эта проблема в masm и как сложно в fasm ;-)

ЗЫ: я задал этот вопрос на board/flatassembler дабы сподвигнуть Privalov'а на добавление такой же возможности в FASM которая есть в masm и реализуется таким простым макросом, но пока видимо я не очень убедителен =)


Дата: Июл 17, 2004 14:09:23

Asterix

Дык пусть такая маленькая проблема решается маленьким макросом на MASM и несколько большим на FASM.
Но как (точнее возможно ли) сделать на MASM это:

ExitProcess 0
?

Я не имею ввиду тупо определять макрос для каждой API'шной и своей функции вручную, а переложить эту работу на транслятор.


invoke, вложенные один в другой вроде:
mov OldEditProc, $invoke(SetWindowLong, invoke(GetDlgItem, hWnd, IDC_EDIT1),GWL_WNDPROC, OFFSET SubclassEditProc)
тоже можно делать на FASM, это позволяют мои старые инклуды:
move OldEditProc, <invoke SetWindowLong, <invoke GetDlgItem, hWnd, IDC_EDIT1>,GWL_WNDPROC, SubclassEditProc>

Так что imho Privalov не будет ничего менять.
У FASM просто "несколько" отличная от MASM идеология макроязыка, но реально можно очень много - вплоть до переопределения каждой мнемоники.
Я уж не говорю про полный контроль за PE форматом :)


Дата: Июл 17, 2004 17:46:17

ExitProcess 0

Такое точно нельзя.

mov OldEditProc, $invoke(SetWindowLong, $invoke(GetDlgItem, hWnd, IDC_EDIT1),GWL_WNDPROC, OFFSET SubclassEditProc)

а такое легко. Только надо добавить проверку, чтоб eax после вложенных $invoke не использовался.


Дата: Июл 17, 2004 22:06:53 · Поправил: Asterix

S_T_A_S_
> Но как (точнее возможно ли) сделать на MASM это:
ExitProcess 0


Я вроде видел такой макрос на board.win32asmcommunity.net , но там кажется было так ExitProcess, 0 что imho не очень плохо ;-)

> тоже можно делать на FASM, это позволяют мои старые инклуды

Это опять же только в случае использования расширенной команды mov ?

> Так что imho Privalov не будет ничего менять.
У FASM просто "несколько" отличная от MASM идеология макроязыка


Не будет, но я этого не понимаю, причем тут идеология, нужно добавить эту возможность а программист пусть сам решает использовать ему или нет.

Four-F
> а такое легко. Только надо добавить проверку, чтоб eax после вложенных $invoke не использовался.

Какую проверку и куда добавить, это я что с такой записью могу нарваться на косяк?


Дата: Июл 18, 2004 00:10:34

mov bla, $invoke(func1, $invoke(func2, par1), eax)
раскроется в такое:
push par1
call func2
push eax     ; но тут уже совсем не то, что было до вызова всей цепочки !
push eax     ; то, что вернула func2
call func1
mov bla, eax

В общем случае нельзя использовать eax во внешнем вызове и addr соответственно тоже. Это макрос и должен проверить, но это непросто :)

Я у ся в макросах примерно так делаю:
IF reax                        ;; if eax was used report error
    IFIDNI <Entry>, <eax>
        line TEXTEQU %@Line
        % ECHO @FileCur(line) : ERROR! Register value overwritten by XXX macro.
        .ERR
    ENDIF           
ENDIF


Подробнее можно глянуть в cocomac или в KmdKit.


Дата: Июл 18, 2004 03:21:03 · Поправил: Asterix

Four-F
> Подробнее можно глянуть в cocomac или в KmdKit.

Я что-то не нахожу там, тот макрос($invoke) что я приводил выше есть в cocomac в одном из примеров, но он никак не увязан с проверкой на eax, или может есть другая более расширенная версия этого макроса?

А так я для себя уяснил, что нужно осторожно использовать eax при вложенных $invoke(), а также ADDR и всё будет нормально ;-)


Дата: Июл 18, 2004 11:38:15

Asterix > „Я вроде видел такой макрос на board.win32asmcommunity.net“

Дык Four-F же говорит - нельзя. Значит нельзя :).

> „Это опять же только в случае использования расширенной команды mov ? “

Да.

> „причем тут идеология, нужно добавить эту возможность а программист пусть сам решает использовать ему или нет. “

В таком случае придётся сильно переделывать FASM, что может повлечь за собой проблемы с backward compatibility.
К тому же, всё это достижимо уже имеющимися средствами, просто подход не такой, как в MASM.


Four-F > „mov bla, $invoke(func1, $invoke(func2, par1), eax) - раскроется в такое..“

Хм.. Действительно непростой случай - тут опять нужно писать свой макрос для invoke.

В FASM у меня раскладывалось так:
mov bla, invoke func1, <invoke func2, par1>, eax

push eax   ; аргумент для func1
push par1
call func2
push eax   ; то, что вернула func2
call func1
mov bla, eax

Проверка на изменения EAX всё одно делалась, но это нужно для таких случаев:

mov bla, invoke func1, EAX, <invoke func2, par1>

Здесь очевидно выхода никакого нет, кроме хитрых манипуляций со стеком..
imho это уже перебор - размер команд будет слишком велик, а производимый код не очевиден.

. 1 . 2 . 3 . >>


Powered by miniBB 1.6 © 2001-2002
Время загрузки страницы (сек.): 0.094