view 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 source

/**
 * 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*/);      // プロセスコンテキストの書き出し完了を保証
}