Merge remote branch 'origin/android_branch' into android_branch

This commit is contained in:
eehouse@eehouse.org 2011-11-10 06:54:42 -08:00 committed by Andy2
commit 9f22b11f81
5 changed files with 112 additions and 55 deletions

View file

@ -699,6 +699,47 @@ dict_getLangName( const DictionaryCtxt* ctxt )
return ctxt->langName; return ctxt->langName;
} }
#ifdef XWFEATURE_DICTSANITY
XP_Bool
checkSanity( DictionaryCtxt* dict, const XP_U32 numEdges )
{
XP_U32 ii;
XP_Bool passed = XP_TRUE;
array_edge* edge = dict->base;
Tile prevTile = 0;
for ( ii = 0; ii < numEdges && passed; ++ii ) {
Tile tile = EDGETILE( dict, edge );
if ( tile < prevTile ) {
XP_LOGF( "%s: node %ld of %ld has out-of-order tile", __func__,
ii, numEdges );
passed = XP_FALSE;
break;
}
prevTile = tile;
unsigned long index = dict_index_from( dict, edge );
if ( index >= numEdges ) {
XP_LOGF( "%s: node %ld of %ld has too-high index", __func__,
ii, numEdges );
passed = XP_FALSE;
break;
}
if ( IS_LAST_EDGE( dict, edge ) ) {
prevTile = 0;
}
edge += dict->nodeSize;
}
if ( passed ) {
passed = 0 == prevTile; /* last edge seen was a LAST_EDGE */
}
XP_LOGF( "%s(numEdges=%ld)=>%d", __func__, numEdges, passed );
return passed;
} /* checkSanity */
#endif
#ifdef CPLUS #ifdef CPLUS
} }
#endif #endif

View file

@ -207,6 +207,8 @@ void dict_super_init( DictionaryCtxt* ctxt );
void dict_splitFaces( DictionaryCtxt* dict, const XP_U8* bytes, void dict_splitFaces( DictionaryCtxt* dict, const XP_U8* bytes,
XP_U16 nBytes, XP_U16 nFaces ); XP_U16 nBytes, XP_U16 nFaces );
XP_Bool checkSanity( DictionaryCtxt* dict, XP_U32 numEdges );
#ifdef CPLUS #ifdef CPLUS
} }
#endif #endif

View file

@ -92,6 +92,7 @@ DEFINES += -DDISABLE_TILE_SEL
DEFINES += -DSET_GAMESEED DEFINES += -DSET_GAMESEED
DEFINES += -DTEXT_MODEL DEFINES += -DTEXT_MODEL
DEFINES += -DXWFEATURE_WALKDICT DEFINES += -DXWFEATURE_WALKDICT
DEFINES += -DXWFEATURE_DICTSANITY
ifdef CURSES_CELL_HT ifdef CURSES_CELL_HT
DEFINES += -DCURSES_CELL_HT=$(CURSES_CELL_HT) DEFINES += -DCURSES_CELL_HT=$(CURSES_CELL_HT)

View file

@ -225,17 +225,19 @@ initFromDictFile( LinuxDictionaryCtxt* dctx, const char* fileName )
dctx->dictLength = statbuf.st_size; dctx->dictLength = statbuf.st_size;
{ {
FILE* dictF = fopen( fileName, "r" ); FILE* dictF = fopen( fileName, "r" );
XP_ASSERT( !!dictF ); XP_ASSERT( !!dictF );
if ( dctx->useMMap ) { if ( dctx->useMMap ) {
dctx->dictBase = mmap( NULL, dctx->dictLength, PROT_READ, MAP_PRIVATE, fileno(dictF), 0 ); dctx->dictBase = mmap( NULL, dctx->dictLength, PROT_READ,
} else { MAP_PRIVATE, fileno(dictF), 0 );
dctx->dictBase = XP_MALLOC( dctx->super.mpool, dctx->dictLength ); } else {
if ( dctx->dictLength != fread( dctx->dictBase, 1, dctx->dictLength, dictF ) ) { dctx->dictBase = XP_MALLOC( dctx->super.mpool, dctx->dictLength );
XP_ASSERT( 0 ); if ( dctx->dictLength != fread( dctx->dictBase, 1,
} dctx->dictLength, dictF ) ) {
} XP_ASSERT( 0 );
fclose( dictF ); }
}
fclose( dictF );
} }
ptr = dctx->dictBase; ptr = dctx->dictBase;
@ -247,65 +249,65 @@ initFromDictFile( LinuxDictionaryCtxt* dctx, const char* fileName )
XP_DEBUGF( "flags=0X%X", flags ); XP_DEBUGF( "flags=0X%X", flags );
hasHeader = 0 != (DICT_HEADER_MASK & flags); hasHeader = 0 != (DICT_HEADER_MASK & flags);
if ( hasHeader ) { if ( hasHeader ) {
flags &= ~DICT_HEADER_MASK; flags &= ~DICT_HEADER_MASK;
XP_DEBUGF( "has header!" ); XP_DEBUGF( "has header!" );
} }
#ifdef NODE_CAN_4 #ifdef NODE_CAN_4
if ( flags == 0x0001 ) { if ( flags == 0x0001 ) {
dctx->super.nodeSize = 3; dctx->super.nodeSize = 3;
charSize = 1; charSize = 1;
dctx->super.is_4_byte = XP_FALSE; dctx->super.is_4_byte = XP_FALSE;
} else if ( flags == 0x0002 ) { } else if ( flags == 0x0002 ) {
dctx->super.nodeSize = 3; dctx->super.nodeSize = 3;
charSize = 2; charSize = 2;
dctx->super.is_4_byte = XP_FALSE; dctx->super.is_4_byte = XP_FALSE;
} else if ( flags == 0x0003 ) { } else if ( flags == 0x0003 ) {
dctx->super.nodeSize = 4; dctx->super.nodeSize = 4;
charSize = 2; charSize = 2;
dctx->super.is_4_byte = XP_TRUE; dctx->super.is_4_byte = XP_TRUE;
} else if ( flags == 0x0004 ) { } else if ( flags == 0x0004 ) {
dctx->super.nodeSize = 3; dctx->super.nodeSize = 3;
dctx->super.isUTF8 = XP_TRUE; dctx->super.isUTF8 = XP_TRUE;
isUTF8 = XP_TRUE; isUTF8 = XP_TRUE;
dctx->super.is_4_byte = XP_FALSE; dctx->super.is_4_byte = XP_FALSE;
} else if ( flags == 0x0005 ) { } else if ( flags == 0x0005 ) {
dctx->super.nodeSize = 4; dctx->super.nodeSize = 4;
dctx->super.isUTF8 = XP_TRUE; dctx->super.isUTF8 = XP_TRUE;
isUTF8 = XP_TRUE; isUTF8 = XP_TRUE;
dctx->super.is_4_byte = XP_TRUE; dctx->super.is_4_byte = XP_TRUE;
} else { } else {
/* case I don't know how to deal with */ /* case I don't know how to deal with */
formatOk = XP_FALSE; formatOk = XP_FALSE;
XP_ASSERT(0); XP_ASSERT(0);
} }
#else #else
XP_ASSERT( flags == 0x0001 ); XP_ASSERT( flags == 0x0001 );
#endif #endif
if ( formatOk ) { if ( formatOk ) {
XP_U8 numFaceBytes, numFaces; XP_U8 numFaceBytes, numFaces;
if ( hasHeader ) { if ( hasHeader ) {
XP_U16 headerLen; XP_U16 headerLen;
XP_U32 wordCount; XP_U32 wordCount;
memcpy( &headerLen, ptr, sizeof(headerLen) ); memcpy( &headerLen, ptr, sizeof(headerLen) );
ptr += sizeof(headerLen); ptr += sizeof(headerLen);
headerLen = ntohs( headerLen ); headerLen = ntohs( headerLen );
if ( headerLen != sizeof(wordCount) ) { /* the only case we know right now */ if ( headerLen != sizeof(wordCount) ) { /* the only case we know right now */
goto closeAndExit; goto closeAndExit;
} }
memcpy( &wordCount, ptr, sizeof(wordCount) ); memcpy( &wordCount, ptr, sizeof(wordCount) );
ptr += sizeof(wordCount); ptr += sizeof(wordCount);
dctx->super.nWords = ntohl( wordCount ); dctx->super.nWords = ntohl( wordCount );
XP_DEBUGF( "dict contains %ld words", dctx->super.nWords ); XP_DEBUGF( "dict contains %ld words", dctx->super.nWords );
} }
if ( isUTF8 ) { if ( isUTF8 ) {
numFaceBytes = *ptr++; numFaceBytes = *ptr++;
} }
numFaces = *ptr++; numFaces = *ptr++;
if ( !isUTF8 ) { if ( !isUTF8 ) {
numFaceBytes = numFaces * charSize; numFaceBytes = numFaces * charSize;
} }
@ -320,42 +322,47 @@ XP_ASSERT( flags == 0x0001 );
} }
XP_U8 tmp[numFaceBytes]; XP_U8 tmp[numFaceBytes];
memcpy( tmp, ptr, numFaceBytes ); memcpy( tmp, ptr, numFaceBytes );
ptr += numFaceBytes; ptr += numFaceBytes;
dict_splitFaces( &dctx->super, tmp, numFaceBytes, numFaces ); dict_splitFaces( &dctx->super, tmp, numFaceBytes, numFaces );
memcpy( &xloc, ptr, sizeof(xloc) ); memcpy( &xloc, ptr, sizeof(xloc) );
ptr += sizeof(xloc); ptr += sizeof(xloc);
memcpy( dctx->super.countsAndValues, ptr, numFaces*2 ); memcpy( dctx->super.countsAndValues, ptr, numFaces*2 );
ptr += numFaces*2; ptr += numFaces*2;
} }
dctx->super.langCode = xloc & 0x7F; dctx->super.langCode = xloc & 0x7F;
if ( formatOk ) { if ( formatOk ) {
XP_U32 numEdges;
skipBitmaps( dctx, &ptr ); skipBitmaps( dctx, &ptr );
curPos = ptr - dctx->dictBase; curPos = ptr - dctx->dictBase;
dictLength = dctx->dictLength - curPos; dictLength = dctx->dictLength - curPos;
if ( dictLength > 0 ) { if ( dictLength > 0 ) {
memcpy( &topOffset, ptr, sizeof(topOffset) ); memcpy( &topOffset, ptr, sizeof(topOffset) );
/* it's in big-endian order */ /* it's in big-endian order */
topOffset = ntohl(topOffset); topOffset = ntohl(topOffset);
dictLength -= sizeof(topOffset); /* first four bytes are offset */ dictLength -= sizeof(topOffset); /* first four bytes are offset */
ptr += sizeof(topOffset); ptr += sizeof(topOffset);
} }
if ( dictLength > 0 ) { if ( dictLength > 0 ) {
# ifdef NODE_CAN_4
numEdges = dictLength / dctx->super.nodeSize;
# else
numEdges = dictLength / 3;
# endif
#ifdef DEBUG #ifdef DEBUG
# ifdef NODE_CAN_4 # ifdef NODE_CAN_4
dctx->super.numEdges = dictLength / dctx->super.nodeSize;
XP_ASSERT( (dictLength % dctx->super.nodeSize) == 0 ); XP_ASSERT( (dictLength % dctx->super.nodeSize) == 0 );
# else # else
dctx->super.numEdges = dictLength / 3;
XP_ASSERT( (dictLength % 3) == 0 ); XP_ASSERT( (dictLength % 3) == 0 );
# endif # endif
dctx->super.numEdges = numEdges;
#endif #endif
dctx->super.base = (array_edge*)ptr; dctx->super.base = (array_edge*)ptr;
@ -366,6 +373,10 @@ XP_ASSERT( flags == 0x0001 );
} }
dctx->super.name = copyString( dctx->super.mpool, fileName ); dctx->super.name = copyString( dctx->super.mpool, fileName );
if ( ! checkSanity( &dctx->super, numEdges ) ) {
goto closeAndExit;
}
} }
goto ok; goto ok;

View file

@ -903,6 +903,7 @@ tmp_noop_sigintterm( int XP_UNUSED(sig) )
} }
#ifdef XWFEATURE_WALKDICT #ifdef XWFEATURE_WALKDICT
//# define PRINT_ALL
static void static void
testGetNthWord( const DictionaryCtxt* dict, char** words, testGetNthWord( const DictionaryCtxt* dict, char** words,
XP_U16 depth, IndexData* data ) XP_U16 depth, IndexData* data )
@ -948,7 +949,6 @@ walk_dict_test( const LaunchParams* params, const DictionaryCtxt* dict,
XP_ASSERT( count == dict_countWords( dict ) ); XP_ASSERT( count == dict_countWords( dict ) );
char** words = g_malloc( count * sizeof(char*) ); char** words = g_malloc( count * sizeof(char*) );
XP_ASSERT( !!words ); XP_ASSERT( !!words );
// # define PRINT_ALL
/* if ( dict_firstWord( dict, &word ) */ /* if ( dict_firstWord( dict, &word ) */
/* && dict_getNextWord( dict, &word ) */ /* && dict_getNextWord( dict, &word ) */
@ -1085,9 +1085,11 @@ walk_dict_test_all( const LaunchParams* params, GSList* testDicts,
DictionaryCtxt* dict = DictionaryCtxt* dict =
linux_dictionary_make( MPPARM(params->util->mpool) name, linux_dictionary_make( MPPARM(params->util->mpool) name,
params->useMmap ); params->useMmap );
XP_LOGF( "walk_dict_test(%s)", name ); if ( NULL != dict ) {
walk_dict_test( params, dict, testPrefixes ); XP_LOGF( "walk_dict_test(%s)", name );
dict_destroy( dict ); walk_dict_test( params, dict, testPrefixes );
dict_destroy( dict );
}
} }
} }
#endif #endif