CPUをつくろう -CPUとは-

CPUとは何だろう

前回まででCPUを作るために必要な基礎的な知識を紹介した。これからCPUを作っていく事になるのだが、まずそのCPUとは何なのか? これから作るものが何なのか分からないと作りようがない。

「CPUとは中央演算装置、コンピュータの頭脳にあたる」という説明が良く見られるが、これからCPUを作るにはそれだけの理解ではたりない。どういう構造で何をしているのか。

まずCPUには主要装置として以下の装置が含まれる。(下図の赤枠の中の部分)

  • ALU(演算装置):計算をする装置
  • レジスタ:計算途中の値を一時的に保存する装置
  • 制御装置:ALUやレジスタ間のデータの流れを制御する装置
  • 命令デコーダ:メモリから読み出した命令を解釈する装置
  • プログラムカウンタ:メモリの番地を指定する装置

加えて以下の周辺装置も必要である。

  • クロック:CPU内の各装置の動作を同期させる信号
  • メモリ:命令とデータを格納する装置
  • 入力装置:計算データ等を入力する装置
  • 出力装置:計算結果のデータ等を出力する装置

クロック

クロックとは、HiとLoを一定周期で繰り返すパルス波形のこと。プログラムカウンタ、制御装置、レジスタ等に入力しCPUを動作させる信号である。

メモリ

CPUに実行させる命令とデータを記憶させておく装置。メモリにはROMとRAMがあるが、今回作るCPUでは、このメモリはROMとする。

メモリは基本的には1区画が8bitになっており、1区画の中に命令やデータを1つずつ格納できる。そして、その何区が何個も連続している。区画は1区画毎に先頭から0、1、2…というアドレス(番地)が割り振られている。

下図の例ではアドレス0に0b0110 1101という値が格納されている。

プログラムカウンタ

メモリには命令が1つずつ格納されているのだが、CPUはこの命令をアドレス0から順々に実行していく事になる。プログラムカウンタとは次に実行するべきメモリのアドレスを指し示す装置である。

クロックが入力されるたびに指し示すアドレスをカウントアップして行く。

命令デコーダ

メモリから読み出した命令はそのままではCPUを動作させることが出来ない。命令デコーダは命令をCPUが解釈できる信号に変換する装置である。

制御装置

CPUはレジスタの値を演算装置に転送して計算したり、演算装置で計算した結果の値をレジスタに格納したりする。前者のデータの流れは”レジスタ→演算装置”となっているし、後者は”演算装置→レジスタ”となっており、それぞれでデータの流れる向きが違う。

制御装置は、メモリから読み取った命令に応じて、このデータの流れを切り替える装置である。

レジスタ

演算装置で計算した値や、入力装置から入力した値を一時的に格納する装置。データ幅はCPUによって様々だが、このレジスタのデータ幅が広いほどCPUで扱える命令やデータの範囲が広くなり、CPUは高性能になる。データ幅が8bitのものを8bitCPUとか、32bitのものを32bitCPUと呼んだりする。

レジスタは通常2つ以上あり、Aレジスタ、Bレジスタという様に個別の名前がつけられている。

データを一時的に格納するものにはRAMというメモリもあるが、レジスタはCPUに内蔵されておりRAMよりも超高速にデータの転送が可能となっている。RAMは計算結果を格納するのに対し、レジスタは更に一時的な計算途中の値などを格納する。

ALU(演算装置)

CPUの心臓部、計算をする装置。具体的にはレジスタや入力装置からデータを入力し、入力した値に対し加算や減算を行う。

入力装置

計算させたい値をCPUに入力する装置。

出力装置

計算した結果等の値を出力する装置。

CPUをつくろう -2進数と16進数編2-

16進数の必要性

コンピュータは数を0と1のみの2進数で表現する。この2進数、人間にとっては弱点がある。桁数が多くなると何が書いてあるか分かりづらいのだ。例えは0b01100011、これはぱっとみて全体の桁数も分かりづらいし、どの桁が1でどの桁が0かもとても見づらい。

そこで人間が理解し易いように16進数を用いる。

16進数

16進数とは、16から1を引いた数”15”で桁上がりをする数の表現方法である。1から15までを1桁で表現するのだが、残念ながら10以降を1桁で表現できる数字は無い。よって10〜15をアルファベットのA〜Fで表す。10進数、2進数、16進数の対比を示す。

10進数2進数16進数
000
111
2102
3113
41004
51015
61106
71117
810008
910019
101010A
111011B
121100C
131101D
141110E
151111F

ここでも16進数は10を”イチゼロ”と言い、1Bは”イチビー”と言う。

2進数と同様に、これが16進数表記だと分かるように頭に”0x”をつけ、0x10や0x1Bという様に記述する。

2進数は4bit毎に間を開けて書いておくと16進数に変換するときに見やすくなる。2進数4bit分で16進数1桁になるからだ。

2進数を4bit毎に区切り、4bitづつ16進数に変換していけば16進数表記になる。0b0000 0000は0x00、0b0110 1100は0x6Cとなる。

16進数を使えば少ない桁数で2進数を表現できるため、数の把握が容易になる。

CPUをつくろう -2進数と16進数編-

2進数

コンピュータは全ての数を0と1のみで表現する。対して人間は0〜9までの数字を使って数を表現する。0〜9をで表現する数を10進数、それに対し0、1のみで表現する数を2進数という。

10進数と2進数の対比を以下に示す。

10進数2進数
00
11
210
311
4100
5101
6110
7111
81000
91001
101010
111011
121100
131101
141110
151111

10進数は、0,1,2…と進んで行き9まで来ると桁上がりして10となる。10進数の10から1を引いた数”9”まで来ると桁上がりする。

2進数は、2から1を引いた数”1”まで来ると桁上がりする。つまり全ての桁が1になると桁上がりをする。例えば1の次は桁上がりして10となる。ちなみに2進数の10は”ジュウ”ではない。10と書いて”イチゼロ”とか”イチマル”と言う。

ここで、10と書いても10進数のジュウなのか、2進数のイチゼロなのか区別がつかないため、普通は10進数の場合は頭に”d”をつけてd10のように書き、2進数の場合は頭に”0b”をつけて0b10と書く。dはデシマルの略、bはバイナリの略である。10進数のdは省略する場合が多い(と思う)。

2進数の場合、1桁を”bit(ビット)”という。bitというのがコンピュータで数を表す最小単位となる。0b10は2bitだし、0b1111は4bitである。

bitが8つ集まった8bitの事を”Byte(バイト)”という。0b11111111は1Byteである。

コンピュータで2進数を扱う場合、表記を1Byte単位に合わせて書く場合がある。0b1なら0b0000 0001、0b11110なら0b0001 1110と書く。この際4bit毎にスペースを入れて書くと読みやすくなる。(理由は後の16進数の項目で説明する)

10進数と2進数の変換

・10進数から2進数へ

10進数を2進数に変換するには、変換したい10進数の数字を商が0になるまで2で割り続け、余りを求めていく。求められた余りが変換後の2進数となる。

例えば35を2進数に変換すると、0b0010 0011となる。

・2進数から10進数へ

2進数から10進数に変換するには、各bitの値にその桁の「重み」を掛ける。重みという言葉が出てきたが、n桁目の重みは2のn-1乗となる。例えば、3桁目の重みは2の2乗となって4である。そして最後に各桁で算出した値を足し合わせる。

先ほどの0b0010 0011を10進数に変換すると、下記の通り35となる。