flat assembler
Message board for the users of flat assembler.
![]() Goto page Previous 1, 2 |
Author |
|
Tomasz Grysztar 13 Feb 2012, 11:35
l_inc wrote: However if you make such comparison valid and returning always false for "=" and true for "<>" (I think, it's a reasonable modification) l_inc wrote: And if you still want to add an additional operator, than a better idea would be to transform a relocatable value into a non-relocatable with an operator named "fixate" or "anchor" or "settle" (i.e. just remove the relocatability flag). The "virtual" trick may allow to retrieve the value that fasm generates into opcode, but the value itself is useless if you do not know exact way of how it should be relocated to become correct one. With relocatable PE it is not a problem, but in formats like ELF there are many different relocation types and you can even specify them to add an arbitrary value to the value from code before relocating, which makes retrieval of value from opcode a very risky business. |
|||
![]() |
|
Tomasz Grysztar 13 Feb 2012, 11:58
But your proposal did give me a hint for a better operator - it should be operator that would allow to test whether two values are relative to the same base (and so that substracting one from the other would be allowed and would give absolute value in result). Again, there is a problem with inventing the time, for now let's say it would be "samebaseas" or "relativeto" - then one wouldn't need the previously discussed hypothetical operator to check whether value is relocatable, it would be enough to do:
Code: if mylabel relativeto 0 |
|||
![]() |
|
l_inc 13 Feb 2012, 13:17
Tomasz Grysztar
Quote: If you compare non-relocatable value with a simple number, it can become "true" of "false" at the runtime depending on how your code was relocated, so it is something like writing "if eax=0" and expecting assembler to give definite answer. First of all, I assume, you mean "compare a relocatable value". Because under "relocatable" I understand, that the value can be relocated (changed) at the load time. Secondly, let me explain my point about returning false. Currently in your implementation every numeric value is a tuple, which consists of the actual value and the flag "relocatable" (I'm not aware of ELF's abilities, probably it should be a tuple with the actual value and the currently computed base, if ELF's allow different code parts to be relocated asynchronously, i.e. with different deltas). A tuple is equal to another tuple if and only if all of their corresponding components are equal. Therefore it's absolutely logical to return inequality if the flag "relocatable" is not equal to the flag of the compared value. Quote: such operator would not be very useful, because it would be equivalent to saying "subtract some value I don't know from this one". That's not true. I have my overloaded implementation of display, which allows to easily display numeric values. It makes use of the following macro (to post the complete implementation would be too much code): Code: ;Displays a hexadecimal representation of a number macro dispHex num*, padding, leader, trailer { local digCount,dig,number number = num virtual dq number load number qword from $$ end virtual if number < 0 number = number + 100000000h end if digCount = 0 while 1 shl (digCount*4) <= number digCount = digCount + 1 end while if digCount = 0 digCount = 1 end if if ~ leader eq display leader end if if ~ padding eq if digCount < padding times (padding-digCount) display '0' end if end if repeat digCount dig = number shr ((digCount-%)*4) and 0Fh+'0' if dig > '9' dig = dig-'0'+('A'-10) end if display dig end repeat if ~ trailer eq display trailer end if } As you can see I make use of double reassignment: first with = and second with dq->load. This allows to display values like "$" or "$-$$" independently of the context (with or without relocations enabled), and I find it very handy, even knowing, that the actual value of "$" can be different after the image is loaded. Quote: it would be enough to do: Could you explain the functionality? Because I don't understand, why the same expression Code: $ relativeto 0 Another example of using this feature is the following: Code: ;Allows to reduce code size by replacing <push const> with <push reg> ;usage: ;BeginRegIsConst ebx,0 ; mov eax,0 ;EndRegIsConst macro BeginRegIsConst reg*,const* { local block_closed if ~ defined block_closed display 'Error: current block is not closed',13,10 rb -1 end if purge EndRegIsConst macro push [args] \{ \common \local \isconst,\buf \isconst = 0 if 0 eqtype args virtual dq args load \buf qword from $$ end virtual if \buf = const push reg \isconst = 1 end if end if if ~ \isconst push args end if \} macro mov [args] \{ \common \local \isconst,\buf \isconst = 0 match first=,second,args \\{ if 0 eqtype second virtual dq second load \buf qword from $$ end virtual if \buf = const mov first,reg \isconst = 1 end if end if \\} if ~ \isconst mov args end if \} macro pushd [args] \{ \common push args \} macro BeginRegIsConst dummy1*,dummy2* \{ display 'Error: ',`reg,' still equals ',`const,13,10 err \} macro EndRegIsConst \{ purge push,pushd,mov,BeginRegIsConst \} macro EndRegIsConst \{ EndRegIsConst purge EndRegIsConst block_closed = 1 \} } I hope, it's clear from the comments, why this code is very handy. However in this case the reassignment with dq->load is exactly, what is not desired, because the second parameter of the macro could accidentally be equal to a some relocatable value and the program will become incorrect. Therefore instead of just clearing the relocatability flag I'd need a possibility to examine it, so that I do the replacement only for the fixed numeric values, that cannot be relocated at load time. |
|||
![]() |
|
Tomasz Grysztar 13 Feb 2012, 13:56
l_inc wrote: First of all, I assume, you mean "compare a relocatable value". Because under "relocatable" I understand, that the value can be relocated (changed) at the load time. Yes, that was a typo, sorry. l_inc wrote: Secondly, let me explain my point about returning false. Currently in your implementation every numeric value is a tuple, which consists of the actual value and the flag "relocatable" Not, it is more complex than that... l_inc wrote: (I'm not aware of ELF's abilities, probably it should be a tuple with the actual value and the currently computed base, if ELF's allow different code parts to be relocated asynchronously, i.e. with different deltas) l_inc wrote: A tuple is equal to another tuple if and only if all of their corresponding components are equal. This work only one way - if all components are equal, the equality of resulting values follows. But even when they are not equal, the result values could become the same. l_inc wrote: Therefore it's absolutely logical to return inequality if the flag "relocatable" is not equal to the flag of the compared value. Not, it is not - it is like returning false when you try to compare "eax" with "0". It is not possible to determine result of such comparison at assembly time, it is a run-time construct. l_inc wrote:
This might be working out for you with relocatable PE, where there is only one possible base of relocations and thus you know what the base is (and, as I wrote in earlier post, if you know what the base is, you can just substract it). But even then when you display both absolute values and offset from base in the same way, on reading this output you may not be able to tell whether this is just some computed number (which will always be the same at run-time), or an address which can become something different at run-time. l_inc wrote:
In general, it would work like this: Code: if mylabel relativeto 0 dd mylabel xor 0xABCD ; this is just a number, I can do any computations on it else if mylabel relativeto ebp offset_in_stack = mylabel - ebp else if mylabel relativeto $ jmp mylabel ; I know this jump will never generate relocation else if mylabel relativeto some_external_array offset_in_array = mylabel - some_external_array end if |
|||
![]() |
|
revolution 13 Feb 2012, 14:04
Tomasz Grysztar wrote:
|
|||
![]() |
|
l_inc 13 Feb 2012, 14:30
Tomasz Grysztar
Quote: But even when they are not equal, the result values could become the same. I actually proposed to forget about such thing like "result values" and compute only on the basis of tuples (vectors). Then it would work both ways. And I don't see, why it would violate correctness. But if you say, the thing is more complicated in ELF's, I'll have to blindly believe it cannot be mapped to the arithmetic with vectors (may be the vector should just be extended with one or two components like "base register"?). Quote: it is like returning false when you try to compare "eax" with "0" Well, yes. So what? The returned false is in this case the compile time comparison which does not have to reflect the run time. It has never been a problem for you to compare "eax" with "0" and return false when compared with eqtype. Why? Because it's just a different type of comparison. If you want a run time comparison, you always have cmp. Quote: on reading this output you may not be able to tell whether this is just some computed number (which will always be the same at run-time), or an address which can become something different at run-time That's not a problem, as long as I'm aware of it. I just appreciate it's possible to remove the relocatability with such workaround. Quote: The "$ relativeto 0" would be false in relocatable format, and it is related to the fact that you cannot do computations like "($-0) shr 3" in such case OK. But "relativeto" is IMHO very confusing here. I find "samebaseas" better. "relativeto" means for me a kind of offset. Like "rva" is an offset from the image base. Quote:
Wouldn't you know the jump will never generate relocation without checking this? Direct near/short jumps never generate relocations. To generate a relocation it should be indirect or far. |
|||
![]() |
|
Tomasz Grysztar 13 Feb 2012, 15:27
l_inc wrote: Well, yes. So what? The returned false is in this case the compile time comparison which does not have to reflect the run time. It has never been a problem for you to compare "eax" with "0" and return false when compared with eqtype. Why? Because it's just a different type of comparison. If you want a run time comparison, you always have cmp. l_inc wrote: Wouldn't you know the jump will never generate relocation without checking this? Direct near/short jumps never generate relocations. To generate a relocation it should be indirect or far. |
|||
![]() |
|
l_inc 13 Feb 2012, 16:20
Tomasz Grysztar
Quote: fasm makes sure that values you assume to be equal are equal and there was much effort put into ensuring that in whole fasm's architectural design. OK. That's not problem for me. Thank you for the explanation. Just, please, don't remove the trick with virtual. Because I think, with 129-bit internal arithmetic I will get wrong values, when trying to do dq->load (or let's say do(from define octaword)->load). Quote: In object format jump may generate relocation - when you jump to other section, or call the external procedure. OK. Thank you for the information. I'm looking forward to be able to use the new directive. ![]() |
|||
![]() |
|
shutdownall 13 Feb 2012, 16:33
Tomasz Grysztar wrote: it would be enough to do: I like the keyword relativeto. Sounds a little bit italian like Iveco. Spaghetti carbonara et una coca cola ... ![]() |
|||
![]() |
|
l_inc 13 Feb 2012, 16:39
Oh. For that reason there should be definitely added the directive 相同的基.
|
|||
![]() |
|
LocoDelAssembly 13 Feb 2012, 16:51
LocoDelAssembly wrote: Also, would this be the first time fasm introduces a keyword composed of more than one word? Because of the paragraph above, I think relativeto, relto, basedon would be nice. |
|||
![]() |
|
l_inc 19 Feb 2012, 13:41
I don't think my opinion is going to change something (because I have already justified it before), but I still think relativeto is a very bad choise. Aside from it's large length the name is not consistent with it's commutativity property. eqbase (analogously to the here discussed eqtype) would be IMHO a much better name.
|
|||
![]() |
|
Tomasz Grysztar 19 Feb 2012, 13:56
I do not think that "relativeto" has a problem with implied non-commutativity, it is like saying two values are related to each other, they are each other's relatives. I preferred to avoid suggesting that there is some base value, perhaps sometimes there is no real base at all, only the relation of two values.
|
|||
![]() |
|
l_inc 19 Feb 2012, 15:47
Tomasz Grysztar
I thought about that explanation, and have no counterarguments. May be I'm just bound to a single understanding of an ambiguous expression. However it would be nice to see some native speakers opinions. |
|||
![]() |
|
l_inc 21 Jun 2014, 12:13
Tomasz Grysztar
No native speakers seem to have been willing to express an opinion. Thus here's my last question on that. Quote: it is like saying two values are related to each other Then why wasn't it a "relatedto"? _________________ Faith is a superposition of knowledge and fallacy |
|||
![]() |
|
Goto page Previous 1, 2 < Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2023, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.