目次
はじめに
X680x0の内蔵音源は、8チャンネルのFM音源(OPM…YM2151)と、15.625kHzまでのサンプリング周波数で再生できる1チャンネルのPCM音源(ADPCM…MSM6258V)で構成されています。PCMデータをステレオ再生する(左と右で別々のPCMデータを再生する)ためには最低でも2チャンネルのPCM音源が必要ですから、ハードウェアを追加しない限り、普通の方法ではPCMデータをステレオで再生することはできません。しかし、限られた内蔵音源を駆使してPCMデータをステレオ再生する試みは過去に幾つかありました。
X680x0において広く公開されたPCMのステレオ再生プログラムとしては、古くはOh!X 1993年3月号の“(で)のショートプロぱーてぃ”のコーナーに掲載された秋山嗣晴氏によるPCMST.Sに遡ります。PCMST.Sによるステレオ再生の方法は、ステレオのPCMデータを細切れにしてADPCMで左右交互に出力し、左右の切り換えを高速に行うことでADPCMを疑似的にステレオ化するというものでした。私の知る限り、X68000の内蔵音源のみでPCMデータをステレオ再生する試みを広く発表されたプログラムとしてはPCMST.Sがおそらく初めてであり、私も当時その発想と実現力に感動を覚えつつOh!Xに掲載されていたプログラムをせっせと入力した覚えがあります。
ただ、PCMST.Sの方法では実際に左右同時に(意図した)音が出るわけではなく、また、PCMデータを細切れにしているためにノイズが多いのが難点でした。なお、このプログラムはその後バージョンアップされて電脳倶楽部VOL.99(1996年8月号)にPCMST.XとWAVST.Xとして掲載されています。
電脳倶楽部にPCMST.Xが掲載されたことがきっかけで、伊倉"DigitalJunkie"晴読氏が別のアプローチでPCMデータをステレオ再生するプログラムSTPLAY.Xを作り、電脳倶楽部VOL.100(1996年9月号)に掲載されました。STPLAY.Xは、右側の音をADPCMで、左側の音をFM音源で再生するという方法で、左右同時に15.625kHzでPCMを再生することができました。
FM音源を4チャンネル使うことで1チャンネルのPCM音源をエミュレートできることは同氏の手によって電脳倶楽部VOL.78(1994年11月号)に掲載された“志村けんX”というプログラムで既に証明されており、STPLAY.Xはそれを応用したものでした。
今回の試み
さて、私が激光電脳倶楽部VOL.6に向けて音に関係する記事を書くことになったとき、私は自分もPCMのステレオ再生を試みようと思いました。それも激光電脳倶楽部なのですから、CD2PCMT.Xなどを使うことで音楽CDから容易にデータを供給できる(勿論、個人的な使用の範囲でですが)サンプリング周波数が44.1kHzのステレオのPCMデータを直接再生できるプログラムを作りたくなりました。
前述の通り、X680x0の内蔵ADPCM音源は最高で15.625kHzまでのサンプリング周波数にしか対応しておらず、ADPCMでこれよりも高い周波数でPCMデータ再生することは不可能です。しかし、STPLAY.Xで使われていたFM音源の処理能力にはまだ少し余裕があります。そこで、私は15.625kHzのADPCMの使用はさっさと諦めて、左右両方のチャンネルをFM音源で再生して再生周波数をADPCMよりも上げられないかと考えました。
FM音源の処理速度の限界
諦めついでにもう1つ。アセンブラでFM音源レジスタを直接叩いたことがある人ならば知っていることですが、FM音源レジスタの読み書きはFM音源アドレスポート($00E90001)とFM音源データポート($00E90003)という2つのポートをアクセスすることによって行います。ここで、それぞれのポートに書き込んだ後、FM音源データポートの書き込みビジーフラグ($00E90003のMSB)がクリアされるまで次の書き込みを行ってはいけないという決まりがあります。FM音源データポートへの書き込みの後ビジーフラグがクリアされるまでにかかる時間は、FM音源LSI(YM2151)の入力クロックの68クロック分です。YM2151には4MHzのクロックが入っていますから、FM音源データポートへの書き込みを繰り返す場合には少なくとも17μ秒以上間隔をあけて行わなければならないことになります。実際にこれよりも短い間隔でFM音源データポートに書き込もうとすると、書き込みに失敗して期待通りの音が出なくなります。
音楽CDのサンプリング周波数は44.1kHzです。単純に割り算をすると、1周期あたり約22.6757μ秒しかありません。しかもステレオですから、1周期の間に2チャンネル分のデータを処理しなければなりません。
FM音源データポートへの書き込みは1回あたり最低でも17μ秒以上かかり、2チャンネル更新するためにはTLを2つ更新するため少なくとも2回データポートに書き込まなければなりませんから、17*2=34>22.6757であり、実際に動かして確かめるまでもなく、FM音源のみでPCMデータをステレオで44.1kHzという周波数で再生することが不可能であることがわかります。
仕方がないので、44.1kHzでのステレオ再生は諦めて、周波数を落としてステレオ再生することを考えましょう。
FM音源でPCMデータを再生する方法
ここで説明する方法は伊倉"DigitalJunkie"晴読氏が“志村けんX”やSTPLAY.Xで使用した方法を私が改良したものです。
- 矩形波に近い音を作る
まず、FM音源を1チャンネル使って、波長が非常に長くてなるべく矩形波に近い音を作ります(図1)。この波形が、変位が最大になった状態をどれだけ安定して維持できるかが、再生できるPCMの音質に影響してきます。
矩形波に近い音のパラメータ(FM音源レジスタに設定する値)は、次のような方法で独自に決定しました。
FM音源のレジスタにどのようなパラメータを指定するとどのような音(波形)が作られるのかを数値計算で予測してグラフを描き、それがなるべく矩形波に近付くようにパラメータを調整して、目的に合ったパラメータを見つけるのです。
変調を強くかけたほうが矩形波に近付けやすいので、ここではコネクションを0にして4つのスロットを直列に接続します。フィードバックは使いません。すると、生成される波形は時刻tに関する次のような関数で予測できます(波形を予測するための式は『Inside X68000』の記述を参考にしました)。
変位(t)=α(C2)*sin(MUL(C2)*t
+α(M2)*sin(MUL(M2)*t
+α(C1)*sin(MUL(C1)*t
+α(M1)*sin(MUL(M1)*t))))
α(M1)=10^(-0.75/20*TL(M1)+e/2)
α(C1)=10^(-0.75/20*TL(C1)+e/2)
α(M2)=10^(-0.75/20*TL(M2)+e/2)
α(C2)=10^(-0.75/20*TL(C2)+e/2)
MUL(n)=スロットnのMUL(周波数の倍率)で掛ける値(0.5,1〜15)
TL(n)=スロットnのトータルレベル(0〜127)
t=時刻
e=2.718281828459(自然対数の底)
グラフを描きながらMUL(n)とTL(n)を少しずつ変化させ、なるべく波長が長くて矩形波に近くて最大変位が安定している波形を生成するパラメータを探した結果、次のようなパラメータが得られました。
MUL(M1)=1,MUL(C1)=1,MUL(M2)=1,MUL(C2)=0.5
TL(M1)=45,TL(C1)=36,TL(M2)=34,TL(C2)=0
または
TL(M1)=47,TL(C1)=38,TL(M2)=35,TL(C2)=0
この矩形波に近い音の波長は、ほぼ0.103563秒であることが実験的にわかっています。
- 変位の制御
コネクション0で生成される波の振幅は、キャリア2(C2)のトータルレベル(TL)を変化させることで、キーオンしたままリアルタイムに変動させることができます。TL=0のとき振幅は最大になり、TL=127で最小(無音)になります。矩形波が最大変位を安定して維持している期間は、振幅が変位そのものを表しているので、C2のTLを操作することでリアルタイムに変位を指定できることになります。TLを変化させることで生じる矩形波の変位の変動が、FM音源でPCMデータを再生する場合の音の素になります。
なお、TLで指定した数値に対して変位が指数関数的に変化するのに対して、一般的にPCMデータは直線的な値なので、PCMデータからTLに与える値を求めるためには対数関数による変換が必要です。具体的には、TLに応じて出力される変位は
L=10^(-0.75/20*TL)
という式で計算されるLに比例します(図2および図3)。
PCMデータは、大雑把な言い方をすれば音の波を一定の間隔で細切れにして得られる変位を並べたものですから、それを対数関数で変換してC2のTLに流し込んでやれば、FM音源でPCMデータを再生できるということになります。なお、1データ毎に対数関数を計算していたのでは遅くて仕方がないので、実際にはPCMデータの変位からTLへの変換にテーブルを使います。16ビットのPCMデータを7ビットのTLに変換するために64KBのテーブルを使います。
- 複数の矩形波を重ねる
さて、TLで変位を自由に操れるといっても、矩形波(に近い音)が1つだけでは安定して使える期間が短すぎて、PCMデータを長時間連続して再生することができません。そこで、この矩形波に近い音をCh1〜Ch4の4つのチャンネルでCh1→Ch2→Ch3→Ch4→Ch1→…の順序で、なるべく正確に1/4周期ずつずらして発生させます(図4)。
この後、Ch1〜Ch4がそれぞれ安定して最大変位を維持している範囲を1/4周期ずつピックアップし、それぞれその範囲でTLを操作します。
- STPLAY.Xの場合
STPLAY.Xでは、PCMデータをTLに変換して乗せるチャンネルの順序が常にCh1→Ch2→Ch3→Ch4 →Ch1→…となっていて、使用していないチャンネルはすべて最大変位(TL=0)の半分の変位(TL=8)に固定されていました。この方法では、Ch1とCh3、Ch2とCh4がそれぞれ1/2周期ずつずれていますから、使用するチャンネルの変位をTL=8の前後で高速に変動させてやれば、最終的には変位0を挟んで上下に高速に変動する波が作り出されます(図5)。
この方法の欠点は、出力される音の最小の変位をTL=8に割り当ててあり、図2からわかるようにTL=8の近辺では変位の分解能が低いために波形の再現性が悪く、音量に関係なく大量の高周波ノイズが発生してしまうことです。
- 新しい方法
私が採った方法は、見掛けはSTPLAY.Xの方法よりもむしろ簡単です。Ch1とCh3、Ch2とCh4はそれぞれ1/2周期ずつずれているので、Ch1の変位が+側にあるときCh3の変位は-側にあります。そこで、Ch1の変位が+側にある期間は、+側のPCMデータをCh1に、-側のPCMデータをCh3に乗せるのです。使っていないチャンネルはすべて無音(TL=127)に固定します。他のチャンネルを使うときも同様です(図6)。
この新しい方法では、出力される音の最小の変位をTL=127に割り当ててあり、図2からわかるようにTL=127の近辺では変位の分解能が非常に高いので、波形の再現性がSTPLAY.Xの方法よりも圧倒的に良くなります。
- 変位の符号に応じたチャンネルの切り換え
ところで、当然のことですが、変位が+側にあるときと-側にあるときで使用するチャンネルを変えるということは、変位の符号が変わる度に使用するチャンネルを切り換えなければならないということです。チャンネルを切り換えるにはそれまで使っていたチャンネルを無音にした上で次に使うチャンネルにデータを乗せなければなりません。すると、チャンネルを切り換える瞬間に、最短でもFM音源レジスタを1つ更新する(1つのチャンネルを無音にする)のにかかる時間だけ、本来のデータと異なる変位を出力してしまうことになります。たとえ一瞬でも局所的に本来のデータと大きく異なる変位を出力するとプチノイズになってしまうので、いかにしてなるべく正しい変位を出力しつつチャンネルを切り換えるかが重要になってきます。
変位の符号が変わるということは、極端な高周波成分を含んでいない限り、その前後の変位は0に近いはずです。そこで、0を挟んで変位の符号が変わっているところの前後(どちらか一方が+側で他方が-側)で、前後のうち変位が0に近い側の変位を強制的に0にすることにします。波形が少し乱れますが、前述のように極端な高周波成分が含まれていなければもともと0に近かったデータですから、音質の大きな劣化はないはずです(図7)。
変位が0になっていれば、チャンネルの切り換えは簡単です。変位が0のデータを出力すればそのチャンネルは無音になりますから、そのまま次のデータから次のチャンネルに移ることができます。
- 1/4周期毎のチャンネル遷移
ところで、Ch1〜Ch4がそれぞれ安定して最大変位を維持している範囲を1/4周期ずつピックアップすると書きましたが、実はこれが非常にシビアな処理になります。再生が続いている間は4チャンネルともキーオンしたままですから、波の位相はMPUの動作とは無関係に正確に進行して行きます。これに追従して正確なタイミングで使用するチャンネル(TLを操作するチャンネル)を切り換えないと、あっという間に最大変位が安定している範囲を外れ、期待通りの音が出なくなってしまうのです。
STPLAY.Xでは上記の音の波長の値が不正確で、短時間で破綻してしまうため数分間隔でキーオンからやり直すことになっており、キーオンし直すときに異音が出てしまっていました。今回私は実験で上記の音のかなり正確な波長として0.103563秒という値を得、少なくとも1時間程度ならばキーオンし続けても破綻しないようにすることに成功しました。
実際に矩形波に近い音の波長を管理する方法は以下の通りです。
まず、非常に短い間隔でFM音源レジスタを更新するために、TIMER-Dによる割り込みを使います。TIMER-DはCONFIG.SYSにPROCESS=の指定をしたときにHumanがバックグラウンド処理のために使用しますが、PCMを再生している最中にバックグラウンドタスクを回すだけのMPUパワーが残っているとはとても思えませんから、ためらわずにTIMER-D割り込みをHumanから奪って使います。
TIMER-D割り込みの割り込み間隔は1μ秒単位で指定できますが、FM音源レジスタを1つ更新するのに18μ秒以上かかるので、割り込み間隔をあまり短くしても意味がありません。そこで、X68030の場合はデフォルトで22μ秒間隔で割り込むことにします。周波数に換算すると45.455kHzになります。ステレオ再生時は1サンプリングあたりFM音源レジスタを2回更新する必要があるので、22.727kHzになります。これは44.1kHzの半分の22.05kHzよりも少し高い周波数です。
FM音源でPCMを再生する場合、最も厄介なのが、FM音源で発生させた矩形波に近い音の波長の管理です。前述の通り、FM音源で発生している音の波長は0.103563秒であり、割り込み間隔の22μ秒で割ると1周期あたりの割り込み回数が約4707.41回ということになります。キーオンは4707.41/4=1176.85より割り込み回数にして1176〜1177回の間隔で行えばよいとして、その後の1/4周期毎のチャンネル遷移を如何に正確に行うかが問題です。22μ秒という短い間隔の割り込み要求をMPUが1回も取りこぼさないという保証はなく、1周期あたり1回ずつずれただけでも誤差が蓄積して数秒から数10秒で破綻してしまいます。特に後でディスクアクセスをしながらPCMをステレオ再生しようとしていることを考えると、割り込みを取りこぼすのは必至で、TIMER-Dの割り込み回数だけに頼っていたのでは波長の管理はできないという結論に達します。
そこで、TIMER-Cのカウンタを併用することにします。TIMER-Cは普段は1/100秒カウンタとしてカーソルの点滅などに使用されているものです。TIMER-Cを16μ秒単位でダウンカウントするモードにして、256回でオーバーフローするように初期値を与えます。すると0.103563/(0.000016*256)=25.283935546875、0.283935546875*256=72.6875となって、1周期の間にTIMER-Cは正確に25回オーバーフローしてから元の値よりも72.6875だけ減ることがわかります。これを利用して、TIMER-DのカウントのみでTIMER-Cが25回オーバーフローする頃まで進んでから、残りの時間をTIMER-Cが前回よりも72.6875小さい値になるまでTIMER-D割り込みの中でTIMER-Cのカウンタを監視しながら進めることで、1周期の終わりを決定します。実際にはTIMER-Cのカウンタは整数なので、72.6875*256=18608から「ワードサイズのワークから毎回18608ずつ引き、その上位バイトを採用する」という方法でTIMER-Cの値を予測して比較します。
この方法によって0.103563秒という微妙な波長を(平均して)極めて正確に維持することが可能になり、1時間くらいキーオンしたままでも大きな誤差が生じず、再生しつづけることができるのです。
ところで、1/4周期進んだところで強制的に次のチャンネルに切り換えてしまうと、変位が大きな区間で切り換えることになった場合にプチノイズが発生してしまいます。今回採用した矩形波に近い音は、独自に作り出したパラメータで生成されていることもあって、最大変位が安定している範囲が1/4周期の0.02589秒よりも約70%長い0.04423秒あることがわかっています。つまり、あまり厳密に1/4周期毎にチャンネルを切り換えなくても、チャンネルを切り換えるタイミングが多少前後した程度ならば問題なく再生できるのです(勿論、長時間再生したとき1周期の長さの平均が 0.103563秒になるように厳密に制御する必要があります)。
変位の符号が変わるときに変位を強制的に0にしているので、1/4周期が経過しても少しの間はチャンネルを変えずに変位の符号が変わるのを待ち、変位の符号が変わった瞬間に符号と同時に1/4周期毎のチャンネルの遷移も行うことにしました。このようなチャンネル遷移の遅延はあまり長くはできませんが、たいていのPCMデータは符号が頻繁に入れ替わるので、少し待つだけでプチノイズはほとんど除去されます。大きな低周波成分があるときは少し待っても変位の符号が変わらないことがあるので、そのような場合は途中で諦めて強制的にチャンネルを遷移します。
ステレオ化
前述のように、FM音源でPCMを再生するためには4チャンネル必要です。FM音源には全部で8つのチャンネルがありますから、すべてのチャンネルを使えばFM音源のみでPCMをステレオ再生することができます。
注意しなければならないのは、FM音源レジスタは2つ同時に更新できないということです。そのため、右側の変位を更新するタイミングと左側の変位を更新するタイミングが微妙にずれてしまいます。この問題を解決するには、PCMデータの周波数を変換するときに、左右の出力データのサンプリング位置をサンプリング間隔の半分だけずらしておかなければなりません。
STPLAY.XではFM音源が担当する音が片側だけだったので、例えばCh1を使っている間はFM音源アドレスポートをCh1のTL($78)に固定してFM音源データポートだけを更新し続けることができました。しかし、ステレオ化する場合、Ch1のTL($78)とCh5のTL($7C)を交互に更新するためにFM音源アドレスポートも毎回更新しなければなりません。そのため、FM音源によるPCMのステレオ再生の負荷はモノラル再生の2倍以上になります。
サンプリング周波数の変換
入力データのサンプリング周波数とFM音源でPCMを再生する際の出力時のサンプリング周波数は異なる場合が多いので、PCMデータのサンプリング周波数の変換が必要です。サンプリング周波数の変換は、PCMデータをOPMデータに変換する前に行います。すなわち、PCM→PCMのサンプリング周波数変換を行います。
S44PLAY.Xでは、次の3通りのサンプリング変換方法を選べるようにしてみました。
- 間引き・伸張
- 直線補間
- 面積補間
- 間引き・伸張
サンプリング間隔が短くなる場合は、データの伸張を行います。1データ毎にサンプリングのタイミングの誤差を蓄積し、誤差が1データ分に達したら最後データを重複して出力します。
サンプリング間隔が長くなる場合は、余った入力データを捨てます。
この方法は非常に簡単なのでリアルタイムに変換できますが、音質は良くありません。
- 直線補間
入力されたPCMデータを直線で補間した上で、出力側のサンプリング間隔でサンプリングしなおします(図8)。
この方法では1データあたり1回の乗算が必要なので、68000ではリアルタイムに変換できません。
- 面積補間
面積補間という呼び方は筆者が勝手につけたものです。
入力されたPCMデータを直線で補間した上で、出力側のサンプリング間隔で刻み、切り取られた各区間の平均の高さ(面積に比例する)を出力データとします。
この方法では1データあたり2回以上の乗算が必要なので、リアルタイム変換ができるのは事実上68060のみです。しかし、今回採用した方法の中では最も音質が良いので、音質にこだわる場合はあらかじめこの方法で変換したデータのファイルを作っておくべきです。
実装
060turboで作り始めたので、.S44ファイルをオンメモリで再生できるようにすることは比較的容易でした。060turboに大容量のSIMMを装着していれば、数分間の曲をオンメモリで再生することができました。
プログラムの名前は、.S44ファイルを直接再生できるということで、S44PLAY.Xにしました。再生中はマシンのパワーをほとんど使ってしまうので他のことをする余裕がないことと、ディスクからデータを読み込みながら再生する機能があるため、他の音源ドライバのように常駐はしません。
次に、ファイルから読み込みながらの再生ができるようにしました。普通に、バッファを2つ使って、一方を再生している間に他方にファイルを読み込んでおくという方法です。68030モードでも動くようになりました。ハードディスクやMOに置いてある.S44ファイルを延々と再生することができます。当然のことですが、フロッピーディスクではデータの供給が間に合いません。
始めは音楽CDからCD2PCMT.Xを使って吸い出して作った.S44ファイルを使ってテストしていたのですが、いちいち.S44ファイルを作るのが面倒になり、数10MB単位のファイルを幾つも転がしておけないので、音楽CDの音声トラックを直接読み込みながらの再生を試みてみました。CD2PCMT.Xのソースを参考にしながら作ったのですが、初めはだいぶてこずりました。SCSIバスを何度もハングアップさせながら作っているうちに、ハングアップしても容易に復帰できるようにするための仕掛けのほうが強力になりました。X680x0がCDプレイヤーになっている様はなかなか壮観です。
S44PLAY.Xの公開済みの最新版は激光電脳倶楽部Vol.7に収録されていますが、バグが取れていないので、月刊電脳倶楽部のほうで更新する予定です。
★1
- フェードイン・フェードアウト
再生中はキーオンしたままなので、FM音源のエンベロープに関するレジスタを操作することで簡単にフェードイン・フェードアウトを行うことができます。フェードイン・フェードアウトの速度の指定が可能です。再生中にいつでも好きなところでフェードアウトを開始することができます。
FMPファイル
ステレオ再生時の片側のサンプリング周波数は最大でも25kHz程度までなので、低いサンプリング周波数でいかに綺麗に再生するかが重要になってきます。しかし、サンプリング周波数の変換を複雑にするとマシンのパワーが不足するのでリアルタイムでの変換ができなくなってしまいます。そこで、高品質な変換を行う場合は、サンプリング周波数の変換(およびPCMからTLへの変換)を済ませたデータを一旦ファイルとして出力しておくことにしました。再生時には変換済みのデータをファイルから読み込みながらただひたすらFM音源レジスタに垂れ流すだけにすることで、特にX68030の場合はFM音源LSI(YM2151)の応答速度ぎりぎりの高いサンプリング周波数で再生できるようになりました。
リアルタイム変換で高品質なステレオPCM再生を行うには68060以上のパワーが必要です。しかし、データをあらかじめ変換しておけば68000でもディスクからデータを読み込みながらの再生が可能です。再生エンジンをゲームなどに実装するときは、あらかじめFMPフォーマットに変換済みのファイルを用意しておくことで、主題歌などを高品質のPCMで再生することが可能です。
困ったこと
- アセンブルできなくて…
S44PLAY.Xのソースリストはオールアセンブラで17000行以上あります。その中に1つで4000行近いマクロ定義があり、マクロ内のローカルシンボルが多すぎるために従来のアセンブラではアセンブルできません。仕方がないのでHAS060.Xのほうを改造してアセンブルしています。★2
- SCSIの強制ソフト転送
ディスクからPCMデータを読み込みながら再生する場合、データの読み込みにDMA転送が使用されていると、MPUが割り込みを取りこぼしてしまうので正常に再生できなくなります。そのため、データの読み込みはソフト転送で行う必要があります。
X68030やMach-2のSCSI-BIOSの高レベル転送コール(_S_READ/_S_READEXT)はSRAMのソフト転送フラグに対応しているので問題ないのですが、SUPERからCompactXVIまでのX68000の内蔵のSCSI-BIOSの高レベル転送コールはソフト転送に対応していないので、これらのコールを自前で展開して低レベルのソフト転送コールを使うようにする必要がありました。
- 040turboには酷?
X68030と060turboの030および060モードでは25kHzで問題なくステレオ再生できます。ところがどういうわけか、040turboの040モードに限ってステレオ25kHzで正常に再生できないのです。68030よりも68040のほうが速いはずなのに…。
これはどうやら040turboの040モード時のバスアクセスが極端に遅いことが原因のようです。060turboの060モードでもバスアクセスは030モードよりも遅くなります。しかし、50MHzの68060はバスアクセスの遅さを補って余りあるパワーを持っているのに対して、25MHzの68040ではそれを補いきれないのです。こればかりは、割り込み間隔を伸ばす以外に対策がなさそうです。
おわりに
S44PLAY.Xは、X680x0用のプログラムの中で最もFM音源を酷使するプログラムの1つと言えると思います。何しろ、FM音源LSI(YM2151)をこれ以上速く制御できないという速度で長時間アクセスし続けるのですから。
PCM音源とは到底呼べないような音源を使ってPCMデータを再生するという発想は、パソコンがまだ8ビットだった時代からあったものです。古くからのOh!Xの読者ならば、あの「サンダーフォース!」の“声”が記憶に残っている人も少なくないのではないでしょうか。
パソコンを特定のソフトを動かすためのプラットフォームとしてだけでなく、パソコンそのものをオモチャとして使う、しかも他の人が思い付かない、あるいは思い付いても誰もやらないような突拍子もない使い方をする、そんな楽しみ方をこれからも続けてゆきたいものです。