1 /*---------------------------------------------------------------------------*
2   Project:  NintendoWare
3   File:     snd_GroupFileReader.cpp
4 
5   Copyright (C)2009-2010 Nintendo Co., Ltd./HAL Laboratory, Inc.  All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law.  They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Revision: 28085 $
14  *---------------------------------------------------------------------------*/
15 
16 #include "precompiled.h"
17 
18 #include <nw/snd/snd_GroupFileReader.h>
19 
20 namespace nw {
21 namespace snd {
22 namespace internal {
23 
24 namespace {
25 
26 const u32 SIGNATURE_INFO_BLOCK  = NW_UT_MAKE_SIGWORD( 'I', 'N', 'F', 'O' );
27 const u32 SIGNATURE_FILE_BLOCK  = NW_UT_MAKE_SIGWORD( 'F', 'I', 'L', 'E' );
28 const u32 SIGNATURE_INFOEX_BLOCK  = NW_UT_MAKE_SIGWORD( 'I', 'N', 'F', 'X' );
29 
30 const u32 SUPPORTED_FILE_VERSION = 0x01000000;
31 const u32 CURRENT_FILE_VERSION   = 0x01010000;
32 
IsValidFileHeader(const void * groupFile)33 bool IsValidFileHeader( const void* groupFile )
34 {
35     const ut::BinaryFileHeader* header =
36         reinterpret_cast<const ut::BinaryFileHeader*>( groupFile );
37 
38     // シグニチャ確認
39     NW_ASSERTMSG( header->signature == GroupFileReader::SIGNATURE_FILE,
40             "invalid file signature. group file is not available." );
41     if ( header->signature != GroupFileReader::SIGNATURE_FILE )
42     {
43         return false;
44     }
45 
46     // バージョン確認
47     NW_ASSERTMSG( header->version >= SUPPORTED_FILE_VERSION,
48             "group file is not supported version.\n"
49             "please reconvert file using new version tools.\n"
50             "(SUPPORTED_FILE_VERSION:0x%08x >= your version:0x%08x)\n",
51             SUPPORTED_FILE_VERSION, header->version
52     );
53     if ( header->version < SUPPORTED_FILE_VERSION ) return false;
54 
55     NW_ASSERTMSG( header->version <= CURRENT_FILE_VERSION,
56             "group file is not supported version.\n"
57             "please reconvert file using new version tools.\n"
58             "(CURRENT_FILE_VERSION:0x%08x >= your version:0x%08x)\n",
59             CURRENT_FILE_VERSION, header->version
60     );
61     if ( header->version > CURRENT_FILE_VERSION ) return false;
62 
63     return true;
64 }
65 
66 } // anonymous namespace
67 
GroupFileReader(const void * groupFile)68 GroupFileReader::GroupFileReader( const void* groupFile )
69 : m_pInfoBlockBody( NULL ),
70   m_pFileBlockBody( NULL ),
71   m_pInfoExBlockBody( NULL )
72 {
73     NW_NULL_ASSERT( groupFile );
74 
75     if ( ! IsValidFileHeader( groupFile ) ) return;
76 
77     const GroupFile::FileHeader* header =
78         static_cast<const GroupFile::FileHeader*>( groupFile );
79 
80     const GroupFile::InfoBlock* infoBlock = header->GetInfoBlock();
81     const GroupFile::FileBlock* fileBlock = header->GetFileBlock();
82     const GroupFile::InfoExBlock* infoExBlock = header->GetInfoExBlock();
83 
84     if ( infoBlock == NULL ) return;
85     if ( fileBlock == NULL ) return;
86 
87     NW_ASSERT( infoBlock->header.kind == SIGNATURE_INFO_BLOCK );
88     NW_ASSERT( fileBlock->header.kind == SIGNATURE_FILE_BLOCK );
89 
90     m_pInfoBlockBody = &(infoBlock->body);
91     m_pFileBlockBody = &(fileBlock->body);
92 
93 
94     // バイナリバージョンが 1.0.0.0 のときは InfoExBlock が含まれない
95     if ( infoExBlock != NULL )
96     {
97         NW_ASSERT( infoExBlock->header.kind == SIGNATURE_INFOEX_BLOCK );
98         m_pInfoExBlockBody = &(infoExBlock->body);
99     }
100 }
101 
ReadGroupItemLocationInfo(GroupItemLocationInfo * out,u32 index) const102 bool GroupFileReader::ReadGroupItemLocationInfo(
103         GroupItemLocationInfo* out, u32 index ) const
104 {
105     if ( m_pInfoBlockBody == NULL )
106     {
107         return false;
108     }
109 
110     const GroupFile::GroupItemInfo* groupItemInfo = m_pInfoBlockBody->GetGroupItemInfo( index );
111     if ( groupItemInfo == NULL )
112     {
113         return false;
114     }
115 
116     out->fileId = groupItemInfo->fileId;
117     out->address = groupItemInfo->GetFileLocation( m_pFileBlockBody );
118     return true;
119 }
120 
GetGroupItemExCount() const121 u32 GroupFileReader::GetGroupItemExCount() const
122 {
123     if ( m_pInfoExBlockBody == NULL )
124     {
125         return 0;
126     }
127 
128     return m_pInfoExBlockBody->GetGroupItemInfoExCount();
129 }
130 
ReadGroupItemInfoEx(GroupFile::GroupItemInfoEx * out,u32 index) const131 bool GroupFileReader::ReadGroupItemInfoEx( GroupFile::GroupItemInfoEx* out, u32 index ) const
132 {
133     if ( m_pInfoExBlockBody == NULL )
134     {
135         return false;
136     }
137 
138     const GroupFile::GroupItemInfoEx* groupItemInfoEx =
139         m_pInfoExBlockBody->GetGroupItemInfoEx( index );
140     if ( groupItemInfoEx == NULL )
141     {
142         return false;
143     }
144 
145     *out = *groupItemInfoEx; // 構造体のコピー
146     return true;
147 }
148 
149 } // namespace nw::snd::internal
150 } // namespace nw::snd
151 } // namespace nw
152 
153