[ASM] Resources for Assembly

Started by
6 comments, last by zyrolasting 14 years ago
My level of experience with Assembly is nil. I want to bite the bullet and write my first assembly programs, but there are some details I am having trouble figuring out. I have three computers in the room, and they all have different processors. What do I need to find out from each one of them (and other computers in the future) to determine what assembler and instruction set I need?
Advertisement
Most computers you'd have around are x86 based. That is most your windows machiens on a AMD Athlon, AMD Phenom, Intel Pentium, Intel CORE, Intel Atom. And the newer Macs. And most linux machines you might have around (though linux runs on everything, so even your router could have linux on it).

The exceptions would be an old Mac, XBox, or PS3. All of those would be PowerPC variants. Or the PSP's R4000 variant. These use MIPS assembly like instructions.


So, you'd want to be looking up x86 assembly probably. BUT before you start down that path, I'd suggest something like SPIM to emulate a MIPS assembly machine if you don't have one to play with.
x86 is kinda a stack machine based assembly, where MIPS is a more register centric assembly. I personally find MIPS assembly easier to understand, and defiantly easier to debug. If you really like it and want more, you can also get OS161, which is an educational operating system and MIPS hardware emulator. That will let you dive into assembly to finish off a full operating system.
in case you're using visual studio, visual c++ comes with inline assembly support for x86:
unsigned int i=0;__asm {	mov eax, i	add eax, 42	mov i, eax}::std::cout << "ASM: " << i << "\n";


this saves you the trouble of setting up an additional toolchain for compiling assembly code.
Quote:Original post by zyrolasting
My level of experience with Assembly is nil. I want to bite the bullet and write my first assembly programs, but there are some details I am having trouble figuring out. I have three computers in the room, and they all have different processors. What do I need to find out from each one of them (and other computers in the future) to determine what assembler and instruction set I need?


If any of your machines is an x86, then I'm really getting along well with this tutorial. It also mentions how to use the code on a number of operating systems and compilers (the 'setup code' is written in C). I found this to be really useful. The only prerequisite is that you know a little bit of C.

It's a free PDF but to support the author I also bought the hardcopy edition. However, I would stick with the PDF as some of the content is very close to the page margin, meaning it gets lost in the spine in the printed version.
Quote:Original post by ComicSansMS
in case you're using visual studio, visual c++ comes with inline assembly support for x86:
*** Source Snippet Removed ***

this saves you the trouble of setting up an additional toolchain for compiling assembly code.


Obligatory:

Quote:Jan: Very interesting, thanks :)

Now we only miss some MSVC dumps. Anyone?



Quote:Original post by Ftn
I think, at least for MSVC, the compiler wont analyze inline assembly blocks.


Indeed, MSVC-Inline-Assembly-Syntax means that assembler-blocks are black boxes to the compiler, forbidding quite a lot of possible optimizations and introducing overhead. MSVC also does not support x64/amd64 architecture.

Quote:MSVC Inline Assembly
Inline assembly is not supported on the Itanium and x64 processors.
[...]
The presence of an __asm block in a function affects optimization in several ways. First, the compiler doesn't try to optimize the __asm block itself. What you write in assembly language is exactly what you get. Second, the presence of an __asm block affects register variable storage. The compiler avoids enregistering variables across an __asm block if the register's contents would be changed by the __asm block. Finally, some other function-wide optimizations will be affected by the inclusion of assembly language in a function.


Quote:Visual C++ Team Blog
[...]
* Inline asm is not supported by Visual C++ on 64-bit machines. Therefore, if you want your code to be 64-bit compatible, you need to use intrinsics.
* The [MSVC] optimizer does not work well with inline asm code, so it is recommended that you write inline asm code in its own function, assemble it, and link it in. With the intrinsics, those additional steps are not necessary.


Important note: Above comments were about MSVC.

Quote:plug plug
You shouldn't use inline assembler when there are intrinsics.

Further, in Microsoft's Compiler, every block of inline assembly is a blackbox to the compiler, effectively meaning that you lose a lot of optimisations around and inside the block of inline assembly, because there's no way in MSVC to tell the compiler about clobbered registers and dependencies on certain variables. AFAIR, you even lose the ability to let the compiler inline your function.

Furthermore, Microsoft's Compiler does not have an inline assembler on 64bit targets.

Sidenote: Using inline assembler in GCC is generally a braindead approach, too, because the compiler has probably more experience in optimisation than most human lifes. But if you are a assembler wizard, you can use it, as GCC intermixes your assembler with the rest of the code. There, even the order of assembly instructions may change drastically, and some of your assembly might even be folded away thanks to CSE, inlining, unrolling, etc.. All that thanks to constrains.



Quote:plug plug plug
Quote:Original post by Matt_D
do you have access to any intrinsics, as inline ASM will cause gcc to dump the current register state to stack in order to let you run inline ASM


I think not. GCC's constraints system is specifically to let the compiler know which registers and variables you will clobber, and whether you need specific registers or let the compiler decide which register to use. You can even delegate the decision whether you need a register at all to the compiler.

And you better not lie as GCC will generally schedule your assembly and make it part of the overall optimization process. It is even possible that GCC will transform your assembler completely away.

That is, as long as you don't put a "volatile" onto your inline assembly, like in the original post.

On MSVC, of course, inline assembler is
A) not possible on amd64 (aka x64, aka x86-64)
B) a major obstacle for the optimizer, as there your assembly is really a blackbox

Quote:, and then load its state back, alongside that the optimizer will most likely do a better job than you will :)

if you can use intrinsics, particularly SIMD ones, use those instead :)


Sure he has access to intrinsics, and not only x86/amd64 ones, but also for AltiVec, ARM, etc., he's on GCC. And thanks to this, he even has inline assembler on AMD64 and many other targets [smile]
Thank you for the very informative posts! I'm trying something right now.
Learning assembly is one part learning the instruction set and one part learning the system architecture.

Something that took me a while to figure out is that the assembly code is tied only to your CPU -- not to the rest of your computer. Much of the black magic that goes on in your tower has more to do with the other hardware components onboard, like the PIC and the various data buses.

Try writing some simple C code and disassemble it. It's a fun way to learn tricks your compiler uses. Both Visual Studio and gcc have the ability to show you the assembly code your program compiles to (although gcc uses a slightly modified syntax). It's all the same though.

You could also try learning bytecode for a virtual machine instead, such as Java bytecode for the JVM. Java bytecode looks and smells like assembly, but it's a little cleaner. (x86 assembly dates back to a time when people wrote everything in assembly, and it shows....)

If you want a really, really simple assembly code to learn, check out the z80 processor. The z80 is a 8-bit processor that is used in lots of your favorite childhood electronics: TI calculators and gaming consoles. The z80 is still used for a cheap embeddable CPU. It's instruction set is very simple compared to x86.

When you get familiar with the concepts of assembly, you could even try writing a very simple bytecode language and virtual machine. You need a way to load constant integers, do arithmetic, load and store integers to memory, compare, do conditional and unconditional jumps, and call and return from functions. A very simple virtual machine might take a hundred lines of code to write. A simple assembler might take a few hundred.

[Edited by - Tac-Tics on April 1, 2010 1:22:01 PM]
Quote:Something that took me a while to figure out is that the assembly code is tied only to your CPU -- not to the rest of your computer. Much of the black magic that goes on in your tower has more to do with the other hardware components onboard, like the PIC and the various data buses.


What about drivers? There has to be low level code for communicating with other devices. If ASM is CPU bound, where does firmware come in?

This topic is closed to new replies.

Advertisement