On Apr 19, 8:29 am, Frank Kotler <spamt...@[EMAIL PROTECTED]
> wrote:
> SoLo2 wrote:
> > Hello!
>
> > I have tried how simple it is to use
> > system calls in Linux from assembler.
> > Setting parameters in the registers
> > eax/edx and then "int 0x80".
>
> > I would like to know it there
> > is a similar, easy way of calling
> > other libraries (specially X windows).
>
> I don't know how "similar" you'd call it, or "easy"... but yes, we
> certainly can do that. At some point, there isn't much "advantage" to
> using asm...
>
> Might be better to start with a simpler "just call printf" example, but
> since you ask about X, I'll append a simple "hello X".
>
> > It should be as simple as giving
> > the function name in ASCII ! :)
>
> Well... it won't work in Egyptian hieroglyphics (unless you've got an
> Egyptian assembler)... I have seen stuff like:
>
> button db "button", 0
>
> ... mostly in "helper" libraries, not in Xlib itself. I don't know when
> or why we have to do that. Mostly it's just "extern XFoo"...
>
> This example links directly with ld. It strikes me that it might be
> "dangerous" to be using C library code, without linking in the C startup
> code. It "seems to work". I haven't had any trouble with it... (we *do*
> need to tell ld which interpreter/dynamic linker to use - ld gets it
> wrong by default! gcc knows...) Replace "_start" with "main", if you
> want to do it that way...
>
> I have other examples... including accessing Xwindows *without*
> libraries - just using the int 80h interface - and even examples that
> avoid using ld - creating a "ready to run" executable using Nasm's "-f
> bin" mode. How "raw" would you like to get? :)
>
> I'm replying from comp.lang.asm.x86 - I doubt if these other groups are
> interested in doing it in assembly language (or are they???). Should
> probably trim followups, at some point. There is also interest in this
> subject on the news:alt.lang.asm newsgroup...
>
> Best,
> Frank
>
> ; rudimentary "hello world" for Xwindows
>
> ; nasm -f elf -O999 x1.asm
> ; add the "-g" switch for debugging info - good luck!
> ;
> ; sorry 'bout this one...
> ; ld -o x1 x1.o -I/lib/ld-linux.so.2 -L/usr/X11R6/lib -lX11
> ;
> ; if you want it small:
> ; strip -R .comment x1
> ;
> ; after all that, we still have to tell ld where the fun begins:
>
> global _start
>
> ; inform Nasm that ld knows where to find this stuff (we hope!)
>
> extern XOpenDisplay
> extern XDefaultRootWindow
> extern XCreateSimpleWindow
> extern XNextEvent
> extern XDestroyWindow
> extern XCloseDisplay
> extern XMapRaised
> extern XSelectInput
> extern XStoreName
> extern XCreateGC
> extern XFreeGC
> extern XDrawImageString
> extern XSetForeground
> extern XSetBackground
>
> ; we'll be needing lots more of these...
>
> KeyPressMask equ 1 ; mask for XSelectInput
> KeyPress equ 2 ; the "type" of event (offset 0 in "glob of
bytes")
>
> ExposeMask equ 1 << 15
> ExposeEvent equ 12
>
> event_size equ 20h ; ??? max size of several different structs
>
> ;------------------------------------------
> section .data
> StringOpenFailed db "Can't Open X display!", 10
> StringOpenFailed_len equ $ - StringOpenFailed
>
> caption db 'A Window', 0
>
> string db ' Greetings from X, Earthling! '
> string_len equ $ - string
> ;-----------------------------------------
>
> ;-----------------------------------------
> section .bss
>
> Display resd 1
> Window resd 1
> GC resd 1
>
> event resd event_size
> ;-------------------------------------
>
> ;-------------------------------------
> section .text
>
> _start: ; let the ritual begin.
>
> ; nop ; parking place for gdb
>
> ; open a connection to the server.
> ; pu****ng 0 uses the "DISPLAY" environment variable
> ; or defaults to local machine.
>
> push 0
> call XOpenDisplay
> add esp, 4
>
> or eax, eax
> je OpenFailed
>
> mov dword [Display], eax
>
> push dword [Display]
> call XDefaultRootWindow
> add esp, 4
> ; error?
>
> push 0 ; background colour
> push 0 ; border colour
> push 0 ; border width
> push 300 ; height
> push 400 ; width
> push 50 ; top co-ord
> push 50 ; left co-ord
> push eax ; XDefaultRootWindow, from above
> push dword [Display] ; display handle
> call XCreateSimpleWindow
> add esp, 36 ; C clean-up parameters stuff
>
> or eax, eax
> je CreateFailed
>
> mov dword [Window], eax
>
> ; this is one Windows doesn't do. if we don't specify
> ; what events (messages) we want to receive, we don't get any.
>
> push KeyPressMask | ExposeMask
> ; "or" this with other events to recv!
> ; don't forget to handle 'em!
> push dword [Window]
> push dword [Display]
> call XSelectInput
> add esp, 12
> ; error?
>
> ; give the baby a name
>
> push caption
> push dword [Window]
> push dword [Display]
> call XStoreName
> add esp, 12
> ; error?
>
> ; make our window visible.
>
> push dword [Window]
> push dword [Display]
> call XMapRaised
> add esp, 8
> ; error?
>
> push 0 ; values?
> push 0 ; valuemask?
> push dword [Window]
> push dword [Display]
> call XCreateGC
> add esp, 16
> ;error?
> mov dword [GC], eax
>
> ; Mmmm, looks like 16-bit color, 5-6-5, on my machine.
> ; Bet we can't count on it!
>
> ; push 65535 ; white
> push 1111100000000000b ; red
> push dword [GC]
> push dword [Display]
> call XSetForeground
> add esp, 12
> ; error?
>
> ; push 0 ; black
> push 0000011111100000b ; green
> push dword [GC]
> push dword [Display]
> call XSetBackground
> add esp, 12
> ; error?
>
> Eventloop:
> push event
> push dword [Display]
> call XNextEvent
> add esp, 8
> ; error?
>
> cmp dword [event], ExposeEvent
> jnz not_expose
> call drawscreen
> jmp Eventloop
> not_expose:
>
> cmp dword [event], KeyPress
> jne Eventloop
>
> ; exit gracefully if key pressed
>
> push dword [GC]
> push dword [Display]
> call XFreeGC
> add esp, 8
>
> push dword [Window]
> push dword [Display]
> call XDestroyWindow
> add esp, 8
>
> CreateFailed:
> push dword [Display]
> call XCloseDisplay
> add esp, 4
> jmp Terminate
>
> OpenFailed:
> mov eax, 4 ; __NR_write
> mov ebx, 2 ; stderr
> mov ecx, StringOpenFailed ; buffer
> mov edx, StringOpenFailed_len ; count
> int 80h
>
> Terminate:
> mov eax, 1 ; function (sys_exit)
> xor ebx, ebx ; exit code
> int 80h ; make Linux system call
> ;-------------------------------------------
>
> ;-------------------------------------------
> drawscreen:
> push string_len
> push string
> push 140 ; y pos
> push 155 ; x pos
> push dword [GC]
> push dword [Window]
> push dword [Display]
> call XDrawImageString
> add esp, 28
> ; error?
> ret
> ;---------------------------------------------
Hello!
Thanks to Frank Kotler for his
excellent example of assembler
i86 and X.
[ Also Kleebauer's with the
Motorola 68millions version. ]
I would like to see that the dynamic
libraries are not very dynamic,
if the higher abstraction of using an
ASCII function name is not used.
This is the case as the compilation
of the program requires naming and
linking some "dynamic" libraries.
The program system or programmer
could use an "INT 80" with the ASCII
library name and then the interrupt
delivers the actual method pointer that
is faster to use for further calls.
Wasn't this already for Linux?
Where is this beautifull idea gone?
Java? :-)
Someone points out that there is
doubt a compiler would reach such
clean code for an X program as this
shown by Mr. Kotler.
Greetings,
H.Samso
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
http://bits.atari.org
http://biis.tripod.com
http://so_o2.tripod.com
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~


|