www.main.lv

Don't think just code it

Menu

  • Projects
    • Robatik
    • ArpSni
  • Samples
    • FreeBSD Asm
    • Linux Asm
    • PyGame Tutorial
    • UNIX programming
    • PSP programming
    • AVR
    • Math
  • Contact

Tags

algo (1)asm (19)attractor (2)avr (2)blender (3)bug (1)c (25)coalision (2)debug (3)editor (1)elf (1)fractals (2)freebsd (3)game (3)generator (1)gimp (1)int80h (22)map (1)math (5)mit (1)nano (1)net (2)opengl (1)plugin (1)post (2)povray (1)psp (3)pygame (19)python (28)robatik (2)sdl (3)skype (2)sql (1)towers (2)tutorial (7)voronoi (1)wudu (1)

Archive

  • 2010 august (1)
  • 2010 july (2)
  • 2010 june (1)
  • 2010 april (2)
  • 2010 march (2)
  • 2010 february (2)
  • 2010 january (2)
  • 2009 december (3)
  • 2009 november (8)
  • 2009 october (3)
  • 2009 september (5)
  • 2009 august (1)
  • 2009 july (1)
  • 2009 june (1)
  • 2009 may (1)
  • 2009 april (3)
  • 2009 march (1)
  • 2009 february (2)
  • 2009 january (1)
  • 2008 october (2)
  • 2008 september (4)

2009-04-07 FreeBSD assembler

I like assembler as it is very simple to learn but you should know how works your HardWare.

At this moment on my computer I have FreeBSD7.1. That whay i will write some examples about assembler for FreeBSD. With some little modifications that code also can be launched on Linux machines. Ou I forget assembler will oriented on Intel architecture. Don't forget AMD also understand Intel commands.




Tools
Simple programm
Hello world
Hello world + libc
C + asm
Links where is somthing useful

Files

Open File


2009-10-24 Making C executables smaller

There are some simple things that can be done to make C executables as small as possible.


Here is some example code we will work with:
#include <SDL/SDL.h>
 
char quit = 0;
 
int main()
{
    SDL_Surface *screen,surface;
    SDL_Event e;
    SDL_Init( SDL_INIT_VIDEO );
    screen = SDL_SetVideoMode( 400, 400, 32, SDL_SWSURFACE );
    while(!quit)
        while(SDL_PollEvent(&e)>0)
        {
            if(e.type==SDL_MOUSEBUTTONDOWN) quit=1;
            if(e.type==SDL_KEYDOWN) quit=1;
        }
    SDL_Quit();
}

Compile: gcc main.c -o main -lSDL

Size before: 5326 bytes


Execute command: strip main

strip
is included in most unix systems. It deletes some info symbols from executables
Size after: 3532 bytes

You can also try sstrip which is advanced version of strip. You can download it from ELF kickers webpage.
Execute command: sstrip main

Size after: 1960 bytes

There are some others way to decrease size of programm.


GC Masher Allows to bruteforce gcc options for smaller executable size.
I where using this options for gcsmaher
-O  -O0  -O1  -O2  -O3  -Os
-ffast-math
-fomit-frame-pointer
-fauto-inc-dec
-mpush-args
-mno-red-zone
-mstackrealign

After runnig with this options executble size is 5175 bytes and best compiling options are all posible combination. 
Combining with sstrip gives 1960 bytes. 
And there size where not reduced but some time there can be saved some bytes.

Now we will change main function with
void _start()
and return change to
asm ( \
      "movl $1,%eax\n" \
      "xor %ebx,%ebx\n" \
      "int $128\n" \
    );

One other thing is to archive your executable and cat it with unpack shell script.
a=/tmp/I;tail -n+2 $0|zcat>$a;chmod +x $a;$a;rm $a;exit

Best options and smallest size now is 563 byte. Nope this is not smallest size try to
 rename executable name to one symbol and you will get 4 extra bytes.
gcc -Os -ffast-math -fomit-frame-pointer 
-fauto-inc-dec -mpush-args -mno-red-zone -c small.c;
ld -dynamic-linker /lib/ld-linux.so.2 small.o /usr/lib/libSDL.so -o small;
strip -s -R .comment -R .gnu.version small;sstrip small;
7z a -tGZip -mx=9 small.gz small > /dev/null;
cat unpack.header small.gz > small;
chmod a+x small;rm small.gz small.o

Download Source 
Rewriting all in asm gives 526 bytes Link.
Link to other resources Link1 
Author in link has 634 bytes. With his options I have 622 bytes and using gcmasher i have 606 bytes. I have used his source in this compare.







2009-09-04 FreeBSD assembler open file

Here code for opening file, reading from it and close it. At beginig i have thinked taht it will be complicated. But it was easy and interesting as C. Here is both C and asm code.

openfile.asm

;/usr/include/sys/syscall.h
;#define SYS_read        3
;#define SYS_write       4
;#define SYS_open        5
;#define SYS_close       6
 
sys_read equ 3
sys_write equ 4
sys_open equ 5
sys_close equ 6
o_rdonly equ 0
 
format ELF
section '.text' executable
public _start
_start:
    ;int fid = open("file.txt",O_RDONLY);
    push o_rdonly
    push f
    mov  eax, sys_open 
    push eax
    int  0x80
    add  esp, 4*3   ; clear stack after interupt	
    mov dword [f_id], eax
 
    ;read( fid , &buf[0] , 12 );
    push f_buf_len
    push f_buf
    push eax
    mov eax, sys_read
    push eax
    int 0x80
    add esp, 4*4
 
    ;write( 1 , &buf[0] , 12 );
    push f_buf_len   
    push f_buf     
    push 1         
    mov  eax, sys_write     
    push eax
    int  0x80
    add  esp,4*3
 
    ;close( fid );
    push dword [f_id]
    mov eax, sys_close
    push eax
    int 0x80
    add esp, 4*2
 
    ;exit from programm
    xor eax, eax	;eax = 0
    push eax
    inc eax			;eax = 1, sys_exit
    int 80h			;system interupt
 
section '.data' writeable
	f db "file.txt",0
	f_len = $-f
	f_buf db 12 dup 0
	f_buf_len = $-f_buf
	f_id dd 0


fasm openfile.asm openfile.o

ld openfile.o -o openfile



c.c
#include <fcntl.h>
 
int main()
{
	int fid = open("file.txt",O_RDONLY);
	char buf[12];
	read( fid , &buf[0] , 12 );
	write( 1 , &buf[0] , 12 );
	close( fid );
	return 0;
}


gcc c.c -o c

file.txt
Only text!!!




2009-11-30 Linux ShellCode 1


First shell code writened from example. Shell code is very interesting way how to execute some code.

asm source:

use32				
xor eax, eax
inc eax
xor ebx, ebx
int 80h

fasm code.asm code.bin

bin2hex output:

\x31\xc0\x40\x31\xdb\xcd\x80
C source:

#include <stdio.h>
char code[] = "\x31\xc0\x40\x31\xdb\xcd\x80";
int main()
{
  void (*ret)();
  ret = (void (*)())code;
  ret();
  printf("Nope it not working\n");
}

gcc main.c -o main


run ./main nothing happens. That exactly that code do exits from programm

Source


My variant of Bin2Hex


2009-10-30 Linux assembler SDL

Open SDL window from asm. I tryed to open SDL window from asm. And that worked. Hardest thing is defining all structures from SDL headers. Windows opening and waiting while anykey will pressed.

include 'cdecl.inc'
 
format ELF
 
extrn SDL_Init
extrn SDL_SetVideoMode
extrn SDL_PollEvent
extrn SDL_Quit
 
;video settings
SDL_INIT_VIDEO	equ 0x00000020
SDL_FULLSCREEN	equ 0x80000000
 
;event settings
SDL_KEYDOWN         equ 2
SDL_MOUSEBUTTONDOWN equ 5
 
;programm settings
SCREEN_WIDTH equ 800
SCREEN_HEIGHT equ 600
SCREEN_BPP equ 24
 
struc SDL_keysym
{
	.scancode 	db 0
	.sym 		dd 0
	.mod		dd 0
	.unicode 	dd 0
}
 
struc SDL_KeyboardEvent
{
	.type  db 0
	.which db 0
	.state db 0
	.keysym SDL_keysym
}
 
struc SDL_Event
{
	.type db 0
	union SDL_KeyboardEvent
	.empty db 0,0,0
}
 
 
section '.text' executable
public _start
_start:
	ccall SDL_Init,SDL_INIT_VIDEO
	ccall SDL_SetVideoMode, SCREEN_WIDTH , SCREEN_HEIGHT , SCREEN_BPP , SDL_FULLSCREEN
	;try to make while loop
while_run:	
	while_polleEvent:
		ccall SDL_PollEvent, event
		cmp eax, 0
		je	while_polleEventquit
		cmp byte [event.type], SDL_KEYDOWN
		jne	while_polleEvent
		mov byte [run], 0
		jmp while_polleEvent
	while_polleEventquit:
 
	; if run != 1 quit
	cmp byte [run], 1	
	je	while_run
 
	ccall SDL_Quit, 0
 
	mov eax, 1
	xor ebx, ebx
	int 80h
 
section '.data' writeable
event		SDL_Event
run 		db 		1


Compile with lines:

fasm sdl.asm sdl.o

ld -dynamic-linker /lib/ld-linux.so.2 sdl.o /usr/lib/libSDL.so -o sdl

Dowload Source



2009-11-08 Linux Assembler Make Directory

Code for creating file:


format ELF executable
 
include 'cdecl.inc'
include 'syscall.inc'
 
mode_t equ dd
 
segment readable executable
start:
	mov eax, SYS_MKDIR
	mov ebx, path
	mov ecx, [mode]
	int 80h
 
	mov eax, SYS_EXIT
	xor ebx, ebx
	int 80h
 
segment readable writeable
path	db 	"dir",0 
mode	mode_t  0777o
fasm makedir.asm -o makedir

Source


2010-01-24 Linux Local Descriptor Table

If 0x80**** adreeses is default nope. You can setup your own. Compiler will not see them
but you can do it. Setup LDT and you will see it.

use32
mov dword [0] ,"Hall"
mov dword [4] ,"Ball"
mov dword [8] ,"Mall"
mov dword [12],0x00000000
yes everything starts from 0x0


#include <stdlib.h>
#include <stdio.h>
#include <sys/syscall.h>
#include <sys/types.h>
#include <asm/ldt.h>
 
char new_segment[16];
 
int main()
{
	int r;
 
	struct user_desc *ldt;
 
	ldt = (struct user_desc*)malloc(sizeof(struct user_desc));
 
	ldt->entry_number = 0;
	ldt->base_addr = ((unsigned long)&new_segment);
	ldt->limit = 16;
	ldt->seg_32bit = 0x1;
	ldt->contents = 0x0;
	ldt->read_exec_only = 0x0;
	ldt->limit_in_pages = 0x0;
	ldt->seg_not_present = 0x0;
	ldt->useable = 0x1;
 
	printf("Start\n");
	r = syscall( __NR_modify_ldt, 1 , ldt , sizeof(struct user_desc) );
	if ( r == -1 )
	{
		printf("Sorry\n");
		exit( 0 );
	}
	asm("pushl %ds");
	asm("movl $0x7, %eax"); /* 0111: 0-Index 1-Using the LDT table 11-RPL of 3 */
	asm("movl %eax, %ds");	
	asm(".byte 0xc7,0x5,0x0,0x0,0x0,0x0,0x48,0x61,\                   0x6c,0x6c,0xc7,0x5,0x4,0x0,0x0,0x0,\                   0x42,0x61,0x6c,0x6c,0xc7,0x5,0x8,0x0,\                   0x0,0x0,0x4d,0x61,0x6c,0x6c,0xc7,0x5,\                   0xc,0x0,0x0,0x0,0x0,0x0,0x0,0x0");
	asm("popl %ds");
	printf("End\n");
 
	printf("Segment [%s]\n",new_segment);
 
	free( ldt );
 
	return 0;
}
asm(".byte ... ") is code.bin

Compile:
fasm code.asm code.bin
gcc main.c -o main


Source


© 2010