Index: trunk/abdev/BasicCompiler_Common/src/Class.cpp
===================================================================
--- trunk/abdev/BasicCompiler_Common/src/Class.cpp	(revision 340)
+++ trunk/abdev/BasicCompiler_Common/src/Class.cpp	(revision 342)
@@ -166,6 +166,6 @@
 bool CClass::IsInheritsInterface( const CClass *pInterfaceClass ) const
 {
-	BOOST_FOREACH( const InheritedInterface &objInterface, interfaces ){
-		if( pInterfaceClass == &objInterface.GetInterfaceClass() ){
+	BOOST_FOREACH( const ::Interface &objInterface, interfaces ){
+		if( pInterfaceClass == &objInterface.GetClass() ){
 			return true;
 		}
@@ -320,5 +320,5 @@
 
 	//メソッドをコピー
-	BOOST_FOREACH( const CMethod *pBaseMethod, inheritsClass.GetMethods() ){
+	BOOST_FOREACH( const CMethod *pBaseMethod, inheritsClass.GetDynamicMethods() ){
 		CMethod *pMethod = new DynamicMethod( *pBaseMethod );
 
@@ -340,5 +340,5 @@
 		}
 
-		methods.push_back( pMethod );
+		GetDynamicMethods().push_back( pMethod );
 	}
 
@@ -368,5 +368,5 @@
 
 	//メソッドをコピー
-	BOOST_FOREACH( const CMethod *pBaseMethod, inheritsInterface.GetMethods() ){
+	BOOST_FOREACH( const CMethod *pBaseMethod, inheritsInterface.GetDynamicMethods() ){
 		CMethod *pMethod = new DynamicMethod( *pBaseMethod );
 
@@ -388,8 +388,8 @@
 		}
 
-		methods.push_back( pMethod );
-	}
-
-	interfaces.push_back( InheritedInterface( const_cast<CClass *>(&inheritsInterface), vtblNum ) );
+		GetDynamicMethods().push_back( pMethod );
+	}
+
+	//interfaces.push_back( Interface( &inheritsInterface, vtblNum ) );
 
 	//仮想関数の数
@@ -399,10 +399,42 @@
 }
 
+bool CClass::Implements( const CClass &interfaceClass, int nowLine )
+{
+	if( !interfaceClass.IsInterface() )
+	{
+		// インターフェイスではないとき
+		SetError(138,interfaceClass.GetName().c_str(),nowLine );
+		return false;
+	}
+
+	if( !interfaceClass.IsReady() ){
+		// インターフェイスが未解析のとき
+		pobj_LoopRefCheck->add(this->GetName().c_str());
+		compiler.GetObjectModule().meta.GetClasses().GetClass_recur(interfaceClass.GetName().c_str());
+		pobj_LoopRefCheck->del(this->GetName().c_str());
+	}
+
+	interfaces.push_back( ::Interface( &interfaceClass ) );
+
+	return true;
+}
 bool CClass::Implements( const char *interfaceNames, int nowLine )
 {
 	Jenga::Common::Strings paramStrs;
 	SplitParameter( interfaceNames, paramStrs );
-
-	// TODO: 実装
+	
+	BOOST_FOREACH( const std::string &paramStr, paramStrs )
+	{
+		//継承元クラスを取得
+		const CClass *pInterfaceClass = compiler.GetObjectModule().meta.GetClasses().Find( paramStr.c_str() );
+		if( !pInterfaceClass ){
+			SetError(106,paramStr.c_str(),nowLine);
+			continue;
+		}
+
+		// インターフェイスを継承する
+		Implements( *pInterfaceClass, nowLine );
+	}
+
 	return true;
 }
@@ -489,7 +521,7 @@
 
 	if( fConstructor == 1 )
-		pobj_c->SetConstructorMemberSubIndex( (int)pobj_c->GetMethods().size() );
+		pobj_c->SetConstructorMemberSubIndex( (int)pobj_c->GetDynamicMethods().size() );
 	else if( bDestructor )
-		pobj_c->SetDestructorMemberSubIndex( (int)pobj_c->GetMethods().size() );
+		pobj_c->SetDestructorMemberSubIndex( (int)pobj_c->GetDynamicMethods().size() );
 
 
@@ -505,5 +537,5 @@
 
 	//メソッド
-	BOOST_FOREACH( const CMethod *pMethod, pobj_c->GetMethods() ){
+	BOOST_FOREACH( const CMethod *pMethod, pobj_c->GetDynamicMethods() ){
 		//基底クラスと重複する場合はオーバーライドを行う
 		if( pMethod->GetInheritsClassPtr() ) continue;
@@ -524,5 +556,5 @@
 
 	//メソッドのオーバーライド
-	BOOST_FOREACH( CMethod *pMethod, pobj_c->GetMethods() ){
+	BOOST_FOREACH( CMethod *pMethod, pobj_c->GetDynamicMethods() ){
 		if( pMethod->GetUserProc().GetName() == temporary ){
 			if( pMethod->GetUserProc().Params().Equals( pUserProc->Params() )
@@ -565,5 +597,5 @@
 	}
 	else{
-		pobj_c->GetMethods().Add(pUserProc, accessibility, isConst, isAbstract, isVirtual);
+		pobj_c->GetDynamicMethods().Add(pUserProc, accessibility, isConst, isAbstract, isVirtual);
 	}
 }
@@ -576,5 +608,5 @@
 
 	//メソッド
-	BOOST_FOREACH( const CMethod *pMethod, methods ){
+	BOOST_FOREACH( const CMethod *pMethod, GetDynamicMethods() ){
 		if( lstrcmp( name, pMethod->GetUserProc().GetName().c_str() ) == 0 ){
 			return 1;
@@ -727,8 +759,34 @@
 	return alignment;
 }
+
+int CClass::GetVtblMasterListIndex( const UserProc *pUserProc ) const
+{
+	int index = 0;
+	BOOST_FOREACH( const CMethod *pMethod, GetDynamicMethods() ){
+		if( &pMethod->GetUserProc() == pUserProc )
+		{
+			return index;
+		}
+	}
+
+	BOOST_FOREACH( const ::Interface &objInterface, interfaces )
+	{
+		index++;
+
+		BOOST_FOREACH( const CMethod *pMethod, objInterface.GetClass().GetDynamicMethods() ){
+			if( &pMethod->GetUserProc() == pUserProc )
+			{
+				return index;
+			}
+		}
+	}
+
+	SetError();
+	return 0;
+}
 int CClass::GetFuncNumInVtbl( const UserProc *pUserProc ) const
 {
 	int n = 0;
-	BOOST_FOREACH( const CMethod *pMethod, methods ){
+	BOOST_FOREACH( const CMethod *pMethod, GetDynamicMethods() ){
 		if( &pMethod->GetUserProc() == pUserProc ) break;
 		if( pMethod->IsVirtual() ) n++;
@@ -736,67 +794,21 @@
 	return n;
 }
-LONG_PTR CClass::GetVtblGlobalOffset(void) const
-{
-
+LONG_PTR CClass::GetVtblMasterListOffset() const
+{
 	//既に存在する場合はそれを返す
-	if(vtbl_offset!=-1) return vtbl_offset;
-
-
-
-	//////////////////////////////////////
-	// 存在しないときは新たに生成する
-	//////////////////////////////////////
-
-	const UserProc **ppsi;
-	ppsi=(const UserProc **)malloc(GetVtblNum()*sizeof(UserProc *));
+	if( vtblMasterListOffset == -1 )
+	{
+		SetError();
+	}
+
+	return vtblMasterListOffset;
+}
+void CClass::GenerateVTablePart( LONG_PTR &vtableDataTableOffset ) const
+{
+	const UserProc **ppsi = (const UserProc **)malloc(GetVtblNum()*sizeof(UserProc *));
 
 	//関数テーブルに値をセット
 	int i2 = 0;
-	BOOST_FOREACH( const CMethod *pMethod, methods ){
-		if(pMethod->IsVirtual()){
-			pMethod->GetUserProc().Using();
-
-			if(pMethod->IsAbstract()){
-				extern int cp;
-				SmoothieException::Throw(300,NULL,cp);
-
-				ppsi[i2]=0;
-			}
-			else{
-				ppsi[i2]=&pMethod->GetUserProc();
-			}
-			i2++;
-		}
-	}
-
-	vtbl_offset=compiler.GetObjectModule().dataTable.AddBinary((void *)ppsi,GetVtblNum()*sizeof(LONG_PTR));
-
-	for( int i=0; i < GetVtblNum(); i++ ){
-		pobj_Reloc->AddSchedule_DataSection(vtbl_offset+i*sizeof(LONG_PTR));
-	}
-
-	free(ppsi);
-
-	return vtbl_offset;
-}
-void CClass::GenerateVTables()
-{
-	if( IsAbstract() )
-	{
-		// 抽象クラスは無視
-		return;
-	}
-	if( !IsUsing() )
-	{
-		// 使われていないクラスは無視
-		return;
-	}
-
-	const UserProc **ppsi;
-	ppsi=(const UserProc **)malloc(GetVtblNum()*sizeof(UserProc *));
-
-	//関数テーブルに値をセット
-	int i2 = 0;
-	BOOST_FOREACH( const CMethod *pMethod, methods ){
+	BOOST_FOREACH( const CMethod *pMethod, GetDynamicMethods() ){
 		if(pMethod->IsVirtual()){
 			if( !pMethod->GetUserProc().IsUsing() )
@@ -819,13 +831,21 @@
 	}
 
-	vtbl_offset=compiler.GetObjectModule().dataTable.AddBinary((void *)ppsi,GetVtblNum()*sizeof(LONG_PTR));
+	vtableDataTableOffset = compiler.GetObjectModule().dataTable.AddBinary( (void *)ppsi, GetVtblNum()*sizeof(LONG_PTR) );
 
 	for( int i=0; i < GetVtblNum(); i++ ){
-		pobj_Reloc->AddSchedule_DataSection(vtbl_offset+i*sizeof(LONG_PTR));
+		pobj_Reloc->AddSchedule_DataSection(vtableDataTableOffset+i*sizeof(LONG_PTR));
 	}
 
 	free(ppsi);
 }
-void CClass::ActionVtblSchedule(LONG_PTR ImageBase, LONG_PTR MemPos_CodeSection){
+void CClass::GenerateVTableMasterList( const std::vector<LONG_PTR> &vtableMasterList, LONG_PTR &offset )
+{
+	offset = compiler.GetObjectModule().dataTable.AddBinary(
+		(void *)&vtableMasterList[0],
+		vtableMasterList.size()*sizeof(LONG_PTR)
+	);
+}
+void CClass::GenerateFullVTables()
+{
 	if( IsAbstract() )
 	{
@@ -838,22 +858,84 @@
 		return;
 	}
+
+	// vtblマスターリストの元データに不要なデータが含まれていたらエラー
+	if( vtblMasterList.size() )
+	{
+		SetError();
+	}
+
+	// 自身のクラスのvtblを生成
+	GenerateVTablePart( this->vtbl_offset );
+	vtblMasterList.push_back( this->vtbl_offset );
+
+	// インターフェイスのvtblを生成
+	BOOST_FOREACH( const ::Interface &objInterface, interfaces )
+	{
+		LONG_PTR tempVtblOffset;
+		objInterface.GetClass().GenerateVTablePart( tempVtblOffset );
+		vtblMasterList.push_back( tempVtblOffset );
+
+		objInterface.SetVtblOffset( tempVtblOffset );
+	}
+
+	// vtblマスターリストを生成
+	GenerateVTableMasterList( vtblMasterList, this->vtblMasterListOffset );
+}
+void CClass::ActionVtblSchedule( LONG_PTR ImageBase, LONG_PTR MemPos_CodeSection, LONG_PTR MemPos_DataSection )
+{
+	if( IsAbstract() )
+	{
+		// 抽象クラスは無視
+		return;
+	}
+	if( !IsUsing() )
+	{
+		// 使われていないクラスは無視
+		return;
+	}
 	if(vtbl_offset==-1) return;
 
-	LONG_PTR *pVtbl;
-	pVtbl=(LONG_PTR *)((char *)compiler.GetObjectModule().dataTable.GetPtr()+vtbl_offset);
-
-	int i;
-	for(i=0;i<GetVtblNum();i++){
-		UserProc *pUserProc;
-		pUserProc=(UserProc *)pVtbl[i];
-		if(!pUserProc) continue;
-
-		if( pUserProc->GetBeginOpAddress() == 0
-			&& pUserProc->GetEndOpAddress() == 0 )
-		{
-			Jenga::Throw( "未解決の仮想関数が存在する" );
-		}
-
-		pVtbl[i]=pUserProc->GetBeginOpAddress()+ImageBase+MemPos_CodeSection;
+	// 自身のクラスのvtbl
+	{
+		LONG_PTR *pVtbl = (LONG_PTR *)((char *)compiler.GetObjectModule().dataTable.GetPtr() + vtbl_offset);
+
+		for( int i=0; i<GetVtblNum(); i++ ){
+			const UserProc *pUserProc = (UserProc *)pVtbl[i];
+			if(!pUserProc) continue;
+
+			if( pUserProc->GetBeginOpAddress() == 0
+				&& pUserProc->GetEndOpAddress() == 0 )
+			{
+				Jenga::Throw( "未解決の仮想関数が存在する" );
+			}
+
+			pVtbl[i] = pUserProc->GetBeginOpAddress() + ImageBase + MemPos_CodeSection;
+		}
+	}
+
+	// インターフェイスのvtbl
+	BOOST_FOREACH( const ::Interface &objInterface, interfaces )
+	{
+		LONG_PTR *pVtbl = (LONG_PTR *)((char *)compiler.GetObjectModule().dataTable.GetPtr() + objInterface.GetClass().vtbl_offset);
+
+		for( int i=0; i<objInterface.GetClass().GetVtblNum(); i++ ){
+			const UserProc *pUserProc = (UserProc *)pVtbl[i];
+			if(!pUserProc) continue;
+
+			if( pUserProc->GetBeginOpAddress() == 0
+				&& pUserProc->GetEndOpAddress() == 0 )
+			{
+				Jenga::Throw( "未解決の仮想関数が存在する" );
+			}
+
+			pVtbl[i] = pUserProc->GetBeginOpAddress() + ImageBase + MemPos_CodeSection;
+		}
+	}
+
+	// vtblマスターリスト
+	LONG_PTR *pVtblMasterList = (LONG_PTR *)((char *)compiler.GetObjectModule().dataTable.GetPtr() + vtblMasterListOffset );
+	for( int i=0; i<static_cast<int>(vtblMasterList.size()); i++ )
+	{
+		pVtblMasterList[i] = vtblMasterList[i] + ImageBase + MemPos_DataSection;
 	}
 }
@@ -862,5 +944,5 @@
 	// 未実装(abstract)の仮想関数を持つ場合はtrueを返す
 
-	BOOST_FOREACH( const CMethod *pMethod, methods ){
+	BOOST_FOREACH( const CMethod *pMethod, GetDynamicMethods() ){
 		if(pMethod->IsVirtual()){
 			if(pMethod->IsAbstract()){
@@ -1051,14 +1133,14 @@
 	{
 		CClass *pClass = Iterator_GetNext();
-		pClass->GenerateVTables();
-	}
-}
-
-void Classes::ActionVtblSchedule(LONG_PTR ImageBase, LONG_PTR MemPos_CodeSection){
+		pClass->GenerateFullVTables();
+	}
+}
+
+void Classes::ActionVtblSchedule( LONG_PTR ImageBase, LONG_PTR MemPos_CodeSection, LONG_PTR MemPos_DataSection ){
 	Iterator_Reset();
 	while( Iterator_HasNext() )
 	{
 		CClass *pClass = Iterator_GetNext();
-		pClass->ActionVtblSchedule(ImageBase,MemPos_CodeSection);
+		pClass->ActionVtblSchedule( ImageBase, MemPos_CodeSection, MemPos_DataSection);
 	}
 }
@@ -1826,5 +1908,5 @@
 
 		// 仮想関数になるメソッドに使用チェックをつける
-		BOOST_FOREACH( const CMethod *pMethod, pParentClass->GetMethods() )
+		BOOST_FOREACH( const CMethod *pMethod, pParentClass->GetDynamicMethods() )
 		{
 			if( pMethod->IsVirtual() )
@@ -1834,5 +1916,5 @@
 		}
 
-		pCompilingMethod = pParentClass->GetMethods().GetMethodPtr( pUserProc );
+		pCompilingMethod = pParentClass->GetDynamicMethods().GetMethodPtr( pUserProc );
 		if( !pCompilingMethod ){
 			pCompilingMethod = pParentClass->GetStaticMethods().GetMethodPtr( pUserProc );
