농소
시스템 프로그래밍, 시스템 콜 본문
시스템 프로그래밍
게임 프로그래밍 - 게임 관련 라이브러리 사용
네트워크 프로그래밍 - 소켓을 이용한 네트워크 라이브러리 사용
시스템 프로그래밍
- 윈도우즈 : win API (Advanced Programing Interface)
- 리눅스 : system call
시스템 호출(System call)은 운영 체제의 커널이 제공하는 서비스에 대해,
응용 프로그램의 요청에 따라 커널에 접근하기 위한 인터페이스이다.
os를 크게 나누면 2가지로 나눌 수 있다
1). shell(user) - 사용자 영역 (목적 - h/w제어)
2). H/W(Device)
- shell에서 하드웨어에 바로접근하게되면 문제가발생 한다.
- 그래서 중간에 커널이 존재한다. 또, 장치를 출력하고싶으면 interface를 이용
- interface = win api, system call 함수형태로 제공
커널 : 장치로부터 자원을 내보내거나 들이거나 어떻게 메모리를 관리할것인가를 관리
os랑은 다름 os가 더 큰개념
쉘 | 커널 | 하드웨어 -> os라 함
- c에서 printf같은경우 내부적으로 write라는 시스템콜을 두번 사용한다.
- eax레지스터에 system call 번호를 넣고, ebx, ecx, edx, esi, edi 를 인자로 이용한다.
- 그외 인자를 추가할 시 스택을 이용
- 인터럽트 명령어를 사용하여 시스템콜을 호출 = 80h
리눅스 시스템 콜 같은경우 win api와는 다르게 웹상에 공개되어있어 쉽게 찾아볼 수 있다.
주로 이용하는 시스템 콜 참조 사이트
https://syscalls.kernelgrok.com/
예를들어 write같은 경우
<write system call 표현방법>
이런식으로 표현이 가능하다.
[실습]
1). 디렉터리 생성 : mkdir 명령어 만들기
- read, write, mkdir 시스템콜 이용한다.
참고사항
- read 는 \n까지 읽어들인다
- read는 읽어들인 문자열의 길이를 반환
- 메모리는 지역변수만 사용
c언어
int main()
{
char path[1024] = {0,};
int end = 0;
int result = 0;
write( 1, "input: ", 7 );
read( 0, path, 1024 );
while( path[end] != '\n' ) {
end++
}
path[end] = 0;
result = mkdir( path, 0755);
if( result < 0) {
write( 1, "failed\n", 7 )
} else {
write( 1, "success\n", 8 )
}
return 0;
}
어셈블리 언어
segment .data
fail db 'failed', 10, 00
success db 'success', 10, 00
input db 'input :', 00
segment .text
global _start
_start:
push ebp
mov ebp, esp
sub esp, 1032
mov ecx, 256
mov eax, 0
lea edi, [ebp-1024] ;char path[1024] = {0,}
rep stosb
mov dword [ebp-1028], 0 ;end
mov dword [ebp-1032], 0 ;result
; write( 1, "input: ", 7 );
mov eax, 4
mov ebx, 1
mov ecx, input
mov edx, 7
int 80h
; read( 0, path, 1024 );
mov eax, 3
mov ebx, 0
lea ecx, [ebp-1024]
mov edx, 1024
int 80h
while:
lea eax, [ebp-1024]
mov ebx, [ebp-1028]
cmp byte [eax + ebx * 1], 10
je end
inc dword [ebp-1028]
jmp while
end:
lea eax, [ebp-1024]
mov ebx, [ebp-1028]
mov byte [eax + ebx * 1], 0 // 마지막 널문자 제거 제거를 안하면
example 파일을 만들시 example\n이 되버림
; result = mkdir( path, 0755);
mov eax, 27h
lea ebx, [ebp-1024]
mov ecx, 0755o
int 80h
mov dword [ebp-1032], eax
if:
cmp dword [ebp-1032], 0
jge .else
mov eax, 4
mov ebx, 1
mov ecx, fail
mov edx, 7
int 80h
jmp .end
.else:
mov eax, 4
mov ebx, 1
mov ecx, success
mov edx, 8
int 80h
.end:
xor eax, eax
leave
ret
2). 파일 입/출력 : cat
- open, read, write 시스템콜 이용
c언어
int main()
{
char path[1024] = {0,};
char buffer[1024] = {0,};
int size = 0;
int fd = 0;
int end = 0;
write( 1, "input: ", 7 );
read( 0, path, 1024 );
while( path[end] != '\n' ) {
end++;
}
path[end] = 0;
fd = open( path, 0, 0 );
size = read( fd, buffer, 1024 );
while(size == 0) {
write( 1, buffer, 1024 );
size = read( fd, buffer, 1024 );
}
어셈블리 언어
segment .data
input db 'input: ', 00
segment .text
global _start
_start:
push ebp
mov ebp, esp
sub esp, 2060
mov ecx, 512
mov eax, 0
lea edi, [ebp-2048]
rep stosd
mov dword [ebp-2052], 0 ; size
mov dword [ebp-2056], 0 ; fd
mov dword [ebp-2060], 0 ; end
;write
mov eax, 4
mov ebx, 1
mov ecx, input
mov edx, 7
int 80h
;read
mov eax, 3
mov ebx, 0
lea ecx, [ebp-1024]
mov edx, 1024
int 80h
while1:
lea eax, [ebp-1024]
mov ebx, [ebp-2060]
cmp byte [eax + ebx * 1], 10
je .end
inc dword [ebp-2060]
jmp while1
.end:
lea eax, [ebp-1024]
mov ebx, [ebp-2060]
mov byte [eax + ebx *1], 0
;open
mov eax, 5
lea ebx, [ebp-1024]
mov ecx, 0
mov edx, 0
int 80h
mov dword [ebp-2056], eax
;read
mov eax, 3
mov ebx, [ebp-2056]
lea ecx, [ebp-2048]
mov edx, 1024
int 80h
mov dword [ebp-2052], eax
while2:
cmp dword [ebp-2052], 0
je end
;write
mov eax, 4
mov ebx, 1
lea ecx, [ebp-2048]
mov edx, 1024
int 80h
;read
mov eax, 3
mov ebx, [ebp-2056]
lea ecx, [ebp-2048]
mov edx, 1024
int 80h
mov dword [ebp-2052], eax
jmp while2
end:
xor eax, eax
leave
ret
3). 쉘 : shell
- execve, read, write 사용
c언어
#include <stdio.h>
int main()
{
char *argv[2] = {0,};
char buffer[1024] = {0,};
int end = 0;
write( 1, "input: ", 7 );
read( 0, buffer, 1024 );
// while( buffer[end] != '\n' ) {
while( *(buffer+end) != '\n' ){
end++;
}
}
buffer[end] = 0;
argv[0] = buffer;
argv[1] = NULL;
execve( buffer, argv, NULL);
return 0;
}
어셈블리 언어
segment .data
input db 'input: ', 00
segment .text
global _start
_start:
push ebp
mov ebp, esp
sub esp, 1036
mov ecx, 256
mov eax, 0
lea edi, [ebp-1024]
rep stosd
mov dword [ebp-1028], 0
mov dword [ebp-1032], 0
mov dword [ebp-1036], 0
mov eax, 4
mov ebx, 1
mov ecx, input
mov edx, 7
int 80h
mov eax, 3
mov ebx, 0
lea ecx, [ebp-1024]
mov edx, 1024
int 80h
while:
lea eax, [ebp-1024]
mov ebx, [ebp-1036]
cmp byte [eax + ebx * 1], 10
je .end
inc dword [ebp-1036]
jmp while
.end:
lea eax, [ebp-1024]
mov ebx, [ebp-1036]
mov byte [eax + ebx * 1], 0
lea eax, [ebp-1024]
mov dword [ebp-1032], eax
mov dword [ebp-1028], 0
mov eax, 11
lea ebx, [ebp-1024]
lea ecx, [ebp-1032]
mov edx, 0
int 80h
xor eax, eax
leave
ret
'Security > System Hacking' 카테고리의 다른 글
바이너리 분석 연습 (0) | 2018.01.29 |
---|---|
디버거 GDB 사용법 (0) | 2018.01.26 |
asm 지역변수 배열, main 함수의 인자 int argc, char *argv[ ] (0) | 2018.01.24 |
프로세스 메모리 구조, 스택 레지스터, 함수 (0) | 2018.01.23 |
nasm 반복문 연습2 (0) | 2018.01.20 |