mene mene tekel
I have nasm code successfully compiles to a win32 DLL. Now, I habe to provide this code on a Linux Shared Library (they call it a .so file) to be accessed by a tomcat application server (32 bit). OK, I have no glue about Linux. From the nasm manual I learnt about sections (instead of segments) and nasm -elf produces a .o object file (would be enough for me, also) but it did not run on the Linux server - link problems. Perhaps, it has to do with this suff arround GOT - but is completey unclear to me. All nasm examples generate .out executables, doesn't help me.
Unfortunately, I've no Linux available to test some stuff by myself.
If it's not big thing it would be great if somebody could post a code example i.e. a function "giveback" taking an Int32 argument and giving it back again like
_StdCall Int32 giveback(Int32 number)
This entry point giveback should be exposed by the resulting .o object file and the nasm.exe and alink.exe command line commands to generate this .o from the .asm would be helpful, also.
(please, no gcc usage, I don't have any Linux tool available on my win32 computer, I can use nasm.exe and alink.exe, only)
Many thanks for help,
Nasm.exe will produce ELF linkable object files, regardless of what OS it's running on. Alink.exe, however, has *no* idea how to make a shared object out of it. You're SOL on that score. Fergeddiit!
It "should" be possible to compile ld to run under Windows as a "cross linker". Good luck, even if you use gcc... "should" be possible even with whatever non-gcc compiler you're using... says right in the glossy brochure that C is portable, right?
I sympathize with your position. *I* can't (won't, I should say) test anything on Windows. However, as it happens, I've got more versions of ld than you can shake a stick at. I've seen an example of a "simple" shared library. I seem to recall that the command line to ld involves "--shared". We've gotta move our gem to some directory mentioned in /etc/ldconf and then do ldconfig to "activate" it.
However, there's more to it than that. Unless I'm mistaken, the difference between a PE and a .dll is that the latter has a relocation section. An .so, AFAIK, does not have a relocation section and must be position independent code. "GOT" and friends are supposed to assist in this... I'm afraid I don't "get" how to use 'em...
If you had a friend who was running Linux, say fbkotler at users.sf.net or at verizon.net... you might be able to get him to run your code past ld and report back what the error message was, at least...
(incidentally, "segment" and "section" are exact aliases to Nasm. There are differences - *big* differences - between Windows and Linux, but this ain't one of 'em)
P.S. You can use a "live CD" to test stuff under Linux, without having to "install" it...
mene mene tekel
Thanks for your fast response - made me sure that the problem is not our .o from nasm. You are right, I can generate an ELF linkable object. When I compile i.e. this example code
bits 32 ;32bit code
%define pObj ebp+12 ;jobject = UInt32
%define pEnv ebp+8 ;JNIEnv = UInt32
mov ebp, esp
mov eax, dword 7 ;Return 7
mov esp, ebp
.rtn ret 4*2
with the -felf32 option. I then have a .o we can use on the Linux server to link a .so library using ld!
(the two extra arguments JNIEnv and jobject are necessary for the Java JNI interface - forget about it, here)
OK, but tomcat could not link our .so ...
Reason for that, we found out now: the Linux name of the library *must* start with the prefix 'lib'!
LOL - omitting the .so extension is ok is some way, but having to name rtnSeven.so as libRtnSeven.so ...
I will remember that next time a Linux guy blame me that Microsoft identifies files by their extensions ;-)
But, seriously, when I take a look into the .o generated by nasm with the editor, I see some "strange" things:
1. The .o contains *all* labels used in the .asm file, in the above example two labels:
regardless of the global instruction stating that only rtnSeven should be exposed! Every label is exposed! This makes no sense, isn't it?
2. When I define variables (labels) in the .data section, same with those labels: *all* present in the .o!
3. The .o contains *all* equ definitions from the file, even regardless whether they are used or not in the code. This means, when I have an include file with some definitions like
NULL equ 0x00000000
TRUE equ 0x00000001
FALSE equ 0x00000000
then the .o file exposes i.e. a 'label' named NULL or at least the .o file cares a parameter name NULL. But shouldn't NULL be replaced with 0x0000000 by the preprocessor and so will never occur in a library? At least nasm behaves like that when generating .obj files for PE!
Because I have a lot of such equates they blow up the resulting .o especially those of them never used in the code!
Can that behavior be correct?
00006d0: 6d00 5452 5545 0046 414c 5345 004e 554c m.TRUE.FALSE.NUL <-- equ used in code
00006e0: 4c00 444c 4c5f 5052 4f43 4553 535f 4445 L.DLL_PROCESS_DE
00006f0: 5441 4348 0044 4c4c 5f50 524f 4345 5353 TACH.DLL_PROCESS <-- equ never used in code
0000700: 5f41 5454 4143 4800 444c 4c5f 5448 5245 _ATTACH.DLL_THRE
0000710: 4144 5f41 5454 4143 4800 444c 4c5f 5448 AD_ATTACH.DLL_TH
0000720: 5245 4144 5f44 4554 4143 4800 7056 6572 READ_DETACH.pVer <-- .data section labels
0000730: 7369 6f6e 0075 4b65 7956 616c 7565 0064 sion.uKeyValue.d
0000740: 4375 746f 6666 5800 6443 7574 6f66 6659 CutoffX.dCutoffY
I use "The Netwide Assembler 0.99.05"
Would be great you could help to make my (now working) .o libs more perfect.
mene mene tekel
Hi, me again!
no response so far? Hmmm... ok, did I miss a simple "-s strip option" or something like that to eliminate all these useless equates and labels from the elf .o lib? Or is it an (un)known problem with the nasm.exe -felf32 ?
I feel not good with all my local label names in my .o lib ... Nobody an idea how to make the "global/extern" mechanism working correctly - just like in nasm.exe -fobj?
AFAIK, Nasm follows the ELF specification. You can use the "-s" switch - to ld, not Nasm - to remove unneeded cruft - or "strip -R.comment myfile" works good... but that's *after* Nasm has done its work.
AFAIK, "global" and "extern" *do* work as intended. ELF is different from OMF. That isn't really a "problem"...
You can look at the Manual, "ELF extensions to the 'global' directive", for "hidden", but I don't think it'll do what you want. I'm afraid the only way to eliminate the useless symbols is to eliminate the useless symbols...
thanks, that's the way it works:
Only global declared symbols remain in the .o
That's what I wanted to have!
I put Martin's program into demolib.asm, and compiled it with:
nasm -f elf32 demolib.o demolib.asm
Then wrote a program demo.asm to call rtnSeven:
nasm -f elf32 -demo.o demo.asm
ld -s -o aout demo.o demolib.o
Segmentation fault (core dumped)
I'm using ubuntu 7, nasm 2.05.01, why this error occured? are there any examples show how to create a linux shared library and call its function in other asm module?
"_start" doesn't get called. (apparently just jumped to) The first thing on the stack will be the command line parameter count. So "ret" is going to try to execute code at... probably 1, unless you gave it parameters. Segfault!
After the "call rtnSeven", the "result" (7, we hope) should be in eax. We probably want it in ebx for an "error code" to return to the system...
mov ebx, eax
mov eax, 1 ; __NR_exit
... now you should be able to see the result by "echo $?"
There's a shared lib example, "libsimple", from "seadhurt"(?) in the "files" section of the !Yahoo! linux-nasm-users group. Here, I'll "liberate" it for us:
This is quite a simple example, as the name indicates, but it'll give us something to start with.
I've lost track of it, but I had another example from Robin Miyagi (from linuxassembly.org)... Here it is! "pic-asm". My recollection was that I never got this to work without segfaulting, but... it works now! (???) Same place:
Whups! Typo in that second URL...
Thanks very much!
I'd really appreciate if you made it for ELF64 as well. I've been trying to make my code work in Ubuntu 8.10 x64 for several days now ;(
I'll begin the port immediately upon receipt of the 64-bit machine you send me. :)
Seriously, I'm glad you reminded me... That's Robin Miyagi's code, not mine. What I've got for a makefile - possibly modified from Robin's original - doesn't actually link as a shared library - links (via gcc) directly with textio.so. However, I did get it to work by linking with ld -o test test.o -I/lib/ld-linux.so.2 -ltextio -L/usr/local/lib (I *think* that's what I did) I'm going to have to look into it more...
But 64-bit code is a whole different ballgame! I have *no* idea how you'd do a shared library. What have you tried?
> I'd really appreciate if you made it for ELF64 as well...
Here's the simple code of my test library:
const_shift: dd 1, 2, 3, 4
; int __cdecl transform_em64(unsigned int * buf)
movdqu xmm0, [rcx]
paddd xmm0, [rel const_shift]
movdqu [rcx], xmm0
This works for Win64 (nasm 2.05, VS2005 SP1) but for Linux64 (nasm 2.03.01, gcc 4.3.2) I get all sorts of errors: "panic: intra-segment OUT_REL4ADR", floating point exception (when tried to use GOT code from nasm manual), etc.
Please suggest correct code.
Thanks a lot
Okay... I'm reading messages "out-of-order"... or perhaps my brain is out-of-order...
Nasm 2.03.01 does complain about this code. The latest snapshot - 20090105 from http://www.nasm.us - seems to like it okay. I'm not able to try linking/running it, but it assembles without error...
See if that helps...
Yeah, 2.06rc2 works nicely (with rdi instead of rcx, that was Win64 code). Thanks a lot