03.09.2012, 15:21, "Olivier Goffart" <oliv...@woboq.com>: > On Sunday 02 September 2012 23:10:18 Konstantin Tokarev wrote: >> Hi all, >> >> When building Qt 5 on big endian host (PPC) I've found moc breaking on Qt >> classes containing Q_PLUGIN_METADATA with >> >> ASSERT: "idx >= 0 && idx < s" in file >> ../../../include/QtCore/../../src/corelib/tools/qvarlengtharray.h, line 111 >> >> It turned out to be a fault of QJsonPrivate::Parser::parseObject which has >> different code for handling of big endian and little endian cases: >> >> if (parsedObject.offsets.size()) { >> int tableSize = parsedObject.offsets.size()*sizeof(uint); > ^^^^^^^^^^^^^ > > The error is there: one should multiply tableSize by sizeof(uint) only if > one > do a memcpy. >> table = reserveSpace(tableSize); >> #if Q_BYTE_ORDER == Q_LITTLE_ENDIAN >> memcpy(data + table, parsedObject.offsets.constData(), tableSize); >> #else >> offset *o = (offset *)(data + table); >> for (int i = 0; i < tableSize; ++i) >> o[i] = parsedObject.offsets[i]; >> >> #endif >> } >> >> Could anyone explain why memcpy cannot be used for big endian case here? > I guess that's because the offsets needs to be stored in little endian. > offset is a typedef to a class that has an assignement operator which swap > the > bytes.
It turned out to be not the only place where memcpy is working incorrectly. Unit test segfaults on memcpy in Value::copyData 404 case QJsonValue::Array: 405 case QJsonValue::Object: { 406 const QJsonPrivate::Base *b = v.base; 407 if (!b) 408 b = (v.t == QJsonValue::Array ? &emptyArray : &emptyObject); 409 memcpy(dest, b, b->size); 410 break; 411 } I tried to understand why memcpy fails here and how to replace it for BE case, but still don't have a clue. I'm also quite disappointed to see so heavily endian- dependent code written nowadays. -- Regards, Konstantin _______________________________________________ Development mailing list Development@qt-project.org http://lists.qt-project.org/mailman/listinfo/development