'ASM'에 해당되는 글 2건
- 2007.07.21 부트섹터에서 프로그램 실행시키기. 14
- 2007.04.06 운영체제 없이 화면에 A를 찍어보아요... 6
부트섹터에서 프로그램 실행시키기.
Programming/System 2007. 7. 21. 18:29
;파일 시스템을 배운 보람(?) 이 있습니다..
;저기 FAT12다루는 부분.. FAT16이랑 비슷합니다..
;파일시스템도 fat만 거의 다 끝내놓고 더이상 진적이 없는..
;과연 스터디는 할수 있을지..
;모책을 보고 있는 예제를 혼자서 비스므리 하게 짜봤습니다
;모르는 부분은 상당히 보고 했으므로 비슷한 부분이 많을듯.
;nask라는 이상한(?) 어셈블러로 해서 nasm이랑 약간 문법이 틀린데가 있습니다
;resb는 nasm의 times로 어떻게 대체 가능한합니다.
;부트섹터에서 부트섹터 외에 있는 프로그램으로 이동시켜서 실행하게 해주는 프로그램이
;부트로더인모양? 초보라 잘 모르겠네요.
;개인 기억용, 틀려도 절대 책임같은건 지지 않음..(아마 틀린거 많을걸?)
;영어에 태클 걸지 말것!
;저기 FAT12다루는 부분.. FAT16이랑 비슷합니다..
;파일시스템도 fat만 거의 다 끝내놓고 더이상 진적이 없는..
;과연 스터디는 할수 있을지..
;모책을 보고 있는 예제를 혼자서 비스므리 하게 짜봤습니다
;모르는 부분은 상당히 보고 했으므로 비슷한 부분이 많을듯.
;nask라는 이상한(?) 어셈블러로 해서 nasm이랑 약간 문법이 틀린데가 있습니다
;resb는 nasm의 times로 어떻게 대체 가능한합니다.
;부트섹터에서 부트섹터 외에 있는 프로그램으로 이동시켜서 실행하게 해주는 프로그램이
;부트로더인모양? 초보라 잘 모르겠네요.
;개인 기억용, 틀려도 절대 책임같은건 지지 않음..(아마 틀린거 많을걸?)
;영어에 태클 걸지 말것!
부연설명 (잊어버릴까봐..)
mov ax,0 ; ax = 0
int 0x10 ;번호에 해당하는 인터럽트 발생
(쉽게 말해 ax,bx,cx,dx,같은게 인자고 이걸사용하면 함수를 부르는거라 생각하면 될듯)
inc ax ; ax ++
dec ax ; ax--
add ax,3 ; ax = ax + 3
sub ax,3 ; ax = ax - 3
cmp ax,3 ; if문, ax가 (뒤에 따라 점프)
jmp lable; goto label
jc : jump carry,에러가 난다면.. 점프
je ; jump equal 같으면 점프
jb ; jemp below 작으면 점프
jbe ; jemp below equal 작거나 같으면 점프
jnc ; jemp not carry
db ; byte (db 0x00 이면 현재위치에 1byte 만큼 0을 쓴다 라는 뜻인듯)
dw ;word (마찬가지)
dd ; double word (마찬가지)
[] ; c와 같다(배열과 포인터에 나오는 그거임... *(변수))
$ ; 현재 위치
resb ; 0로 범위까지 채운다 (nasm에는 없음 times로 대체)
mov ax,0 ; ax = 0
int 0x10 ;번호에 해당하는 인터럽트 발생
(쉽게 말해 ax,bx,cx,dx,같은게 인자고 이걸사용하면 함수를 부르는거라 생각하면 될듯)
inc ax ; ax ++
dec ax ; ax--
add ax,3 ; ax = ax + 3
sub ax,3 ; ax = ax - 3
cmp ax,3 ; if문, ax가 (뒤에 따라 점프)
jmp lable; goto label
jc : jump carry,에러가 난다면.. 점프
je ; jump equal 같으면 점프
jb ; jemp below 작으면 점프
jbe ; jemp below equal 작거나 같으면 점프
jnc ; jemp not carry
db ; byte (db 0x00 이면 현재위치에 1byte 만큼 0을 쓴다 라는 뜻인듯)
dw ;word (마찬가지)
dd ; double word (마찬가지)
[] ; c와 같다(배열과 포인터에 나오는 그거임... *(변수))
$ ; 현재 위치
resb ; 0로 범위까지 채운다 (nasm에는 없음 times로 대체)
;main
;Program start place
ORG 0x7c00
;#define READ_CYRINDERS 10
READ_CYLINDER EQU 10
;FAT12 Boot record setting
jmp init_register ;Jump boot code (3byte)
db 0x90 ;padding (jump boot code)
db "Lowid " ;OEM Name (8byte)
dw 512 ;Bytes per secter
db 1 ;Secter per Cluster
dw 1 ;Reserved Secter count
db 2 ;Number of fats
dw 224 ;Boot entry count
dw 2880 ;Total secter 16
db 0xf0 ;Media(now,floppy disk)
dw 9 ;Fat size 16
dw 18 ;Sector per track
dw 2 ;Number of heads
dd 0 ;Hidden secter (no use partition)
dd 2280 ;Total secter32?? (drive size)
db 0 ;Drive Number
db 0 ;Reseved1
db 0x29 ;Boot signature(must 0x29?)
dd 0xffffffff ;Volume serial num??
db "Lowid_vol " ;Volume label (11byte)
db "FAT12 " ;Filesystem Type (8byte)
resb 18
init_register:
mov ax,0
mov sp,0x7c00
mov ds,ax
mov ss,ax
;(Read)Segment + offset
mov ax,0x0820
mov es,ax
mov bx,0
;init_CHS
mov ch,0 ;Cyrinder
mov dh,0 ;Head
mov cl,2 ;Sector
init_di_register:
mov di,0 ;error count
read_disk:
mov ah,0x02 ;read_mode
mov al,1 ;read secter size
mov dl,0 ;drive
int 0x13 ;disk nterrupt
jnc succeed ;no error.. jump (read)succeed
;error
inc di ;di ++
cmp di,5 ;if 5
je error ;equal.. goto error
jmp read_disk
print:
mov al,[si] ;print character
mov ah,0x0e ;mode
mov bh,0x15 ;color
int 0x10 ;video interrupt
inc si
cmp al,0
je finish
jmp print
error:
mov si,error_string
jmp print
;MAX(floppy disk?) - cylinder:40, head:2 sector:18
;cylinder:0 head:0 sector:1
;cylinder:0 head:0 sector:2
;cylinder:0 head:0 sector:3
; .......
;cylinder:0 head:0 sector:17
;cylinder:0 head:0 sector:18
;cylinder:0 head:1 sector:1
;cylinder:0 head:1 secter:2
; .......
;cylinder:0 head:1 secter:17
;cylinder:0 head:1 secter:18
;cylinder:1 head:0 secter:1
succeed:
;Move Segment and offset
mov ax,es
add ax,512/16
mov es,ax
;Read 18 secter
inc cl
cmp cl,18
jbe init_di_register
;Read 2 head
mov cl,0 ;init secter
inc dh
cmp dh,2
jb init_di_register
;Read 10 cylinder
mov dh,0 ;init head
inc ch
cmp ch,READ_CYLINDER
jb init_di_register
;All compleate!.. print succeed
mov si,succeed_string
jmp print
;jemp! (video file)
finish:
jmp 0xc200
error_string:
db "Read Failed - Check please!!"
db 0x0a,0x00
succeed_string:
db "Read Succeed - Check OK !!"
db 0x0a,0x00
;for Dos Table Signature
resb 0x7dfe - $ ;padding(0)
db 0x55,0xaa ;Dos Table Signature
;Program start place
ORG 0x7c00
;#define READ_CYRINDERS 10
READ_CYLINDER EQU 10
;FAT12 Boot record setting
jmp init_register ;Jump boot code (3byte)
db 0x90 ;padding (jump boot code)
db "Lowid " ;OEM Name (8byte)
dw 512 ;Bytes per secter
db 1 ;Secter per Cluster
dw 1 ;Reserved Secter count
db 2 ;Number of fats
dw 224 ;Boot entry count
dw 2880 ;Total secter 16
db 0xf0 ;Media(now,floppy disk)
dw 9 ;Fat size 16
dw 18 ;Sector per track
dw 2 ;Number of heads
dd 0 ;Hidden secter (no use partition)
dd 2280 ;Total secter32?? (drive size)
db 0 ;Drive Number
db 0 ;Reseved1
db 0x29 ;Boot signature(must 0x29?)
dd 0xffffffff ;Volume serial num??
db "Lowid_vol " ;Volume label (11byte)
db "FAT12 " ;Filesystem Type (8byte)
resb 18
init_register:
mov ax,0
mov sp,0x7c00
mov ds,ax
mov ss,ax
;(Read)Segment + offset
mov ax,0x0820
mov es,ax
mov bx,0
;init_CHS
mov ch,0 ;Cyrinder
mov dh,0 ;Head
mov cl,2 ;Sector
init_di_register:
mov di,0 ;error count
read_disk:
mov ah,0x02 ;read_mode
mov al,1 ;read secter size
mov dl,0 ;drive
int 0x13 ;disk nterrupt
jnc succeed ;no error.. jump (read)succeed
;error
inc di ;di ++
cmp di,5 ;if 5
je error ;equal.. goto error
jmp read_disk
print:
mov al,[si] ;print character
mov ah,0x0e ;mode
mov bh,0x15 ;color
int 0x10 ;video interrupt
inc si
cmp al,0
je finish
jmp print
error:
mov si,error_string
jmp print
;MAX(floppy disk?) - cylinder:40, head:2 sector:18
;cylinder:0 head:0 sector:1
;cylinder:0 head:0 sector:2
;cylinder:0 head:0 sector:3
; .......
;cylinder:0 head:0 sector:17
;cylinder:0 head:0 sector:18
;cylinder:0 head:1 sector:1
;cylinder:0 head:1 secter:2
; .......
;cylinder:0 head:1 secter:17
;cylinder:0 head:1 secter:18
;cylinder:1 head:0 secter:1
succeed:
;Move Segment and offset
mov ax,es
add ax,512/16
mov es,ax
;Read 18 secter
inc cl
cmp cl,18
jbe init_di_register
;Read 2 head
mov cl,0 ;init secter
inc dh
cmp dh,2
jb init_di_register
;Read 10 cylinder
mov dh,0 ;init head
inc ch
cmp ch,READ_CYLINDER
jb init_di_register
;All compleate!.. print succeed
mov si,succeed_string
jmp print
;jemp! (video file)
finish:
jmp 0xc200
error_string:
db "Read Failed - Check please!!"
db 0x0a,0x00
succeed_string:
db "Read Succeed - Check OK !!"
db 0x0a,0x00
;for Dos Table Signature
resb 0x7dfe - $ ;padding(0)
db 0x55,0xaa ;Dos Table Signature
;video
ORG 0xc200
;VGA 320x200x8bit
mov al,0x13
mov ah,0x00
int 0x10
finish:
hlt
jmp finish
ORG 0xc200
;VGA 320x200x8bit
mov al,0x13
mov ah,0x00
int 0x10
finish:
hlt
jmp finish
'Programming > System' 카테고리의 다른 글
mmap 사용시 알아둘 사항 (버스오류) (0) | 2010.05.31 |
---|---|
FAT12과 FAT16의 부트레코드의 구성이 같은모양인가 보다 (2) | 2007.07.27 |
압축플때 쓰는 쉘 스크립트 (4) | 2007.06.18 |
MBR(?) 출력 하기 (2) | 2007.06.17 |
screen attach dettach 구별법 (2) | 2007.02.12 |
운영체제 없이 화면에 A를 찍어보아요...
Programming/Kernel 2007. 4. 6. 14:14
말하기 앞서서
일단 세그먼트/오프셋이 뭔지 알고 있다고 가정하고 내용을 작성하였습니다.
그것만 알고 계시다면 다음 이야기를 읽는데는 지장이 없을듯하네요
뭐 틀린내용이 있을수도 있으니 100%다 믿진 마시고요;
혹시 틀린게 있으면 지적 부탁합니다
덧> vmware,nasm,vi 정도는 다 아신다고 가정
0 preview
[org 0x07C0]:처음 시작 주소를 여기부터 시작한대여..바이오스가 이주소를 제일 먼저 읽는다고 함
(왜 거기냐? 라고 묻지마세요 저도 모릅니다 찾아도 도저히 못찾겠더라고요..혹시 아시는 분 있으면 댓글 부탁;)
mov :데이터 치환 (nasm에선 mov ax,0x07 하면 ax=0x07과 같다고 보면 된다)
byte[es:di]:es레지스터에서 di의 오프셋의 위치의 데이터에서 byte(1byte)만큼 데이터를 읽는다
1우리가 알아야 하는것
1)0x7C0라는 주소(세그먼트) 에 프로그램을 위치시켜야한다(org []라는게 이말이다)
2)비디오 메모리(화면에 출력하기 위한) 의 세그먼트는 0xB800이다
3)비디오 메모리 세그먼트가 가리키는 위치에 (오프셋대로)순서대로 값을 집어 넣는다
==>offset 에 관해서.. 첫번짜 byte는 문자 두번째 바이트는 색깔을 잡어 넣는다
ex> 0x07이라면.... 0검정 7하양(0x 0 7)
이상하네... 바로 메모리 접근이 안되나보다.세그먼트 레지스터를 이용해서 접근해보자
es세그먼트(사용자세그먼트 레지스터)레지스터에다가 0xB800를 (컬러 비디오 메모리 주소)
복사한다음 그 값을 복사한 범용레지스터를 다시 세그먼트 레지스터에 복사해 넣는다
대충 다름과 같은 예가 되겠지...
ax=0x07
es=ax
암튼....그리하여 ax,로 넘긴다음 ... es를 설정해준다
이리하면 잘아알 실행됨.. 화면에 당당히 A출력,바탕은 검정,글색깔은 흰색
ds 레지스터를 이용하여 좀더 간단하게
일단 좀더 폼 잡어서 약간더 추가하면..
추가:jmp $란 현재주소에서 현재주소로(?) jump!하기다 즉,제자리 뛰기
현재상태를 유지하기 위해서다 (프로그램이 끝나면 안되므로..그래도 때에 따라서 돌아가는덴 지장 없을때도)
아놔 이거 하나 안다고 정말 뻘짓한 시간 생각하면 크윽..;;
어셈블리 생판 모르는 상태애서 이거 이해한다고 어려워 죽는줄(?) 알았어영 ㅜㅜ
저같이 삽질을 하시는 분을 조금이라도 줄이기 위해서 이글을 바칩니다 ㅜㅜ 어흑...
일단 세그먼트/오프셋이 뭔지 알고 있다고 가정하고 내용을 작성하였습니다.
그것만 알고 계시다면 다음 이야기를 읽는데는 지장이 없을듯하네요
뭐 틀린내용이 있을수도 있으니 100%다 믿진 마시고요;
혹시 틀린게 있으면 지적 부탁합니다
덧> vmware,nasm,vi 정도는 다 아신다고 가정
0 preview
[org 0x07C0]:처음 시작 주소를 여기부터 시작한대여..바이오스가 이주소를 제일 먼저 읽는다고 함
(왜 거기냐? 라고 묻지마세요 저도 모릅니다 찾아도 도저히 못찾겠더라고요..혹시 아시는 분 있으면 댓글 부탁;)
mov :데이터 치환 (nasm에선 mov ax,0x07 하면 ax=0x07과 같다고 보면 된다)
byte[es:di]:es레지스터에서 di의 오프셋의 위치의 데이터에서 byte(1byte)만큼 데이터를 읽는다
C랑 비교한다면
char buf[3]; 이 있다고 할때
char는 byte,buf 는 es, []안의 숫자는 di로 보면 되겠다...(이게 더 복잡한가?)
=>plus! 그리고 byte[di] 같이 쓰는것은 ds레지스터를 생략해서 쓴것뿐이다
(ds세그먼트의 di 오프셋)
즉 byte[ds:di] == byte[di]랑 같다는 얘기!!
char buf[3]; 이 있다고 할때
char는 byte,buf 는 es, []안의 숫자는 di로 보면 되겠다...(이게 더 복잡한가?)
=>plus! 그리고 byte[di] 같이 쓰는것은 ds레지스터를 생략해서 쓴것뿐이다
(ds세그먼트의 di 오프셋)
즉 byte[ds:di] == byte[di]랑 같다는 얘기!!
1우리가 알아야 하는것
1)0x7C0라는 주소(세그먼트) 에 프로그램을 위치시켜야한다(org []라는게 이말이다)
2)비디오 메모리(화면에 출력하기 위한) 의 세그먼트는 0xB800이다
3)비디오 메모리 세그먼트가 가리키는 위치에 (오프셋대로)순서대로 값을 집어 넣는다
==>offset 에 관해서.. 첫번짜 byte는 문자 두번째 바이트는 색깔을 잡어 넣는다
ex> 0x07이라면.... 0검정 7하양(0x 0 7)
1 [org 0x07C0]
2
3 mov byte[0xB800:0x0000],'A'
4 mov byte[0xB800:0x0001],0x07
2
3 mov byte[0xB800:0x0000],'A'
4 mov byte[0xB800:0x0001],0x07
이상하네... 바로 메모리 접근이 안되나보다.세그먼트 레지스터를 이용해서 접근해보자
es세그먼트(사용자세그먼트 레지스터)레지스터에다가 0xB800를 (컬러 비디오 메모리 주소)
복사한다음 그 값을 복사한 범용레지스터를 다시 세그먼트 레지스터에 복사해 넣는다
대충 다름과 같은 예가 되겠지...
ax=0x07
es=ax
암튼....그리하여 ax,로 넘긴다음 ... es를 설정해준다
1 [org 0x07C0]
2
3 mov ax,0xB800
4 mov es,ax
5
6 mov byte[es:0],'A'
7 mov byte[es:1],0x07
2
3 mov ax,0xB800
4 mov es,ax
5
6 mov byte[es:0],'A'
7 mov byte[es:1],0x07
이리하면 잘아알 실행됨.. 화면에 당당히 A출력,바탕은 검정,글색깔은 흰색
ds 레지스터를 이용하여 좀더 간단하게
1 [org 0x07C0]
2
3 mov ax,0xB800
4 mov ds,ax
5
6 mov byte[0],'A' ;[ds:0]
7 mov byte[1],0x07;[ds:1]
2
3 mov ax,0xB800
4 mov ds,ax
5
6 mov byte[0],'A' ;[ds:0]
7 mov byte[1],0x07;[ds:1]
일단 좀더 폼 잡어서 약간더 추가하면..
1 [org 0x07C0]
2
3 start:
4 mov ax,0xB800
5 mov es,ax
6 mov di,0
7
8 mov byte[es:di],'A'
9 inc di ;c로 치면 di++
10 mov byte[es:di],0x07
11
12 jmp $
2
3 start:
4 mov ax,0xB800
5 mov es,ax
6 mov di,0
7
8 mov byte[es:di],'A'
9 inc di ;c로 치면 di++
10 mov byte[es:di],0x07
11
12 jmp $
추가:jmp $란 현재주소에서 현재주소로(?) jump!하기다 즉,제자리 뛰기
현재상태를 유지하기 위해서다 (프로그램이 끝나면 안되므로..그래도 때에 따라서 돌아가는덴 지장 없을때도)
아놔 이거 하나 안다고 정말 뻘짓한 시간 생각하면 크윽..;;
어셈블리 생판 모르는 상태애서 이거 이해한다고 어려워 죽는줄(?) 알았어영 ㅜㅜ
저같이 삽질을 하시는 분을 조금이라도 줄이기 위해서 이글을 바칩니다 ㅜㅜ 어흑...
'Programming > Kernel' 카테고리의 다른 글
확실히 다르잖아!! (4) | 2008.04.15 |
---|---|
ctags 설정 (4) | 2008.03.11 |
본체 전원키로 시스템 off 시키기 (4) | 2007.04.22 |
KernelProgramming-printk (5) | 2006.07.24 |
Kernel Panic! (2) | 2006.07.21 |