2日目 その2

前回halloos.Sを作りましたが、OS自作本に掲載されているhelloos.nasとはセグメントの設定などが異なっています。
今回はこれをOS自作本にあわせます。


以下修正したhelloos.Sの先頭部分です。

.file "helloos.S"

.code16gcc

.section .rodata
msg1:	
	.string "hello,world"
.text
main:
	cli
	movw $0x0, %ax
	movw %ax, %ss
	movw $0x7c00, %sp
	movw %ax, %ds
	movw %ax, %es
	sti
	
	movl $msg1, %esi

アセンブルして完成といきたいところですが、このままでは正しく"hello, world"が出力されません。
というのもリンクした際に$msg1が正しいアドレスを指してくれないからです。
具体的にみてみましょう。上のソースをアセンブルしたhelloos.binを

$ objdump -m i8086 -b binary -D helloos.bin

で逆アセンブルすると

e:	66 be 30 00 00 00    	mov    $0x30,%esi

つまり$msg1が$0x30と変換されています。いまDSは0なのでアドレス0x00030に文字列を参照にいきますが、このプログラムは先頭が0x07c00から読みこまれているので、"hello, world"は0x00030ではなく正しくは0x07c30に存在しています。


正しいアドレスを指すようにするにはhelloos.lsを以下のように変更します。

OUTPUT_FORMAT("binary")			/* We want raw binary image */
OUTPUT_ARCH(i386)

/* Define memory layout */

MEMORY {
  body : org = 0x7c00, len = 510
  sign : org = 0x7c00 + 510, len = 2
}

/* Specify input and output sections */

SECTIONS {
  .text   : { *(.text) }   > body	/* Executable codes */
  .data   : { *(.data) }   > body	/* Initialized data */
  .bss    : { *(.bss) }    > body	/* Uninitialized data */
  .rodata : { *(.rodata*) } > body	/* Constant data (R/O) */
  .sign   : { *(.sign) }  > sign	/* Boot signature */
}

前回とはMEMORY部が異なっています。
これを使ってリンクしたものを逆アセンブルすると

e:	66 be 30 7c 00 00    	mov    $0x7c30,%esi

正しいアドレスを指しているのがわかります。