Ccmath library:
http://freecode.com/projects/ccmath
It does not specify 32/64 bit in description, but when I compile on Ubuntu 10.10 64 bit it spits out error on asm-file compilling:
solv.s:13: Error: invalid instruction suffix for `push'
code line: pushl %ebp
But if I replace cc shell instruction for gcc -m32 its all OK!
However, can I compile it on x86-64? I have to link this to 64bit project.
That ccmath package looks like it hasn't been updated since 2001. Its assembly routines are not 64-bit capable. You should run the included non_intel.sh script as instructed in the INSTALL file. (As far as this package is concerned, x86-64 is non-intel because "intel" means "x86-32".)
Related
I have a prepared a minimal Cmake project containing one cpp file which represent the main and one cpp file which represent the shared library, that prints basically hello world.
https://github.com/courteous/wasmELF.git
The target is to compile this miniaml code with emscripten/clang only and produce
1) one WebAssembly (wasm) binary module version 0x1 (MVP)
2) one ELF 64-bit LSB
without clearing the cmake build directory and rebuilding it again.
Currently i can successfully produce them bought by running the commands
emconfigure cmake ../ -DCMAKE_BUILD_TYPE=WASM
make
and
cmake ../ -DCMAKE_BUILD_TYPE=Linux
make
However the problem is that in order to do that i need to compile the first one with Clang the to remove the build and then to do a second compilation with GCC. I would like Emscripten/Clang to produce them bought instead. I do not want to delete the build directory since the compilation times is taking too long. (Well not in this Project but imagine if the project was much larger)
What i see is that emscripten/clang selects always a target "wasm32-unknown-emscripten"
clang++ -target wasm32-unknown-emscripten
and if i understand that correctly the target should change
I do see that the project is producing LLVM IR bitcode since i have send the flag "flto"
i.e.
file TestSharedClass.cpp.o
TestSharedClass.cpp.o: LLVM IR bitcode
and in the CMakeLists.txt
set(CMAKE_CXX_FLAGS "-flto")
x86_64-unknown-linux-gnu is a supported target by emscripten/Clang
~/Projects/emscripten/emsdk/upstream/bin$ ./llc --version
LLVM (http://llvm.org/):
LLVM version 11.0.0git
Optimized build with assertions.
Default target: x86_64-unknown-linux-gnu
Host CPU: haswell
Registered Targets:
wasm32 - WebAssembly 32-bit
wasm64 - WebAssembly 64-bit
x86 - 32-bit X86: Pentium-Pro and above
x86-64 - 64-bit X86: EM64T and AMD64
In cmake i do have
SET(TARGET x86_64-unknown-linux-gnu)
however when i run
emconfigure cmake ../ -DCMAKE_BUILD_TYPE=Linux
make
i get mainTestFile.js and mainTestFile.wasm instead of ELF 64-bitcode.
what i am doing wrong here. How to tell clang to product once ELF and once wasm from the same code run without having to clear the build directory. This should be possible since clang is producing LLVM IR bitcode. Or do i understand that wrong?
https://github.com/emscripten-core/emscripten/issues/10361
OK that seems to not be possible i.e. the reply from the dev on github states that emcc or emmake can not be used with another target other then wasm32-unknown-emscripten.
I want to read data from a file in assembly AT&T but I don't really know where to start.
I haven't found a useful resource on internet.
My working environment info:
OS: Ubuntu 14 - 64 bit
CPU: Intel
GAS compiler
Assembly Sintax: AT&T
I'll assemble with: as -o hello.o hello.s
I'll link with: ld -o test hello.o
Look up how to do systems programming on POSIX in C (open/read/write/etc.), then use the same system calls in your asm. There's nothing special about asm for this, compared to just doing it in C. (except that in C you'd be using the glibc wrappers instead of the syscall instruction directly.)
See the x86 tag wiki for links documenting how to make system calls from asm.
Can someone explain the difference between the three architectures?
Actually when I built a 64-bit application in Linux, I got a link error saying:
skipping incompatible library.a when searching for library.a
Then I used objdump -f on that library and I got the below output:
a.o: file format elf32-x86-64
architecture: i386:x64-32, flags 0x00000011:
HAS_RELOC, HAS_SYMS
start address 0x00000000
Does it mean the library is 32-bit? Is that the reason I am getting the linker error?
There are 3 common ABIs usable on standard Intel-compatible machines (not Itanium).
The classic 32-bit architecture, often called "x86" for short, which has triples like i[3-6]86-linux-gnu. Registers and pointers are both 32 bits.
The 64-bit extension originally from AMD, often called "amd64" for short, which has GNU triple of x86_64-linux-gnu. Registers and pointers are both 64 bits.
The new "x32" ABI, with a triple of x86_64-linux-gnux32. Registers are 64 bits, but pointers are only 32 bits, saving a lot of memory in pointer-heavy workflows. It also ensures all the other 64-bit only processor features are available.
Each of the above has its on system call interface, own ld.so, own complete set of libraries, etc. But it is possible to run all 3 on the same kernel.
On Linux, their loaders are:
% objdump -f /lib/ld-linux.so.2 /lib64/ld-linux-x86-64.so.2 /libx32/ld-linux-x32.so.2
/lib/ld-linux.so.2: file format elf32-i386
architecture: i386, flags 0x00000150:
HAS_SYMS, DYNAMIC, D_PAGED
start address 0x00000a90
/lib64/ld-linux-x86-64.so.2: file format elf64-x86-64
architecture: i386:x86-64, flags 0x00000150:
HAS_SYMS, DYNAMIC, D_PAGED
start address 0x0000000000000c90
/libx32/ld-linux-x32.so.2: file format elf32-x86-64
architecture: i386:x64-32, flags 0x00000150:
HAS_SYMS, DYNAMIC, D_PAGED
start address 0x00000960
Now, if you're getting the message about "skipping incompatible library", that means something is messed up with your configuration. Make sure you don't have bad variables in the environment or passed on the command line, or files installed outside of your package manager's control.
Beyond usual full 64bit and good old 32bit ABI there is a special ABI (inspired by SGI n32 envirnment) where pointers are 32bit (thus they are 32bit apps), but it is designed to run on 64bit host and have full access to all x64 goodies:
native x64 registers and math
more registers
SSE2/3/4, AVX1/2/...
Full 4Gb address space on 64bit host
It is called x32 ABI, link: https://en.wikipedia.org/wiki/X32_ABI
UPDATE
On Ubuntu system I have to install two packages (with deps) to get x32 working:
> sudo apt install gcc-multilib
> sudo apt install libx32stdc++-5-dev
Then compiling simlple C++ code with g++ -mx32 hellow.cpp works, making x32 executable
> file a.out
./a.out: ELF 32-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /libx32/ld-linux-x32.so.2, for GNU/Linux 3.4.0
Trying to learn NASM Assembly. I have a 64-bit machine, with Ubuntu. Recently I decided to test the push and pop instructions. I do this:
nasm -felf64 Test.asm
Apparently they are not supported in 64-bit mode. Alright, no problem, I'll just do it for 32 then:
nasm -felf Test.asm
And now, as always,
gcc Test.o
But it now tells me
i386 architecture of input file 'Test.o' is incompatible with i386:x86-64 output
I don't quite grasp the error here. How can I test push and pop in my 64-bit machine, if apparently I can't compile 32-bit programs?
How about "-m32"?
And I think you need to care dependent library(e.g libc), see: Use 32bit shared library from 64bit application?
First, you can use push and pop in 64-bit code, just not with 32-bit registers. If you push and pop 64-bit registers, it'll work fine. In most cases, you can use 32-bit registers in 64-bit code, just not push and pop. There may be other exceptions, but I'm not aware of 'em.
64-bit code uses different system call numbers, puts the parameters in different registers, and uses syscall instead of int 0x80. However, the old int 0x80 interface with the old system call numbers and parameters in the old registers still works. This gives you kind of "mixed" code and may not be a Good Idea, but it works. How long it will continue to work in future kernels is anybody's guess. You may be better off to learn "proper" 64-bit code.
But there are (still!) a lot more 32-bit examples out there. You can tell Nasm -f elf32 (just -f elf is an alias, but I'd use the "full name" just for clarity). If you're using gcc, tell it -m32. If you're using ld directly, tell it -m elf_i386. You do have choices, but they have to be compatible with each other.
how about the "-march=i386" ? see:
http://gcc.gnu.org/onlinedocs/gcc/i386-and-x86_002d64-Options.html
What is the best way to compile programs with DMD on a 64bit machine? It doesn't need to compile to 64Bit code. I know about GDC, but want to work with D2 also. There is also chroot, but am hoping for a simpler way.
The actual problem isn't with compiling, but linking. DMD calls on GCC to perform linking with system libraries. Could I get DMD to have GCC link against 32bit library? Or how would I do it manually?
I already have the ia32 libraries installed which is why I can run DMD.
Ask GCC to perform 32-bit link by passing it '-m32' flag.
It appears that DMD doesn't invoke gcc to perform the link, but rather invokes ld directly. The equivalent ld switch is '-melf_i386', and apparently the way to make DMD pass that option to the linker is with '-L-melf_i386' flag.
Note that many systems separate runtime and development libraries. 32-bit runtime packages are almost always installed by default, but 32-bit development packages may not be.
You need development 32-bit packages to build 32-bit programs. The fact that 32-bit DMD can run does not in itself prove that you have all the 32-bit libraries you need in order to build 32-bit programs.