I have an ATMEL C project (ATmega328) in ATMEL Studio 7 and need to mix in some assembly code.
I don't want to use the C inline assembly asm() directive because I want to keep it separate as a pure assembly file.
I want to include .asm to my project, but here is the thing.
For a C project it allows me to create .s or .S files. These are apparently using a different assembler than the .asm files because in .s files commands like .inc or .equ is not recognized.
However, if I rename the .s to .asm, ATMEL Studio won't invoke the assembler (as for a pure assembly project). I guess I could solve this with the Pre-Build event to manually invoke the right assembler for the .asm files.
I can stick with .s (although I prefer the .asm) file if there was a way to include all the I/O register definitions. #include <avr/io> itself doesn't generate an error but it doesn't define anything either.
#include <avr/io.h>
.global ReadFlux
ReadFlux:
ldi r24,'#'
out TCNT0,r24
in r24,TCNT0
ret
...so TCNT0 is not known and generates an error.
I need to get the assembly version of it; m328def.inc but that one can't be found and also use .equ, not recognized by the .s assembler.
What is the proper way to setup the .s so I don't have to manually define every single IO register?
or (preferably, use the .asm instead).
EDIT
So there are two assemblers; avrasm2.exe and avr-gcc.exe with the assembler-with-cpp directive. In a pure Assembly project it seems like avrasm2.exe is used and in a C/C++ project the GNU assember is used. These 2 flawors are not working in the same way, hence the confusion.
For example with avrasm2.exe I can write like this:
out DDRB,r16
but with avr-gcc.exe I have to write it like this:
out _SFR_IO_ADDR(DDRB),r16
I think the mystery has been solved for now, but I still prefere the avrasm2.exe instead.
Related
I am getting this error when using atomthreads in cosmic c for stm8L151c6 micro controller.
clnk - symbol _archFirstThreadRestore not defined (Debug\atomkernel.o)
Ifound out that _archFirstThreadRestore is defined inside a assembler file named atomports_asm_cosmic.s linker cannot find those routines in the assembler file. How can I make linker to add the assembler file to the c code where those functions are used.
Yes got it.
I got it worked.
The problem was I have to add assembler files to the project source files. Which I didn't do.
How can I get the Watcom compiler (the forked version 2.0 beta which runs on 64-bit hosts) to output 8086 assembly source code in an ASM file? Running wcc -0 main.c from the command prompt produces just the OBJ file.
As a side note, my main task it to convert C source code to assembly code that I can run with EMU8086 (instead of writing the actual assembly code). I am hoping the ASM file generated by Watcom would run without modification (copy-paste) in EMU8086.
I don't see a way to get the Watcom compiler to generate an ASM file directly, but you should be able to use the Watcom disassembler (wdis) to generate an assembly listing from the object file produced by the compiler. In this case you would run something like wdis -l main to read main.obj and produce a file named main.lst that contains an assembly language listing.
If you recompile main.c with a -d1 or -d2 option to place extra debugging data into the main.obj file then you can use the disassembler's -s option to have the assembly language listing interpersed with comments showing the original C source from main.c.
To get the disassembler to omit descriptive comments and just give a plain disassembly that should be acceptable as a source file for the Watcom assembler, give the -a option to the disassembler. This option will also causes the disassembler's output to be written into main.asm rather than main.lst. Sorry, I have no idea whether this output will be directly consumable by EMU8086.
This is all discussed in the Open Watcom C/C++ User Guide and C/C++ Tools User Guide linked from http://www.openwatcom.com/doc.php
I'm trying to get started learning basic assembly with Paul A. Carter's book "PC Assembly Language." However I'm unable to run the first example Carter provides, so I'm kind of stuck until I figure this out.
I assembled the example "first.asm" without any problem, but I can't figure out how to link these files: first.obj, driver.c, asm_io.obj into an executable. In the comment section of first.asm Carter gives these instructions for creating an executable (I'm using Windows 10, VS community 2015 developer command prompt):
; Using MS C/C++
; nasm -f win32 first.asm
; cl first.obj driver.c asm_io.obj
I'm doing exactly that but I'm getting a fatal error 2 unresolved externals, _printf and _scanf. I have every necessary file that I can think of in the same directory, and I'm compiling in that directory.
Driver.c calls the function defined in and it uses a header file called "CDECL.h"; I have this file in my directory, but I don't understand much about this header file. I wonder if the problem is here. I haven't altered it or anything. I assembled asm_io.asm according to Dr. Carter's instructions.
Not too far into asm_io.asm is see this:
extern _scanf, _printf, _getchar, _putchar, _fputs
So here are the unresolved externals. Shouldn't they be defined in stdio.h? Driver.c includes stdio.h, shouldn't the linker be able to resolve these symbols be looking at stdio.h? What might I be missing?
ps. I'm new to programming in general, and this is my first stack overflow question. I'm open to any and all criticism/feedback. I'll provide more information if you need it, I just didn't want to post a massive wall of text and code if not necessary.
Welcome to SO. You need to understand:-
The difference between a header file, e.g.
foo.h // C or maybe C++ header file)
and a library, e.g.
foo.lib foo.dll // Windows
libfoo.a, libfoo.so // Unix/Linux
that implements the calling interface that is (merely) described in a header file.
The difference between compiling or assembling a source file, e.g.
bar.c // C source file
bar.asm // Assembly source, Windows
bar.s // Assembly source, Unix/Linux
to make an object file. e.g.
bar.obj // Windows
bar.o // Unix/Linux
and linking object files and libraries together make a complete executable.
Linking can succeed only if the linker is supplied with (or knows by default)
the names and locations of object files and/or libraries that provide
implementations of all the functions that are called in the program - including
functions whose calling interfaces are described in header files. Otherwise
unresolved symbol errors ensue.
Research these points and you'll quickly get yourself unstuck. See this
pretty good introductory tutorial, which although it is about getting
started with the GNU Compiler Collection rather
than with assembly language programming, will clarify the principles
and distinctions you need to grasp.
How do I create foo.spec files like this one from a C header file?
i.e. I'm looking for an automated way to convert all of a header file's declarations into something simple like:
stdcall CreateFileW(wstr long long ptr long long long)
which I can easily use to perform operations later.
I realize it might not be possible for some types, but it should be possible in a large number of cases.
How do I do this?
Ok, there is the tool likely used in wine project: http://www.winehq.org/docs/winedump
Intro:
winedump is a Wine tool which aims to help:
A: Reimplementing a Win32 DLL for use within Wine, or
B: Compiling a Win32 application with Winelib that uses x86 DLLs
For both tasks in order to be able to link to the Win functions some
glue code is needed. This 'glue' comes in the form of a .spec file.
The .spec file, along with some dummy code, is used to create a
Wine .so corresponding to the Windows DLL. The winebuild program
can then resolve calls made to DLL functions.
Creating a .spec file is a labour intensive task during which it is
easy to make a mistake. The idea of winedump is to automate this task
and create the majority of the support code needed for your DLL. In
addition you can have winedump create code to help you re-implement a
DLL
Spec generation mode:
Spec mode:
<dll> Use dll for input file and generate implementation code.
....
Files output in spec mode for foo.dll:
foo.spec
This is the .spec file.
foo_dll.h
foo_main.c
These are the source code files containing the minimum set
of code to build a stub DLL. The C file contains one
function, FOO_Init, which does nothing (but must be
present).
Makefile.in
This is a template for 'configure' to produce a makefile. It
is designed for a DLL that will be inserted into the Wine
source tree.
So, winedump will dump DLL interface to SPEC file. The Spec file can be additionaly edited by hand.
And the spec describes real DLL interface, not a high-level language interface (like it is encoded in .h headers). So, you can compile your code (.h and .c and maybe something like .def to fix DLL function numbers) on win32 to DLL as usual and then dump the spec from DLL.
I just started to learn masm32 and am a bit confused about the .obj files, I used C# before, so the compiler linked for me, now I have qeditor but I cant find an option to assemble multiple .asm files. I have a very basic program built of:
Vector.asm (+ Vector.inc), ...is a vector
Matrix.asm (+ Matrix.inc), ...is a matrix
Main.asm ... is the main program where I do some Vector calculations
When I compile each one of them seperate, I get 3 .obj files, what are they? I looked into the makeit.bat at the line:
\masm32\bin\PoLink /SUBSYSTEM:CONSOLE "console.obj"
so I thought I could just change it to
\masm32\bin\PoLink /SUBSYSTEM:CONSOLE "console.obj" "vector.obj" "matrix.obj"
to compile my whole program, but I was wrong :(, can anyone help me to successfully create a .bat (because maybe I want to create a little ide later, for which I would need a .bat) which compiles the 3 .obj files into 1 .exe?
I'm not familiar with PoLink, but a standard linker requires more than just a list of .obj files. It will also need to know what you intend on calling the resulting .exe (it can assume if you only give it a single .obj file). May also require an entry point. May even require library definitions if you're doing multiple files. You really need to read the docs and see what it wants on the command line...