Mercurial > hg > Game > Atoc
diff kernel/kernel.c @ 0:42f240cc4bc6
From: 太田 篤志 <atoc@namikilab.tuat.ac.jp>
author | Shinji KONO <kono@ie.u-ryukyu.ac.jp> |
---|---|
date | Tue, 08 Sep 2009 13:44:18 +0900 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/kernel/kernel.c Tue Sep 08 13:44:18 2009 +0900 @@ -0,0 +1,76 @@ +/** + * kernel.c + * SPE 軽量カーネル 本体 + */ + +#include <spu_mfcio.h> +#include "../include/spe_process.h" + +#define FLOOR_TO_BOUNDARY_BYTE(n,b) ( (n) & ~((b)-1) ) // b バイト境界への切り捨て +#define CEIL_TO_BOUNDARY_BYTE(n,b) ( ((n)+(b)-1) & ~((b)-1) ) // b バイト境界への切り上げ + + +// SPE プロセスコンテキストの読み書き領域 +volatile spe_process_context_t this_process __attribute__((aligned(16))); + +// SPE プロセスコンテキストの実効アドレス +extern volatile unsigned long long __process_context_ea__; +// SPE プロセスのプログラム転送開始地点 +extern volatile unsigned int __spe_program_start__; + + + +void start(void) +{ + //----- SPE プロセスコンテキストの読み込み ------------------------------ + mfc_get ( + &this_process, + __process_context_ea__, + CEIL_TO_BOUNDARY_BYTE(sizeof(this_process), 16), + 0, // tag + 0, // tid + 0 // rid + ); + spu_writech(MFC_WrTagMask, 1<<0); + spu_mfcstat(MFC_TAG_UPDATE_ALL); + asm volatile ("dsync"); // プロセスコンテキストの読み込み完了を保証 + + + //----- SPE プロセスとなるプログラムの読み込み ------------------------------ + mfc_get ( + &__spe_program_start__, + this_process.write.pgm_start, + CEIL_TO_BOUNDARY_BYTE(this_process.write.pgm_size, 16), + 0, // tag + 0, // tid + 0 // rid + ); + spu_writech(MFC_WrTagMask, 1<<0); + spu_mfcstat(MFC_TAG_UPDATE_ALL); + asm volatile ("sync"); // プログラムの読み込み完了とその後のプリフェッチを保証 + + + //----- プログラム実行 ------------------------------ + this_process.read.ret = ((unsigned long long (*)(unsigned long long))&__spe_program_start__)(this_process.write.arg); + + + //----- SPE プロセスコンテキストの書き出し ------------------------------ + this_process.read.status = SPE_PROCESS_CONTEXT_STATUS_FINISHED; + + asm volatile ("dsync"); // LS 内のデータ書き込み完了を保証 + + // Note: SPE プロセスのプログラム内で同一タグ ID の DMA 転送を行っている場合を考慮して、 + // コンテキストの書き出しではフェンス修飾を付けておく。 + + mfc_putf ( + &this_process, + __process_context_ea__, + CEIL_TO_BOUNDARY_BYTE(sizeof(this_process), 16), + 0, // tag + 0, // tid + 0 // rid + ); + spu_writech(MFC_WrTagMask, 1<<0); + spu_mfcstat(MFC_TAG_UPDATE_ALL); + mfc_sync(0 /*tag*/); // プロセスコンテキストの書き出し完了を保証 +}