Some C compilers (gcc, for example) allow programmers to mix inline assembly instructions with C instructions using asm blocks.
For example, assume c1 ... c8 are C instructions and a1 ... a6 are assembly language instructions, here are several styles of asm blocks:
c1;
c2;
asm("a1");
c3;
c4;
asm("a2 \n\t a3");
c5;
c6;
asm("a4 \n\t"
"a5 \n\t"
"a6");
c7;
c8;
The control characters "\n\t" are necessary to make sure each assembly language instruction starts on its own line with a tab space indentation to make it more readable.
The file demo1.c contains a simple C program.
Let's analyze the gcc command:
gcc –S –masm=intel –o demo1.s demo1.c
Ordinarily compiling is a three stage pipeline:
1. execute pre-processing directives (like #include)
2. translate pre-processed C to asssembly
3. translate assembly to machine code
The –S option says top after stage 2.
The –o option says to name the output file demo1.s
The –masm=intel option says to assume asm blocks will contain 80x86 instructions in Intel syntax rather than AT&T syntax.
Take a look at demo1.s. Note that the asm block is inserted as:
/APP
push eax
mov eax, _x
add eax, 1
mov _x, eax
pop eax
/NO_APP
Note that after translation the global variable x is renamed _x and the global function main is renamed _main.
Note that I save the registers on the stack that I intend to use (eax in this case), then restore them when I'm done.
The command:
gcc –masm=intel –o demo1.exe demo1.c
generates an executable demo1.exe file.
Here are two useful scripts for compiling and assembling:
(Note: these are actually html files. Save them as bat files.)
Strip off the .c extension to use them:
asm demo1
cc demo1
A particularly useful way to write inline assembly is to place the asm blocks in a separate "helper" function.
In demo2.c the main function is a useful read-eval-print loop written in pure C. The helper function, inc_x, contains the asm block.
Microsoft Visual Studio also supports inline assembly. In fact, their syntax is much better. For example, the asm block in demo2.c looks like this in Visual Studio:
void inc_x()
{
_asm {
push eax
mov eax, x
add eax, 1
mov x, eax
pop eax
};
}
The gcc that comes with the Mac OS takes the same sort of asm blocks that work with Visual Studio (see above). But to compile, you must turn on the switch that allows inline assembly:
gcc –fasm-blocks –o demo1 demo1.c
To run in a BASH shell you need to type:
./demo1
If this doesn't work, try starting your asm block with:
".intel_syntax noprefix \n\t"
Don't bother putting underscores in front of globals.
If you have Linux, then relax, it comes with gcc already installed.
If you have Windows, then there are several options:
1. Download Cygwin, a Linux-like environment for Windows that includes a bash shell and gcc.
2. Download MinGw, the Minimalist GNU for Windows. This includes gcc and has any easy installer.
3. Download djgpp, a complete development environment for DOS/I80386 that includes gcc. This involves downloading several large files.
Of course there are other C compilers that support asm blocks besides gcc, although asm blocks are part of the C standard.
If you want to work in DOC, go for options 2 or 3, if you want to work in (learn) bash, go for option 1.
There are several gcc compilers for Mac OSX. For example:
http://sourceforge.net/projects/gdcmac
The complete documentation for the GNU compiler collection can be found at:
http://gcc.gnu.org/onlinedocs/gcc-4.4.0/gcc/
There are lots of C tutorials. For example:
http://www.geocities.com/SiliconValley/Software/5562/
http://www.cs.cornell.edu/courses/cs414/2001SP/tutorials/cforjava.htm
Here's a convenient listing of the C library:
http://www.acm.uiuc.edu/webmonkeys/book/c_guide/