aramis_acg 2011-02-20 00:01:52 +00:00
parent 79eca6196d
commit 94767ecf8c
9 changed files with 80 additions and 41 deletions

View File

@ -328,7 +328,7 @@ void BaseImporter::ConvertToUTF8(std::vector<char>& data)
if(*((uint16_t*)&data.front()) == 0xFEFF) {
DefaultLogger::get()->debug("Found UTF-16 BOM ...");
const uint16_t* sstart = (uint16_t*)&data.front()+1, *send = (uint16_t*)&data.back()+1;
const uint16_t* sstart = (uint16_t*)&data.front()+1, *send = (uint16_t*)(&data.back()+1);
char* dstart,*dend;
std::vector<char> output;
do {

View File

@ -236,9 +236,9 @@ struct Mesh
//! \brief Data structure to store all obj-specific model datas
struct Model
{
typedef std::map<std::string*, std::vector<unsigned int>* > GroupMap;
typedef std::map<std::string*, std::vector<unsigned int>* >::iterator GroupMapIt;
typedef std::map<std::string*, std::vector<unsigned int>* >::const_iterator ConstGroupMapIt;
typedef std::map<std::string, std::vector<unsigned int>* > GroupMap;
typedef std::map<std::string, std::vector<unsigned int>* >::iterator GroupMapIt;
typedef std::map<std::string, std::vector<unsigned int>* >::const_iterator ConstGroupMapIt;
//! Model name
std::string m_ModelName;

View File

@ -66,6 +66,8 @@ ObjFileParser::ObjFileParser(std::vector<char> &Data,const std::string &strModel
m_uiLine(0),
m_pIO( io )
{
memset(m_buffer, BUFFERSIZE, 0);
// Create the model instance to store all the data
m_pModel = new ObjFile::Model();
m_pModel->m_ModelName = strModelName;
@ -188,7 +190,7 @@ void ObjFileParser::copyNextWord(char *pBuffer, size_t length)
{
size_t index = 0;
m_DataIt = getNextWord<DataArrayIt>(m_DataIt, m_DataItEnd);
while ( !isSeparator(*m_DataIt) && m_DataIt != m_DataItEnd )
while ( m_DataIt != m_DataItEnd && !isSeparator(*m_DataIt) )
{
pBuffer[index] = *m_DataIt;
index++;
@ -262,7 +264,7 @@ void ObjFileParser::getFace()
char *pPtr = m_buffer;
char *pEnd = &pPtr[BUFFERSIZE];
pPtr = getNextToken<char*>(pPtr, pEnd);
if (pPtr == '\0')
if (pPtr == pEnd || *pPtr == '\0')
return;
std::vector<unsigned int> *pIndices = new std::vector<unsigned int>;
@ -279,7 +281,7 @@ void ObjFileParser::getFace()
if (*pPtr == '\0')
break;
if (*pPtr=='\r')
if (*pPtr=='\r' || *pPtr=='\n')
break;
if (*pPtr=='/' )
@ -372,7 +374,7 @@ void ObjFileParser::getMaterialDesc()
return;
char *pStart = &(*m_DataIt);
while ( !isSeparator(*m_DataIt) && m_DataIt != m_DataItEnd )
while ( m_DataIt != m_DataItEnd && !isSeparator(*m_DataIt) )
++m_DataIt;
// Get name
@ -406,10 +408,9 @@ void ObjFileParser::getMaterialDesc()
// Get a comment, values will be skipped
void ObjFileParser::getComment()
{
bool running = true;
while (running)
while (m_DataIt != m_DataItEnd)
{
if ( '\n' == (*m_DataIt) || m_DataIt == m_DataItEnd )
if ( '\n' == (*m_DataIt))
{
++m_DataIt;
break;
@ -431,7 +432,7 @@ void ObjFileParser::getMaterialLib()
return;
char *pStart = &(*m_DataIt);
while (!isNewLine(*m_DataIt))
while (m_DataIt != m_DataItEnd && !isNewLine(*m_DataIt))
m_DataIt++;
// Check for existence
@ -465,7 +466,7 @@ void ObjFileParser::getNewMaterial()
char *pStart = &(*m_DataIt);
std::string strMat( pStart, *m_DataIt );
while ( isSeparator( *m_DataIt ) )
while ( m_DataIt != m_DataItEnd && isSeparator( *m_DataIt ) )
m_DataIt++;
std::map<std::string, ObjFile::Material*>::iterator it = m_pModel->m_MaterialMap.find( strMat );
if ( it == m_pModel->m_MaterialMap.end() )
@ -516,7 +517,7 @@ void ObjFileParser::getGroupName()
// Store groupname in group library
char *pStart = &(*m_DataIt);
while ( !isSeparator(*m_DataIt) )
while ( m_DataIt != m_DataItEnd && !isSeparator(*m_DataIt) )
m_DataIt++;
std::string strGroupName(pStart, &(*m_DataIt));
@ -524,7 +525,7 @@ void ObjFileParser::getGroupName()
if ( m_pModel->m_strActiveGroup != strGroupName )
{
// Search for already existing entry
ObjFile::Model::ConstGroupMapIt it = m_pModel->m_Groups.find(&strGroupName);
ObjFile::Model::ConstGroupMapIt it = m_pModel->m_Groups.find(strGroupName);
// We are mapping groups into the object structure
createObject( strGroupName );
@ -533,7 +534,7 @@ void ObjFileParser::getGroupName()
if (it == m_pModel->m_Groups.end())
{
std::vector<unsigned int> *pFaceIDArray = new std::vector<unsigned int>;
m_pModel->m_Groups[ &strGroupName ] = pFaceIDArray;
m_pModel->m_Groups[ strGroupName ] = pFaceIDArray;
m_pModel->m_pGroupFaceIDs = (pFaceIDArray);
}
else
@ -563,7 +564,7 @@ void ObjFileParser::getObjectName()
if (m_DataIt == m_DataItEnd)
return;
char *pStart = &(*m_DataIt);
while ( !isSeparator( *m_DataIt ) )
while ( m_DataIt != m_DataItEnd && !isSeparator( *m_DataIt ) )
++m_DataIt;
std::string strObjectName(pStart, &(*m_DataIt));

View File

@ -147,7 +147,7 @@ void RemoveRedundantMatsProcess::Execute( aiScene* pScene)
uint32_t me = aiHashes[i] = ((MaterialHelper*)pScene->mMaterials[i])->ComputeHash();
for (unsigned int a = 0; a < i;++a)
{
if (me == aiHashes[a]) {
if (abReferenced[a] && me == aiHashes[a]) {
++iCnt;
me = 0;
aiMappingTable[i] = aiMappingTable[a];

View File

@ -47,6 +47,8 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// internal headers of the post-processing framework
#include "SplitByBoneCountProcess.h"
#include <limits>
using namespace Assimp;
// ------------------------------------------------------------------------------------------------
@ -262,7 +264,7 @@ void SplitByBoneCountProcess::SplitMesh( const aiMesh* pMesh, std::vector<aiMesh
// and copy over the data, generating faces with linear indices along the way
newMesh->mFaces = new aiFace[subMeshFaces.size()];
size_t nvi = 0; // next vertex index
std::vector<size_t> previousVertexIndices( numSubMeshVertices, SIZE_MAX); // per new vertex: its index in the source mesh
std::vector<size_t> previousVertexIndices( numSubMeshVertices, std::numeric_limits<size_t>::max()); // per new vertex: its index in the source mesh
for( size_t a = 0; a < subMeshFaces.size(); ++a )
{
const aiFace& srcFace = pMesh->mFaces[subMeshFaces[a]];
@ -306,7 +308,7 @@ void SplitByBoneCountProcess::SplitMesh( const aiMesh* pMesh, std::vector<aiMesh
newMesh->mNumBones = 0;
newMesh->mBones = new aiBone*[numBones];
std::vector<size_t> mappedBoneIndex( pMesh->mNumBones, SIZE_MAX);
std::vector<size_t> mappedBoneIndex( pMesh->mNumBones, std::numeric_limits<size_t>::max());
for( size_t a = 0; a < pMesh->mNumBones; ++a )
{
if( !isBoneUsed[a] )
@ -333,7 +335,7 @@ void SplitByBoneCountProcess::SplitMesh( const aiMesh* pMesh, std::vector<aiMesh
for( size_t b = 0; b < bonesOnThisVertex.size(); ++b )
{
size_t newBoneIndex = mappedBoneIndex[ bonesOnThisVertex[b].first ];
if( newBoneIndex != SIZE_MAX )
if( newBoneIndex != std::numeric_limits<size_t>::max() )
newMesh->mBones[newBoneIndex]->mNumWeights++;
}
}
@ -359,7 +361,7 @@ void SplitByBoneCountProcess::SplitMesh( const aiMesh* pMesh, std::vector<aiMesh
for( size_t b = 0; b < bonesOnThisVertex.size(); ++b)
{
size_t newBoneIndex = mappedBoneIndex[ bonesOnThisVertex[b].first ];
ai_assert( newBoneIndex != SIZE_MAX );
ai_assert( newBoneIndex != std::numeric_limits<size_t>::max() );
aiVertexWeight* dstWeight = newMesh->mBones[newBoneIndex]->mWeights + newMesh->mBones[newBoneIndex]->mNumWeights;
newMesh->mBones[newBoneIndex]->mNumWeights++;

View File

@ -101,7 +101,7 @@ void XFileImporter::InternReadFile( const std::string& pFile, aiScene* pScene, I
mImportedMats.clear();
// in the hope that binary files will never start with a BOM ...
mBuffer.resize( fileSize);
mBuffer.resize( fileSize + 1);
file->Read( &mBuffer.front(), 1, fileSize);
ConvertToUTF8(mBuffer);

View File

@ -91,7 +91,7 @@ XFileParser::XFileParser( const std::vector<char>& pBuffer)
// set up memory pointers
P = &pBuffer.front();
End = P + pBuffer.size();
End = P + pBuffer.size() - 1;
// check header
if( strncmp( P, "xof ", 4) != 0)
@ -180,7 +180,8 @@ XFileParser::XFileParser( const std::vector<char>& pBuffer)
// First find out how much storage we'll need. Count sections.
const char* P1 = P;
unsigned int est_out = 0;
while (P1 < End)
while (P1 + 3 < End)
{
// read next offset
uint16_t ofs = *((uint16_t*)P1);
@ -199,12 +200,16 @@ XFileParser::XFileParser( const std::vector<char>& pBuffer)
// and advance to the next offset
P1 += ofs;
est_out += MSZIP_BLOCK; // one decompressed block is 32786 in size
// this block would continue past the file end, abort
if (P1 > End)
throw DeadlyImportError("X: Unexpected end of file while uncompressing");
}
// Allocate storage and do the actual uncompressing
uncompressed.resize(est_out);
// Allocate storage and terminating zero and do the actual uncompressing
uncompressed.resize(est_out + 1);
char* out = &uncompressed.front();
while (P < End)
while (P + 3 < End)
{
uint16_t ofs = *((uint16_t*)P);
AI_SWAP2(ofs);
@ -592,6 +597,9 @@ void XFileParser::ParseDataObjectMeshNormals( Mesh* pMesh)
void XFileParser::ParseDataObjectMeshTextureCoords( Mesh* pMesh)
{
readHeadOfDataObject();
if( pMesh->mNumTextures + 1 > AI_MAX_NUMBER_OF_TEXTURECOORDS)
ThrowException( "Too many sets of texture coordinates");
std::vector<aiVector2D>& coords = pMesh->mTexCoords[pMesh->mNumTextures++];
unsigned int numCoords = ReadInt();
@ -609,6 +617,8 @@ void XFileParser::ParseDataObjectMeshTextureCoords( Mesh* pMesh)
void XFileParser::ParseDataObjectMeshVertexColors( Mesh* pMesh)
{
readHeadOfDataObject();
if( pMesh->mNumColorSets + 1 > AI_MAX_NUMBER_OF_COLOR_SETS)
ThrowException( "Too many colorsets");
std::vector<aiColor4D>& colors = pMesh->mColors[pMesh->mNumColorSets++];
unsigned int numColors = ReadInt();
@ -659,7 +669,7 @@ void XFileParser::ParseDataObjectMeshMaterialList( Mesh* pMesh)
// commented out version check, as version 03.03 exported from blender also has 2 semicolons
if( !mIsBinaryFormat) // && MajorVersion == 3 && MinorVersion <= 2)
{
if( *P == ';')
if(P < End && *P == ';')
++P;
}
@ -1043,6 +1053,7 @@ std::string XFileParser::GetNextToken()
// in binary mode it will only return NAME and STRING token
// and (correctly) skip over other tokens.
if( End - P < 2) return s;
unsigned int tok = ReadBinWord();
unsigned int len;
@ -1051,13 +1062,17 @@ std::string XFileParser::GetNextToken()
{
case 1:
// name token
if( End - P < 4) return s;
len = ReadBinDWord();
if( End - P < len) return s;
s = std::string(P, len);
P += len;
return s;
case 2:
// string token
if( End - P < 4) return s;
len = ReadBinDWord();
if( End - P < len) return s;
s = std::string(P, len);
P += (len + 2);
return s;
@ -1070,10 +1085,12 @@ std::string XFileParser::GetNextToken()
P += 16;
return "<guid>";
case 6:
if( End - P < 4) return s;
len = ReadBinDWord();
P += (len * 4);
return "<int_list>";
case 7:
if( End - P < 4) return s;
len = ReadBinDWord();
P += (len * mBinaryFloatSize);
return "<flt_list>";
@ -1227,6 +1244,7 @@ void XFileParser::ReadUntilEndOfLine()
// ------------------------------------------------------------------------------------------------
unsigned short XFileParser::ReadBinWord()
{
assert(End - P >= 2);
const unsigned char* q = (const unsigned char*) P;
unsigned short tmp = q[0] | (q[1] << 8);
P += 2;
@ -1236,6 +1254,7 @@ unsigned short XFileParser::ReadBinWord()
// ------------------------------------------------------------------------------------------------
unsigned int XFileParser::ReadBinDWord()
{
assert(End - P >= 4);
const unsigned char* q = (const unsigned char*) P;
unsigned int tmp = q[0] | (q[1] << 8) | (q[2] << 16) | (q[3] << 24);
P += 4;
@ -1247,17 +1266,22 @@ unsigned int XFileParser::ReadInt()
{
if( mIsBinaryFormat)
{
if( mBinaryNumCount == 0)
if( mBinaryNumCount == 0 && End - P >= 2)
{
unsigned short tmp = ReadBinWord(); // 0x06 or 0x03
if( tmp == 0x06) // array of ints follows
if( tmp == 0x06 && End - P >= 4) // array of ints follows
mBinaryNumCount = ReadBinDWord();
else // single int follows
mBinaryNumCount = 1;
}
--mBinaryNumCount;
return ReadBinDWord();
if ( End - P >= 4) {
return ReadBinDWord();
} else {
P = End;
return 0;
}
} else
{
FindNextNoneWhiteSpace();
@ -1296,10 +1320,10 @@ float XFileParser::ReadFloat()
{
if( mIsBinaryFormat)
{
if( mBinaryNumCount == 0)
if( mBinaryNumCount == 0 && End - P >= 2)
{
unsigned short tmp = ReadBinWord(); // 0x07 or 0x42
if( tmp == 0x07) // array of floats following
if( tmp == 0x07 && End - P >= 4) // array of floats following
mBinaryNumCount = ReadBinDWord();
else // single float following
mBinaryNumCount = 1;
@ -1308,14 +1332,24 @@ float XFileParser::ReadFloat()
--mBinaryNumCount;
if( mBinaryFloatSize == 8)
{
float result = (float) (*(double*) P);
P += 8;
return result;
if( End - P >= 8) {
float result = (float) (*(double*) P);
P += 8;
return result;
} else {
P = End;
return 0;
}
} else
{
float result = *(float*) P;
P += 4;
return result;
if( End - P >= 4) {
float result = *(float*) P;
P += 4;
return result;
} else {
P = End;
return 0;
}
}
}
@ -1323,6 +1357,7 @@ float XFileParser::ReadFloat()
FindNextNoneWhiteSpace();
// check for various special strings to allow reading files from faulty exporters
// I mean you, Blender!
// Reading is safe because of the terminating zero
if( strncmp( P, "-1.#IND00", 9) == 0 || strncmp( P, "1.#IND00", 8) == 0)
{
P += 9;

View File

@ -66,7 +66,7 @@ class XFileParser
{
public:
/** Constructor. Creates a data structure out of the XFile given in the memory block.
* @param pBuffer Memory buffer containing the XFile
* @param pBuffer Null-terminated memory buffer containing the XFile
*/
XFileParser( const std::vector<char>& pBuffer);

View File

@ -50,6 +50,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "aiTypes.h"
#ifdef __cplusplus
#include <boost/noncopyable.hpp>
extern "C" {
#endif