I would prefer if it incited insight.JAAman wrote:i have done that... wrote a section in ASM, then translated it into hex -- its quite fun actually, and after a while, you find patters which give incite into the instruction-set design
quite enjoyable, although quite time-consuming also...
HEX BOOT Loader
I use GAS and have yet to find an instruction i couldnt make.crazygray wrote:It is not exactly the same, there are some instructions I haven't been able to use with an assembler. I enjoy it anyway, it's an intresting thing to do.
Author of COBOS
there are some undocumented instructions such as SALC (Set AL on Carry).
Some asm compilers don't support long jumps, dont know how its with gas.
But the real use of hex still with self modified code or doing patches to the code(which is about the same). But it'll cost you some execution speed(Pentium4 for instance invalidates several cache(code cache) lines).
Some asm compilers don't support long jumps, dont know how its with gas.
But the real use of hex still with self modified code or doing patches to the code(which is about the same). But it'll cost you some execution speed(Pentium4 for instance invalidates several cache(code cache) lines).
- Brynet-Inc
- Member
- Posts: 2426
- Joined: Tue Oct 17, 2006 9:29 pm
- Libera.chat IRC: brynet
- Location: Canada
- Contact:
Most assemblers allow you to use SALC...
With GAS you can use .byte 0xd6, YASM/NASM and FASM should all support the opcode mnemonic salc..
Later versions of GAS may support the SALC mnemonic, but I'm using the version bundled with OpenBSD.
I still don't see any benefits of writing out opcodes manually though, even assembly code is barely maintainable
With GAS you can use .byte 0xd6, YASM/NASM and FASM should all support the opcode mnemonic salc..
Later versions of GAS may support the SALC mnemonic, but I'm using the version bundled with OpenBSD.
I still don't see any benefits of writing out opcodes manually though, even assembly code is barely maintainable
not really... since there arent numbers to represent the ASM -- instead you have partial numbers, with bitfields to represent registers and methods of addressing memory -- so you dont have to memorize numbers, but patterns, and unless you are really skilled at arithmetic and binary/hex conversion in your head, you will need to do it will a calculator in your hand (or running on the computer...)
first you have a selection of override codes, then each instruction opcode can be 1,2 or 3 bytes in length (longer with certain escape codes, but those arnt common), plus some instructions will have a SIB byte, some will have a mod/rm byte, and then some will have immediate/offset/displacement data which (depending on the formation of the mod/rm & SIB bytes, and the particular instruction, can be 1, 2, 4, 6, 8, or 10 bytes -- unless there are some which require more than that...)
the overrides are easy, there are only a few of them, and they are always the same, so all you have to do is remember how they affect each instruction (some are not exactly obvious -- such as a16 affecting the size of eCX in loop instructins...)
many of the opcodes, however, contain bitfields, which must be filled in with the proper size, direction, register, etc fields, for the particular instruction
then the mod/rm byte is very complicated, with 3 bit fields, some of which change meaning based on the specific entries in other fields, and others are not permitted on specific instructions, and some instructions only use some of the fields, with the others containing instruction-specific entries -- and not all instructions have a mod/rm byte at all...
i dont have enough experience with the SIB byte to say much, but its not always there -- its presence is dependent on the specific instruction, and the entries in the mod/rm byte... and it contains more variable bitfields
then the immediate data -- this isnt present for every combination of opcode/mod/rm/SIB -- and is dependent on the specific combination of all of these to whether it is present, how large it is, how it is encoded, and what it means
in all, there are a lot of bitfields, and many contain the same information, encoded in different ways (for example, there are 2 separate bitfields for encoding segment registers -- some instructions use a 2-bit bitfield, which can only encode SS/DS/CS/ES, and others use a 3-bit bitfield which can encode SS/DS/CS/ES/FS/GS and 2 reserved combinations
so its a lot more complicated than just memorizing the opcodes...
first you have a selection of override codes, then each instruction opcode can be 1,2 or 3 bytes in length (longer with certain escape codes, but those arnt common), plus some instructions will have a SIB byte, some will have a mod/rm byte, and then some will have immediate/offset/displacement data which (depending on the formation of the mod/rm & SIB bytes, and the particular instruction, can be 1, 2, 4, 6, 8, or 10 bytes -- unless there are some which require more than that...)
the overrides are easy, there are only a few of them, and they are always the same, so all you have to do is remember how they affect each instruction (some are not exactly obvious -- such as a16 affecting the size of eCX in loop instructins...)
many of the opcodes, however, contain bitfields, which must be filled in with the proper size, direction, register, etc fields, for the particular instruction
then the mod/rm byte is very complicated, with 3 bit fields, some of which change meaning based on the specific entries in other fields, and others are not permitted on specific instructions, and some instructions only use some of the fields, with the others containing instruction-specific entries -- and not all instructions have a mod/rm byte at all...
i dont have enough experience with the SIB byte to say much, but its not always there -- its presence is dependent on the specific instruction, and the entries in the mod/rm byte... and it contains more variable bitfields
then the immediate data -- this isnt present for every combination of opcode/mod/rm/SIB -- and is dependent on the specific combination of all of these to whether it is present, how large it is, how it is encoded, and what it means
in all, there are a lot of bitfields, and many contain the same information, encoded in different ways (for example, there are 2 separate bitfields for encoding segment registers -- some instructions use a 2-bit bitfield, which can only encode SS/DS/CS/ES, and others use a 3-bit bitfield which can encode SS/DS/CS/ES/FS/GS and 2 reserved combinations
so its a lot more complicated than just memorizing the opcodes...
Actually it doesn't... (For the most part), and whomever can tell me why, I'll believe you've hand coded machine languageBrendan wrote:Hi,
something as simple as inserting a few instructions into existing code would involve searching for all CALL, JMP and branch instructions and adjusting the target addresses,
Dan K
Nice overviewJAAman wrote:not really... since there arent numbers to represent the ASM -- instead you have partial numbers, with bitfields to represent registers and methods of addressing memory -- so you dont have to memorize numbers, but patterns, and unless you are really skilled at arithmetic and binary/hex conversion in your head, you will need to do it will a calculator in your hand (or running on the computer...)
For the most part though, when coding by hand, you just remember that xor ax,ax is 31 C0, and mov cx, (byte) is b9 (byte). The bit fields are rarely if ever thought of... in fact there are referenecs that don't even mention them, they just translate every possible permutation into their hex counterpart.
It's all rather pointless though, unless you're prone to making statements like "My dad can beat up your dad", you're better off using assember, and there's really no reason not to... I mean, Every PC that's shipped with microsoft software has shipped with an assembler.... and for the opcodes it doesn't support, then you can drop back to inserting a few dbs as above.
Dan K