コンピュータの構造と命令 以降の講義の目的 高級言語(C言語,Java言語など)で書かれたプログラムを コンピュータはどのようにして実行しているのかを理解し, コンピュータの構造と動作を理解すること。 コンピュータの構成要素 演算データを保持 次に実行する命令 の番地を保持 プロセッサ 主記憶(1GByte) 0番地 R0 R1 R2 R3 1番地 レジスタ プログラムカウンタ(PC) 命令,データ 2番地 命令レジスタ(IR) 命令解読器(ID) ALU PCの指す番地から 読み出した命令を 保持 計算を実行 命令レジスタの 内容を解読 230-1= 1073741823 番地 プログラムの命令と データを格納 PC : Program Counter IR : Instruction Register ALU : Arithmetic Logical Unit ID : Instruction Decoder 1 プロセッサの動作 z プロセッサはメモリに格納された「命令」を順番に実行していく ① ●メモリから命令を読み出してくる。 何番地から命令を読み出すか? ⇒ プロセッサ内部の「プログラムカウンタ(PC)」により指定する 次の命令の実行に備えてPCの値を増やす(インクリメントする)。 ● ② 読み出した命令を解読する。 ③ 命令を実行する(計算を行う)。 ④ 計算結果を格納する。 コンピュータのプログラム(1) 高水準言語プログラム (ソースプログラム) swap(int v[ ], int k) {int temp ; temp=v[k] ; v[k]=v[k+1] ; v[k+1]=temp ; } 機械語命令のプログラム (オブジェクトプログラム) 0100001101001010000110 0101110010101000101110 コンパイラにより 機械語命令に 変換される 1001001000110001001011 1001001000110001001011 0101110010101000101110 0101110010101000101110 注)高水準言語: C,Java,Basicなど 1001001000110001001011 この0と1の数字列(ビットパターン) が主記憶に格納される 2 コンピュータのプログラム(2) 機械語命令のプログラム (オブジェクトプログラム) アセンブリ言語プログラム (アセンブリプログラム) 0100001101001010000110 0101110010101000101110 1001001000110001001011 1001001000110001001011 0101110010101000101110 = 0101110010101000101110 1001001000110001001011 muli $s2,$s5,$s4 add $s2,$s4,$s2 lw $s15,0($s2) lw $s16,4($s2) sw $s16,0($s2) sw $s15,4(s2) jr $s31 この授業では,MIPS社のR2000というプロセッサ(以下ではMIPSプロセッサと 表記する)を題材にアセンブリ言語レベルでのプログラミングについて講義する。 命令の表現 : 機械語とアセンブリ言語 z 機械語(machine language) • プロセッサが実行する命令の体系 • プロセッサの種類ごとに異なる • 機械語は2進数あるいは16進数で表現する 1000 1101 0010 1000 0000 0100 1011 1010 0100 0101 1111 0111 1010 1110 0011 0110 z アセンブリ言語(assembly language) • 機械語命令を記号で表現した言語 lw $t0, 1200($s0) add $s1, $t0, $s1 sw $s1, 1200($s0) 3 8D2804BA 45F7AE36 MIPSプロセッサのイメージ 主記憶(4GByte) プロセッサ 0番地 0 1 2 3 1番地 プログラムカウンタ(PC) 命令,データ 命令レジスタ(IR) レジスタ 2番地 …… 命令解読器(ID) …… 30 31 ALU 230-1= 1073741823 番地 主記憶(メモリ) z データとプログラムを格納するための記憶装置 z 主記憶は「語(ワード:word) 」を単位として,プロセッサ から読書きされる。 – 「語」は複数のbitの集まり(MIPSでは1語32bit=4byte) z 主記憶は膨大な数の「語」からなる – 「語」それぞれに固有の番号を付け,その番号で識別する – その番号のことを「番地 」または「アドレス(address) 」という – 番地はbyte単位で付けられる(0番地,1番地,2番地,…) – 1語4byte とすると,語は4番地ごとに番地付けされる 4 MIPSの主記憶の構成 z 主記憶の各ワード(語)は,番地(アドレス)によって識別され る。(番地はbyte単位で付けられる) 語(ワード)の番地 プロセッサからは 4の倍数の番地 で各ワードを指定 する byte単位での番地 0番地 0番地 1番地 2番地 3番地 4番地 4番地 5番地 6番地 7番地 8番地 8番地 9番地 10番地 11番地 ………… 4n番地 4n 4n+1 4n+2 4n+3 ………… 1073741820番地 (230-4) 230-4 230-3 230-2 230-1 最初のワードの番地は0番地,次は4番地,次は8番地... ,となる レジスタ(register) • プロセッサ内部にある「データを記憶」する機構 ⇒ プログラムの実行途中で,一時的な記憶に使う • 主記憶の「語」の数に比べ,レジスタ数は非常に小さい • プログラムにおけるレジスタの役割 – 主記憶中にあるデータをレジスタに読み込む ロード:load 「持って来る」 – レジスタを指定して演算を行う – 演算結果を主記憶に書き込む ストア:store 「格納する」 5 MIPSのレジスタ z 32個のレジスタ – 機械語では0から31までの番号で識別される – アセンブラ言語では名前(レジスタ名)で識別できる z 使用目的により32個のレジスタを分類(規約) – レジスタ $s0,$s1,$s2,……,$s7 • C言語などの高級言語でプログラム中の変数の値を保持する目的 – レジスタ $t0,$t1,$t2,……,$t7 • 演算の途中での一時的なデータを保持する目的 – レジスタ $zero • 特別なレジスタで,常に 0 を値としてもつ (どのような値を書き込んでも,値は0のまま → データは保存できない) MIPSのレジスタ番号とレジスタ名 レジスタ番号 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 レジスタ名 $zero $at $v0 $v1 $a0 $a1 $a2 $a3 $t0 $t1 $t2 $t3 $t4 $t5 $t6 $t7 レジスタ番号 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 レジスタ名 $s0 $s1 $s2 $s3 $s4 $s5 $s6 $s7 $t8 $t9 $k0 $k1 $gp $sp $fp $ra ※ アセンブリ言語では,レジスタ名で表記する 6 変数の概念 ◆ 「変数」=「データの保存場所 」 保存場所はどこにあるのか? ⇒ 主記憶(メモリ) add $t0, $s0, $s1 プログラム領域 int main( ) { int a,b,c ; a=1024; # ① b=512; #② データ c=a+b; #③ (変数)領域 printf(”%d¥n”,c); } sub $s1, $t2, $t1 … a 1024 ① b 512 ② c 1536 ③ 変数名は主記憶の 番地に対応する 変数の読書き(アクセス) add $t0, $s0, $s1 プログラム 領域 sub $s1, $t2, $t1 … プログラム領域とデータ領域 は一括して主記憶中に確保 される 変数領域の先頭番地(アドレス) を保持していれば,任意の変数 にアクセスできる データ(変数) 領域 a 1024 b 512 c 1536 $gp:global pointer 変数領域の先頭番地を保持する $gp = 変数 a のアドレスを保持 → 変数 b の番地 =$gp+4 変数 c の番地 =$gp+8 … 7 ロードとストアの概念 ロード(load) • 変数の値(主記憶の語の内容)をレジスタに読み出す動作 ストア(store) • レジスタの内容を変数に格納する(主記憶に書き込む)動作 プロセッサ レジスタ1 主記憶 ロード(load) -473 レジスタ2 1998 ストア(store) a -473 b 1998 ロード命令(load instruction) ◆ レジスタに主記憶の語の内容を読み込む動作 lw $Ri,N($Rj) $Ri,$Rj はレジスタの一般表記 • Load Word • レジスタ$Rjの値+N の番地の語の内容をレジスタ $Ri に ロードする • $Rj を「ベースレジスタ 」,Nを「オフセット 」と呼ぶ • Nの値は16bitの2の補数表現のもとで -32768~32767 の範囲(-215~215-1)を指定できる 例1: lw $t0, 0($t4) 例2: lw $s0, 4($s1) 例3: lw $t2, -128($s1) 8 オフセットの役割り 命令 lw $s0,0($t0) の動作 • レジスタ $t0 は値 10000 を保持していると仮定 • 0($t0) が表す番地: 10000+0 = 10000 • 10000 番地 の語の内容2005がレジスタ$s0 にロードされる プロセッサ 主記憶 9996 -473 10000 2005 10004 76401 10008 -1649 10010 0 $t0 : 10000 $t1 : 42000 ・・・・・・ 2005 ???? $s0: ・・・・・・ オフセットの役割り 命令 lw $s0,-4($t0) の動作 • レジスタ $t0 は値 10000 を保持していると仮定 • -4($t0) が表す番地: 10000-4 = 9996 • 9996 番地 の語の内容 -473 がレジスタ$s0にロードされる。 プロセッサ 主記憶 9996 -473 10000 2005 10004 76401 10008 -1649 10010 0 $t0 : 10000 $t1 : 42000 ・・・・・・ $s0: -473 2005 ・・・・・・ 9 ストア命令(store instruction) ◆ レジスタの値を主記憶に書き込む動作 sw $Ri,N($Rj) $Ri,$Rj はレジスタの一般表記 • Store Word • レジスタ$Rj の値+N の番地の語にレジスタ $Ri の 値をストアする(格納する)。 例1: sw $t0, 0($t4) 例2: sw $s0, -4($s1) 例3: sw $t2, 128($s1) オフセットの役割り 命令 sw $s0,8($t0) の動作 • レジスタ $t0 は値 10000 を保持していると仮定 • 8($t0) が表す番地: 10000+8 = 10008 • レジスタ $s0 の内容 -473 が 10008 番地の語に ストア(格納)される プロセッサ 主記憶 9996 -473 10000 2005 10004 76401 10008 -473 -1649 10010 $t0 : 10000 $t1 : 42000 ・・・・・・ $s0: 0 -473 ・・・・・・ 10 変数とロード命令・ストア命令の関係 ※ 変数は主記憶内の連続した領域に割り当てられる(前提) b 変数aの番地は$gpに 格納されているとする 例: 主記憶 変数領域 ※ 変数領域の先頭番地をレジスタ($gp) に入れておき,そのレジスタにオフセットを $gp → a 付けて変数にアクセスする c 変数aの値を$s0レジスタにロードする lw $s0, 0($gp) 変数bの番地=aの番地+4 =$gp+4 $s2レジスタの内容を変数cにストアする sw $s2, 8($gp) 変数cの番地=aの番地+8 =$gp+8 … 例 変数 a と b の値を交換するプログラム アセンブリ言語のプログラム C言語のプログラム w=a; a=b; b=w; $gp a 1 2 lw $t0, 0($gp) sw $t0,8($gp) w = a; 3 4 lw $t0, 4($gp) sw $t0, 0($gp) a = b; 5 6 lw $t0, 8($gp) sw $t0, 4($gp) b = w; これは説明用の行番号 b w ある変数の値を別の変数に代入するには, ロード命令とストア命令を使い,レジスタを 経由しなければならない 11 ロード命令・ストア命令の機械語形式 ロード命令 rs op offset ベースレジスタ番号 格納先レジスタ番号 100011 31 rt 26 25 オフセット 16 15 21 20 0 ストア命令 op rs rt offset 101011 ベースレジスタ番号 格納元レジスタ番号 オフセット 31 26 25 16 15 21 20 op(operation;命令) : rs : rt : offset : 6bit 5bit 5bit 16bit 0 命令の種類を表す ベースレジスタを指定する 格納先 / 格納元 レジスタを指定する オフセットを指定する (- 32768 ~ 32767 ; 2の補数表現) ロード命令の機械語 レジスタ番号 レジスタ名 (アセンブリ表記) lw $s1,100($gp) op 100011 31 rs rt 11100 26 25 offset 10001 21 20 $gp (28) 0000 0000 0110 0100 16 15 100 16bitで2の補数表現 $s1 (17) 機械語の16進表記 0 8F910064 lw $t2,-100($gp) op rs rt 100011 11100 01010 31 26 25 $gp (28) 21 20 offset 1111 1111 1001 1100 16 15 $t2 (10) 機械語の16進表記 0 -100 8F8AFF9C 12 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 $zero -----------------------------------$t0 $t1 $t2 $t3 $t4 $t5 $t6 $t7 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 $s0 $s1 $s2 $s3 $s4 $s5 $s6 $s7 $t8 $t9 --------$gp ---------------- ストア命令の機械語 レジスタ番号 レジスタ名 (アセンブリ表記) sw $s1,100($gp) op rs rt 101011 11100 10001 31 26 25 21 20 $gp (28) offset 0000 0000 0110 0100 16 15 0 100 16bitで2の補数表現 $s1 (17) 機械語の16進表記 AF910064 sw $t2,-100($gp) op rs rt 101011 11100 01010 31 26 25 $gp (28) 21 20 offset 1111 1111 1001 1100 16 15 $t2 (10) 機械語の16進表記 0 -100 AF8AFF9C 13 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 $zero -----------------------------------$t0 $t1 $t2 $t3 $t4 $t5 $t6 $t7 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 $s0 $s1 $s2 $s3 $s4 $s5 $s6 $s7 $t8 $t9 --------$gp ----------------
© Copyright 2024 ExpyDoc