X87

**x87**はx86アーキテクチャー命令セットのうち浮動小数点数関係のサブセットのことである。もともとはx86系CPUと協調して動作するオプションの浮動小数点数コプロセッサ (FPU) でサポートされる、8086命令セットの拡張機能であった。これらのマイクロチップは型番の末尾が"87"となっていた。これはNPX (Numeric Processor Extension) としても知られる。基本命令セットに対する他の拡張と同様、x87命令は動作するプログラムを構築するのに必須のものではないが、頻出する数値処理のハードウェアおよびマイクロコード実装により、これらの処理を対応する機械語ルーチンが行うよりもはるかに高速に行うことができる。x87命令セットは加算、減算、比較の基本的な浮動小数点演算だけでなく、タンジェント関数やその逆関数などの超越関数の数値演算を含む。

Intel 80486以降のほとんどのx86プロセッサーはこれらのx87命令をメインCPUに含んでいるが、この用語は今でも命令セットの一部を指すのに用いられることがある。PCにおいてx87命令が標準になる前、コンパイラやプログラマは浮動小数点演算を実行するためにかなり遅い浮動小数点演算ライブラリを使用していた。この手法は（低価格の）組み込みシステムでは依然一般的である。

取り扱う浮動小数点データのフォーマットならびに演算の仕様はIntel 8087, Intel 80287は概ねIEEE-754に準拠しているが、非互換の部分がある。これは、IEEE-754 の策定にIntelが参画していたものの、仕様が確定しないうちに製品化されたためである。Intel 80187, Intel 80387, ならびにIntel 80486以降のCPUに内蔵されるFPUは、完全にIEEE-754に準拠している。

## 開発・製造を行った企業
Intel 8087またはそれ以降のモデルと互換性があるFPUを設計または製造した企業を掲げる。
*AMD (*80287互換チップとしてAMD 80C287, 387, 486DX, 5x86, K5, K6, K7, K8*)
** AMD 80C287は、Intel社のマイクロコードを使用することで100%の互換性を維持している。
*チップス・アンド・テクノロジーズ (*Super MATH*コプロセッサ)
*Cyrix (*FasMath*, *Cx87SLC*, *Cx87DLC*他, *6x86*, *Cyrix MII*)
*富士通 (初期の*Pentium Mobile*他)
* (*80387* *486DX*)
*IBM (様々な*387*や*486*の設計)
*IDT (WinChip, *C3*, *C7*, *Nano*, 他)
* (*2C87*, *3C87*, 他), LC Technology (*Green MATH*コプロセッサ)
*ナショナル セミコンダクター (*Geode GX1*, *Geode GXm*, 他)
*NexGen (*Nx587*)
*Rise Technology (*mP6*)
*STマイクロエレクトロニクス (*486DX*, *5x86*, 他)
*テキサス・インスツルメンツ (*486DX* 他)
*トランスメタ (*TM5600* *TM5800*)
*ULSI (*Math·Co*コプロセッサ)
*VIA (*C3*, *C7*, *Nano*, 他), Xtend (*83S87SX-25*他コプロセッサ).

## アーキテクチャーの世代

### Intel 8087

**8087**はインテルによって設計された最初の16ビットプロセッサ用数値演算コプロセッサ（インテルでの呼称は*NDP; Numeric Data Processor*）。これはIntel 8088または8086と接続できる様に設計されている。以下のような演算が可能である。
*算術演算
:加算、減算、乗算、除算、平方根、絶対値など
*超越関数
:tan, arctan, 2x-1, y*log2x, y*log2(x+1)
*定数のロード
:0, 1, π, log102, loge2, log210, log2e

### Intel 80187
**80187**(80C187)はIntel 80186 CPU用の数値演算コプロセッサ。80188は8ビットデータバスを持っているため8087しか使用できない。80187は80186や80188と同時期には登場せず、80287や80387の後に登場した。8087と同じメインプロセッサへのインターフェイスを持っているにもかかわらず、コアは80387のもので、IEEE 754に完全に準拠し、また全ての80387拡張命令を実行することができた。

### Intel 80287

**Intel 80287**は、80286のために用意されていた数値演算コプロセッサ。

8086同様80286は整数計算の命令しか備えていないため、80286だけで浮動小数点演算を行うには別途ライブラリを用意する必要があった。80287を80286の搭載されたコンピュータにセットすると、浮動小数点計算の命令を使うことができるようになる。また、互換性のため、アプリケーションからはNDPがあるように見せかけて、実際は割り込みルーチン内に浮動小数点演算ライブラリを組み込む手段も用意されていた。これは、NDPの有無に係わらずアプリケーションからは同一の方法で浮動小数点演算を行える様にする仕組みであったが、この方法は非常に遅いため、あまり使われる事は無かった。この手段を使わず、浮動小数点演算命令をエミュレーションライブラリにより実行していた場合は、NDPを利用するためにはアプリケーションソフトウェア自体も再コンパイルが必要であった。

80287は、当初、協調して動作する80286と同一クロック周波数で同期して動作する見込みが立たなかったため、厳密な意味でのコプロセッサではなく、単なる入出力プロセッサとして設計された。このため、逆に、より高速なクロックで動作させる事もできた。また、このことにより、あまり意味はないがソフトウェア及び外部回路の工夫により、1つの80286に複数の80287を接続したり、他の種類のCPU、例えば386や、Vシリーズなどに80287を接続する事もできた。逆に、80286に、他の種類のNDPを接続する事も可能であった。

NECのPC-9801VXなど、80286を搭載したコンピュータには、80287を挿入することができるソケットが用意されていた。

後にIEEE 754への対応度を改善した80287XLが登場した。

### Intel 80387
**Intel 80387**は、インテルの32ビットCPUである80386用の数値演算コプロセッサ。インテル最初のIEEE 754対応品となった。原理的にはこれ以前のプロセッサである8087や80287と同じである。80386を搭載したコンピュータには、80387を挿すことができる専用のソケットが用意されていた。80386SX用には**80387SX**がある。

80387では、FSIN, FCOS, FSINCOS, FPREM1, FUCOM, FUCOMP, FUCOMPP命令が追加された。

コプロセッサとのインターフェイスには特許が取得されていなかったため、IDTやサイリックスが、さらに高速に演算を行う互換品を製造していた。

File:KL Intel 80387.jpg|i387
File:KL Intel i387SX.jpg|i387SX
File:80386with387.JPG|i386DXとi387DX
File:Intel 387 arch.svg|16ビットバレルシフタとユニット付きi387マイクロアーキテクチャ


### Intel487

**Intel487**は、Intel486の、内蔵FPUをオミットした廉価版である486SX用の外付けFPUコプロセッサという名目で発売されたプロセッサである。実態は、486SXの全機能を乗っ取り、フル機能の486DXとして働くものであり、コプロセッサというよりは、後のオーバードライブプロセッサに近い。

486は最初から数値演算コプロセッサの機能が統合されて開発されたため、コプロセッサは必要なかった。しかし、後に数値演算機能のない廉価製品の486SXが発売されると、それ用の487SXが用意された。内部は、486DXとほとんど同等である。

クロックダブラを搭載したSX2が発売されると、487SX2が追加された。こちらの内部はDX2である。

#### 原理
従来のx87シリーズは、x86シリーズCPU用の数値演算コプロセッサとして開発されているが、486は数値演算コプロセッサの機能を内蔵する形で開発され、浮動小数点演算機能のみを後から追加する必要がなく、外部の数値演算コプロセッサと通信する機能を持たない。

しかし、廉価版として内蔵FPUを持たない486SXが登場したため、別の方法で浮動小数点演算機能を追加する必要ができた。このため487SXは486DXと同等のCPU機能を搭載し、システムは、487SXが装着された場合には従来のCPUを停止させて487SXをCPUとして動作させることとした。このようにしてシステムへの数値演算コプロセッサ機能の追加を実現したが、増設により従来の80x87シリーズと同等の役割を果たしているように見えることから、従前の命名規則による487SXという名称にされている。

487SX用スロットが用意されていない486SX搭載機では、（それが可能なように設計されていれば）CPUを単に486DXに乗せ変えることで浮動小数点演算機能に対応できる。このような考えはオーバードライブプロセッサに引き継がれた。また、486SX2を最後にFPU非内蔵モデルは消えたため、x86用数値演算コプロセッサは消滅した。

マルチプロセッサに対応するための機能は無いので、486SXと増設した487SXを同時に使用することはできない。

### Pentium Pro
Pentium Pro世代から内蔵のFPUにFCMOV, FCOMI命令が追加された。これらの命令はCPUIDのCMOVビットがセットされていれば使用できる。

### Pentium III
Pentium III世代からFXSAVE, FXRSTOR命令が追加された。これらの命令はCPUIDのFXSRビットがセットされていれば使用できる。

### Pentium 4 (Prescott)
Pentium 4 (Prescott)世代から内蔵のFPUにFISTTP命令が追加された。この命令はCPUIDのSSE3ビットがセットされていれば使用できる。

### Haswell
CPUIDで「Deprecates FPU CS and FPU DS」ビットがセットされているとFXSAVE命令などで、FPU CS, FPU DSを保存しない。これによりFPU CS, FPU DSが保存されるという元々の仕様に従って作成された過去のソフトウェアが動作しなくなる。

## 関連記事
*MMX
*ストリーミングSIMD拡張命令 (SSE)
*3DNow!
*SIMD

## 脚注

* 

## 参考文献
* Robert L.Hummel著 槌田浩一訳 80x86/80x87ファミリー・テクニカルハンドブック　技術評論社　ISBN 4-87408-588-1
* 

## 外部リンク
*Everything you always wanted to know about math coprocessors
*The Difference Between x87 Instructions FSIN, FCOS, FSINCOS, and FPTAN and Their Mathematical Counterparts