Merge branch 'master' into refactor

Conflicts:
	src/3rdparty/v8
	src/gui/text/qfont_qpa.cpp
	src/gui/widgets/qlinecontrol.cpp
	src/plugins/platforms/fontdatabases/fontconfig/qfontconfigdatabase.cpp
	tests/auto/gui.pro
	tests/auto/network.pro
	tests/auto/qstring/tst_qstring.cpp

Change-Id: Id118c172645303ccf06a207050d5bf1462ff57fe
This commit is contained in:
Gunnar Sletta 2011-09-12 07:49:03 +02:00
commit a9ac6da893
38 changed files with 986 additions and 720 deletions

View File

@ -299,10 +299,9 @@ if (abs_path($out_basedir) ne abs_path($qtbasedir)) {
# Generate the new contents # Generate the new contents
my $newContents = $existingContents; my $newContents = $existingContents;
# Strip out any existing config test results or include statements # Strip out any existing config test results
$newContents =~ s/^config_test_[^\$]*$//gm; $newContents =~ s/^config_test_[^\$]*$//gm;
$newContents =~ s/^# Compile time test results[^\$]*$//gm; $newContents =~ s/^# Compile time test results[^\$]*$//gm;
$newContents =~ s/include\(\$\$PWD\/..\/.qmake.cache\)$//gm;
# Add any remaining content and make sure we start on a new line # Add any remaining content and make sure we start on a new line
if ($newContents and chop $newContents ne '\n') { if ($newContents and chop $newContents ne '\n') {
@ -322,9 +321,6 @@ if (abs_path($out_basedir) ne abs_path($qtbasedir)) {
# Remove blank lines # Remove blank lines
$newContents =~ s/^[\s]*$//gms; $newContents =~ s/^[\s]*$//gms;
# Include top level .qmake.cache
$newContents = $newContents . "include(\$\$PWD/../.qmake.cache)\n";
# and open the file # and open the file
open my $cacheFileHandle, ">$qmakeCachePath" or die "Unable to open $qmakeCachePath for writing: $!\n"; open my $cacheFileHandle, ">$qmakeCachePath" or die "Unable to open $qmakeCachePath for writing: $!\n";

15
configure vendored
View File

@ -1041,7 +1041,7 @@ while [ "$#" -gt 0 ]; do
VAL=no VAL=no
;; ;;
#Qt style yes options #Qt style yes options
-incremental|-qvfb|-profile|-shared|-static|-sm|-xinerama|-xshape|-xsync|-xinput|-egl|-reduce-exports|-pch|-separate-debug-info|-stl|-freetype|-xcursor|-xfixes|-xrandr|-xrender|-mitshm|-fontconfig|-xkb|-xcb|-nis|-qdbus|-dbus|-dbus-linked|-glib|-gstreamer|-gtkstyle|-cups|-iconv|-largefile|-h|-help|-v|-verbose|-debug|-release|-fast|-accessibility|-confirm-license|-gnumake|-framework|-qt3support|-debug-and-release|-exceptions|-cocoa|-carbon|-universal|-harfbuzz|-prefix-install|-silent|-armfpa|-optimized-qmake|-dwarf2|-reduce-relocations|-sse|-openssl|-openssl-linked|-ptmalloc|-xmlpatterns|-phonon|-phonon-backend|-multimedia|-audio-backend|-svg|-declarative|-declarative-debug|-javascript-jit|-script|-scripttools|-rpath|-force-pkg-config|-s60|-usedeffiles|-icu) -incremental|-qvfb|-profile|-shared|-static|-sm|-xinerama|-xshape|-xsync|-xinput|-egl|-reduce-exports|-pch|-separate-debug-info|-stl|-freetype|-xcursor|-xfixes|-xrandr|-xrender|-mitshm|-fontconfig|-xkb|-xcb|-nis|-qdbus|-dbus|-dbus-linked|-glib|-gstreamer|-gtkstyle|-cups|-iconv|-largefile|-h|-help|-v|-verbose|-debug|-release|-fast|-accessibility|-confirm-license|-gnumake|-framework|-qt3support|-debug-and-release|-exceptions|-cocoa|-carbon|-universal|-harfbuzz|-prefix-install|-silent|-armfpa|-optimized-qmake|-dwarf2|-reduce-relocations|-sse|-openssl|-openssl-linked|-ptmalloc|-xmlpatterns|-phonon|-phonon-backend|-multimedia|-audio-backend|-svg|-v8|-declarative|-declarative-debug|-javascript-jit|-script|-scripttools|-rpath|-force-pkg-config|-s60|-usedeffiles|-icu)
VAR=`echo $1 | sed "s,^-\(.*\),\1,"` VAR=`echo $1 | sed "s,^-\(.*\),\1,"`
VAL=yes VAL=yes
;; ;;
@ -7361,6 +7361,7 @@ fi
canBuildQtXmlPatterns="yes" canBuildQtXmlPatterns="yes"
canBuildWebKit="$HAVE_STL" canBuildWebKit="$HAVE_STL"
canBuildQtConcurrent="yes" canBuildQtConcurrent="yes"
canBuildV8="yes"
# WebKit requires stdint.h # WebKit requires stdint.h
"$unixtests/compile.test" "$XQMAKESPEC" "$QMAKE_CONFIG" $OPT_VERBOSE "$relpath" "$outpath" config.tests/unix/stdint "Stdint" $L_FLAGS $I_FLAGS $l_FLAGS "$unixtests/compile.test" "$XQMAKESPEC" "$QMAKE_CONFIG" $OPT_VERBOSE "$relpath" "$outpath" config.tests/unix/stdint "Stdint" $L_FLAGS $I_FLAGS $l_FLAGS
@ -7584,8 +7585,18 @@ fi
#fi #fi
case "$CFG_ARCH" in
i386|x86_64|arm|macosx) ;;
*) canBuildV8="no";;
esac
if [ "$CFG_V8" = "yes" -a "$canBuildV8" = "no" ]; then
echo "Error: V8 was requested, but is not supported on this platform."
exit 1
fi
if [ "$CFG_V8" = "auto" ]; then if [ "$CFG_V8" = "auto" ]; then
CFG_V8=yes CFG_V8="$canBuildV8"
fi fi
if [ "$CFG_V8" = "no" ]; then if [ "$CFG_V8" = "no" ]; then

6
dist/changes-5.0.0 vendored
View File

@ -116,6 +116,9 @@ Qt for Windows CE
- moc - moc
* [QTBUG-20785] The moc now has a -b<file> option to #include an additional
file at the beginning of the generated file.
- uic - uic
@ -125,6 +128,9 @@ Qt for Windows CE
- qmake - qmake
* QMAKE_MOC_OPTIONS variable is now available for passing additional parameters
to the moc.
- configure - configure

View File

@ -45,10 +45,10 @@ defineReplace(mocCmdBase) {
contains(TEMPLATE, "vc.*") { contains(TEMPLATE, "vc.*") {
RET += $$mocinclude.commands RET += $$mocinclude.commands
} }
RET += $$QMAKE_MOC $(DEFINES) @$$WIN_INCLUDETEMP $$join(QMAKE_COMPILER_DEFINES, " -D", -D) RET += $$QMAKE_MOC $(DEFINES) @$$WIN_INCLUDETEMP $$join(QMAKE_COMPILER_DEFINES, " -D", -D) $$QMAKE_MOC_OPTIONS
return($$RET) return($$RET)
} }
return($$QMAKE_MOC $(DEFINES) $(INCPATH) $$join(QMAKE_COMPILER_DEFINES, " -D", -D)) return($$QMAKE_MOC $(DEFINES) $(INCPATH) $$join(QMAKE_COMPILER_DEFINES, " -D", -D) $$QMAKE_MOC_OPTIONS)
} }
#moc headers #moc headers

View File

@ -1524,8 +1524,8 @@ void VCXProjectWriter::write(XmlOutput &xml, const VCEventTool &tool)
{ {
xml xml
<< tag(tool.EventName) << tag(tool.EventName)
<< attrTagS(_Command, tool.CommandLine.join(vcxCommandSeparator())) << tag(_Command) << valueTag(tool.CommandLine.join(vcxCommandSeparator()))
<< attrTagS(_Message, tool.Description) << tag(_Message) << valueTag(tool.Description)
<< closetag(tool.EventName); << closetag(tool.EventName);
} }

View File

@ -3535,6 +3535,61 @@ bool QString::endsWith(const QChar &c, Qt::CaseSensitivity cs) const
} }
#if defined(QT_ALWAYS_HAVE_SSE2)
static inline __m128i mergeQuestionMarks(__m128i chunk)
{
const __m128i questionMark = _mm_set1_epi16('?');
# ifdef __SSE4_2__
// compare the unsigned shorts for the range 0x0100-0xFFFF
// note on the use of _mm_cmpestrm:
// The MSDN documentation online (http://technet.microsoft.com/en-us/library/bb514080.aspx)
// says for range search the following:
// For each character c in a, determine whether b0 <= c <= b1 or b2 <= c <= b3
//
// However, all examples on the Internet, including from Intel
// (see http://software.intel.com/en-us/articles/xml-parsing-accelerator-with-intel-streaming-simd-extensions-4-intel-sse4/)
// put the range to be searched first
//
// Disassembly and instruction-level debugging with GCC and ICC show
// that they are doing the right thing. Inverting the arguments in the
// instruction does cause a bunch of test failures.
const int mode = _SIDD_UWORD_OPS | _SIDD_CMP_RANGES | _SIDD_UNIT_MASK;
const __m128i rangeMatch = _mm_cvtsi32_si128(0xffff0100);
const __m128i offLimitMask = _mm_cmpestrm(rangeMatch, 2, chunk, 8, mode);
// replace the non-Latin 1 characters in the chunk with question marks
chunk = _mm_blendv_epi8(chunk, questionMark, offLimitMask);
# else
// SSE has no compare instruction for unsigned comparison.
// The variables must be shiffted + 0x8000 to be compared
const __m128i signedBitOffset = _mm_set1_epi16(0x8000);
const __m128i thresholdMask = _mm_set1_epi16(0xff + 0x8000);
const __m128i signedChunk = _mm_add_epi16(chunk, signedBitOffset);
const __m128i offLimitMask = _mm_cmpgt_epi16(signedChunk, thresholdMask);
# ifdef __SSE4_1__
// replace the non-Latin 1 characters in the chunk with question marks
chunk = _mm_blendv_epi8(chunk, questionMark, offLimitMask);
# else
// offLimitQuestionMark contains '?' for each 16 bits that was off-limit
// the 16 bits that were correct contains zeros
const __m128i offLimitQuestionMark = _mm_and_si128(offLimitMask, questionMark);
// correctBytes contains the bytes that were in limit
// the 16 bits that were off limits contains zeros
const __m128i correctBytes = _mm_andnot_si128(offLimitMask, chunk);
// merge offLimitQuestionMark and correctBytes to have the result
chunk = _mm_or_si128(correctBytes, offLimitQuestionMark);
# endif
# endif
return chunk;
}
#endif
static QByteArray toLatin1_helper(const QChar *data, int length) static QByteArray toLatin1_helper(const QChar *data, int length)
{ {
QByteArray ba; QByteArray ba;
@ -3545,41 +3600,15 @@ static QByteArray toLatin1_helper(const QChar *data, int length)
#if defined(QT_ALWAYS_HAVE_SSE2) #if defined(QT_ALWAYS_HAVE_SSE2)
if (length >= 16) { if (length >= 16) {
const int chunkCount = length >> 4; // divided by 16 const int chunkCount = length >> 4; // divided by 16
const __m128i questionMark = _mm_set1_epi16('?');
// SSE has no compare instruction for unsigned comparison.
// The variables must be shiffted + 0x8000 to be compared
const __m128i signedBitOffset = _mm_set1_epi16(short(0x8000));
const __m128i thresholdMask = _mm_set1_epi16(short(0xff + 0x8000));
for (int i = 0; i < chunkCount; ++i) { for (int i = 0; i < chunkCount; ++i) {
__m128i chunk1 = _mm_loadu_si128((__m128i*)src); // load __m128i chunk1 = _mm_loadu_si128((__m128i*)src); // load
chunk1 = mergeQuestionMarks(chunk1);
src += 8; src += 8;
{
// each 16 bit is equal to 0xFF if the source is outside latin 1 (>0xff)
const __m128i signedChunk = _mm_add_epi16(chunk1, signedBitOffset);
const __m128i offLimitMask = _mm_cmpgt_epi16(signedChunk, thresholdMask);
// offLimitQuestionMark contains '?' for each 16 bits that was off-limit
// the 16 bits that were correct contains zeros
const __m128i offLimitQuestionMark = _mm_and_si128(offLimitMask, questionMark);
// correctBytes contains the bytes that were in limit
// the 16 bits that were off limits contains zeros
const __m128i correctBytes = _mm_andnot_si128(offLimitMask, chunk1);
// merge offLimitQuestionMark and correctBytes to have the result
chunk1 = _mm_or_si128(correctBytes, offLimitQuestionMark);
}
__m128i chunk2 = _mm_loadu_si128((__m128i*)src); // load __m128i chunk2 = _mm_loadu_si128((__m128i*)src); // load
chunk2 = mergeQuestionMarks(chunk2);
src += 8; src += 8;
{
// exactly the same operations as for the previous chunk of data
const __m128i signedChunk = _mm_add_epi16(chunk2, signedBitOffset);
const __m128i offLimitMask = _mm_cmpgt_epi16(signedChunk, thresholdMask);
const __m128i offLimitQuestionMark = _mm_and_si128(offLimitMask, questionMark);
const __m128i correctBytes = _mm_andnot_si128(offLimitMask, chunk2);
chunk2 = _mm_or_si128(correctBytes, offLimitQuestionMark);
}
// pack the two vector to 16 x 8bits elements // pack the two vector to 16 x 8bits elements
const __m128i result = _mm_packus_epi16(chunk1, chunk2); const __m128i result = _mm_packus_epi16(chunk1, chunk2);

View File

@ -901,15 +901,38 @@ static const char *certificate_blacklist[] = {
"92:39:d5:34:8f:40:d1:69:5a:74:54:70:e1:f2:3f:43", "addons.mozilla.org", // Comodo "92:39:d5:34:8f:40:d1:69:5a:74:54:70:e1:f2:3f:43", "addons.mozilla.org", // Comodo
"b0:b7:13:3e:d0:96:f9:b5:6f:ae:91:c8:74:bd:3a:c0", "login.live.com", // Comodo "b0:b7:13:3e:d0:96:f9:b5:6f:ae:91:c8:74:bd:3a:c0", "login.live.com", // Comodo
"d8:f3:5f:4e:b7:87:2b:2d:ab:06:92:e3:15:38:2f:b0", "global trustee", // Comodo "d8:f3:5f:4e:b7:87:2b:2d:ab:06:92:e3:15:38:2f:b0", "global trustee", // Comodo
"05:e2:e6:a4:cd:09:ea:54:d6:65:b0:75:fe:22:a2:56", "*.google.com", // DigiNotar
"05:e2:e6:a4:cd:09:ea:54:d6:65:b0:75:fe:22:a2:56", "*.google.com", // leaf certificate issued by DigiNotar
"0c:76:da:9c:91:0c:4e:2c:9e:fe:15:d0:58:93:3c:4c", "DigiNotar Root CA", // DigiNotar root
"f1:4a:13:f4:87:2b:56:dc:39:df:84:ca:7a:a1:06:49", "DigiNotar Services CA", // DigiNotar intermediate signed by DigiNotar Root
"36:16:71:55:43:42:1b:9d:e6:cb:a3:64:41:df:24:38", "DigiNotar Services 1024 CA", // DigiNotar intermediate signed by DigiNotar Root
"0a:82:bd:1e:14:4e:88:14:d7:5b:1a:55:27:be:bf:3e", "DigiNotar Root CA G2", // other DigiNotar Root CA
"a4:b6:ce:e3:2e:d3:35:46:26:3c:b3:55:3a:a8:92:21", "CertiID Enterprise Certificate Authority", // DigiNotar intermediate signed by "DigiNotar Root CA G2"
"5b:d5:60:9c:64:17:68:cf:21:0e:35:fd:fb:05:ad:41", "DigiNotar Qualified CA", // DigiNotar intermediate signed by DigiNotar Root
"1184640176", "DigiNotar Services 1024 CA", // DigiNotar intermediate cross-signed by Entrust
"120000525", "DigiNotar Cyber CA", // DigiNotar intermediate cross-signed by CyberTrust
"120000505", "DigiNotar Cyber CA", // DigiNotar intermediate cross-signed by CyberTrust
"120000515", "DigiNotar Cyber CA", // DigiNotar intermediate cross-signed by CyberTrust
"20015536", "DigiNotar PKIoverheid CA Overheid en Bedrijven", // DigiNotar intermediate cross-signed by the Dutch government
"20001983", "DigiNotar PKIoverheid CA Organisatie - G2", // DigiNotar intermediate cross-signed by the Dutch government
"d6:d0:29:77:f1:49:fd:1a:83:f2:b9:ea:94:8c:5c:b4", "DigiNotar Extended Validation CA", // DigiNotar intermediate signed by DigiNotar EV Root
"1e:7d:7a:53:3d:45:30:41:96:40:0f:71:48:1f:45:04", "DigiNotar Public CA 2025", // DigiNotar intermediate
// "(has not been seen in the wild so far)", "DigiNotar Public CA - G2", // DigiNotar intermediate
// "(has not been seen in the wild so far)", "Koninklijke Notariele Beroepsorganisatie CA", // compromised during DigiNotar breach
// "(has not been seen in the wild so far)", "Stichting TTP Infos CA," // compromised during DigiNotar breach
"1184640175", "DigiNotar Root CA", // DigiNotar intermediate cross-signed by Entrust
"1184644297", "DigiNotar Root CA", // DigiNotar intermediate cross-signed by Entrust
0 0
}; };
bool QSslCertificatePrivate::isBlacklisted(const QSslCertificate &certificate) bool QSslCertificatePrivate::isBlacklisted(const QSslCertificate &certificate)
{ {
for (int a = 0; certificate_blacklist[a] != 0; a++) { for (int a = 0; certificate_blacklist[a] != 0; a++) {
QString blacklistedCommonName = QString::fromUtf8(certificate_blacklist[(a+1)]);
if (certificate.serialNumber() == certificate_blacklist[a++] && if (certificate.serialNumber() == certificate_blacklist[a++] &&
certificate.subjectInfo(QSslCertificate::CommonName).contains(QString::fromUtf8(certificate_blacklist[a]))) (certificate.subjectInfo(QSslCertificate::CommonName).contains(blacklistedCommonName) ||
certificate.issuerInfo(QSslCertificate::CommonName).contains(blacklistedCommonName)))
return true; return true;
} }
return false; return false;

View File

@ -1270,12 +1270,15 @@ bool QSslSocketBackendPrivate::startHandshake()
// Start translating errors. // Start translating errors.
QList<QSslError> errors; QList<QSslError> errors;
if (QSslCertificatePrivate::isBlacklisted(configuration.peerCertificate)) { // check the whole chain for blacklisting (including root, as we check for subjectInfo and issuer)
QSslError error(QSslError::CertificateBlacklisted, configuration.peerCertificate); foreach (const QSslCertificate &cert, configuration.peerCertificateChain) {
errors << error; if (QSslCertificatePrivate::isBlacklisted(cert)) {
emit q->peerVerifyError(error); QSslError error(QSslError::CertificateBlacklisted, cert);
if (q->state() != QAbstractSocket::ConnectedState) errors << error;
return false; emit q->peerVerifyError(error);
if (q->state() != QAbstractSocket::ConnectedState)
return false;
}
} }
bool doVerifyPeer = configuration.peerVerifyMode == QSslSocket::VerifyPeer bool doVerifyPeer = configuration.peerVerifyMode == QSslSocket::VerifyPeer

View File

@ -475,14 +475,14 @@ QFontEngine *QFontconfigDatabase::fontEngine(const QFontDef &f, QUnicodeTables::
fid.filename = fontfile->fileName.toLocal8Bit(); fid.filename = fontfile->fileName.toLocal8Bit();
fid.index = fontfile->indexValue; fid.index = fontfile->indexValue;
//try and get the pattern
FcPattern *pattern = FcPatternCreate();
bool antialias = !(fontDef.styleStrategy & QFont::NoAntialias); bool antialias = !(fontDef.styleStrategy & QFont::NoAntialias);
QFontEngineFT::GlyphFormat format = antialias? QFontEngineFT::Format_A8 : QFontEngineFT::Format_Mono; QFontEngineFT::GlyphFormat format = antialias? QFontEngineFT::Format_A8 : QFontEngineFT::Format_Mono;
engine = new QFontEngineFT(fontDef); engine = new QFontEngineFT(fontDef);
// try and get the pattern
FcPattern *pattern = FcPatternCreate();
FcValue value; FcValue value;
value.type = FcTypeString; value.type = FcTypeString;
QByteArray cs = fontDef.family.toUtf8(); QByteArray cs = fontDef.family.toUtf8();
@ -497,9 +497,8 @@ QFontEngine *QFontconfigDatabase::fontEngine(const QFontDef &f, QUnicodeTables::
value.u.i = fid.index; value.u.i = fid.index;
FcPatternAdd(pattern,FC_INDEX,value,true); FcPatternAdd(pattern,FC_INDEX,value,true);
QFontEngineFT::HintStyle default_hint_style;
if (FcConfigSubstitute(0,pattern,FcMatchPattern)) { if (FcConfigSubstitute(0,pattern,FcMatchPattern)) {
QFontEngineFT::HintStyle default_hint_style;
//hinting //hinting
int hint_style = 0; int hint_style = 0;
@ -519,9 +518,10 @@ QFontEngine *QFontconfigDatabase::fontEngine(const QFontDef &f, QUnicodeTables::
default_hint_style = QFontEngineFT::HintFull; default_hint_style = QFontEngineFT::HintFull;
break; break;
} }
engine->setDefaultHintStyle(default_hint_style);
} }
FcPatternDestroy(pattern);
engine->setDefaultHintStyle(default_hint_style);
if (!engine->init(fid,antialias,format)) { if (!engine->init(fid,antialias,format)) {
delete engine; delete engine;
engine = 0; engine = 0;
@ -576,26 +576,29 @@ QStringList QFontconfigDatabase::fallbacksForFamily(const QString family, const
} }
FcConfigSubstitute(0, pattern, FcMatchPattern); FcConfigSubstitute(0, pattern, FcMatchPattern);
FcConfigSubstitute(0, pattern, FcMatchFont); FcDefaultSubstitute(pattern);
FcResult result = FcResultMatch; FcResult result = FcResultMatch;
FcFontSet *fontSet = FcFontSort(0,pattern,FcFalse,0,&result); FcFontSet *fontSet = FcFontSort(0,pattern,FcFalse,0,&result);
FcPatternDestroy(pattern);
if (fontSet && result == FcResultMatch) if (fontSet) {
{ if (result == FcResultMatch) {
for (int i = 0; i < fontSet->nfont; i++) { for (int i = 0; i < fontSet->nfont; i++) {
FcChar8 *value = 0; FcChar8 *value = 0;
if (FcPatternGetString(fontSet->fonts[i], FC_FAMILY, 0, &value) != FcResultMatch) if (FcPatternGetString(fontSet->fonts[i], FC_FAMILY, 0, &value) != FcResultMatch)
continue; continue;
// capitalize(value); // capitalize(value);
QString familyName = QString::fromUtf8((const char *)value); QString familyName = QString::fromUtf8((const char *)value);
if (!fallbackFamilies.contains(familyName,Qt::CaseInsensitive)) { if (!fallbackFamilies.contains(familyName,Qt::CaseInsensitive) &&
fallbackFamilies << familyName; familyName.compare(family, Qt::CaseInsensitive)) {
fallbackFamilies << familyName;
}
} }
} }
FcFontSetDestroy(fontSet);
} }
// qDebug() << "fallbackFamilies for:" << family << fallbackFamilies; // qDebug() << "fallbackFamilies for:" << family << style << styleHint << script << fallbackFamilies;
return fallbackFamilies; return fallbackFamilies;
} }

View File

@ -83,7 +83,8 @@ void error(const char *msg = "Invalid argument")
" -U<macro> undefine macro\n" " -U<macro> undefine macro\n"
" -i do not generate an #include statement\n" " -i do not generate an #include statement\n"
" -p<path> path prefix for included file\n" " -p<path> path prefix for included file\n"
" -f[<file>] force #include, optional file name\n" " -f[<file>] force #include, optional file name (overwrite default)\n"
" -b<file> prepend #include <file> (preserve default include)\n"
" -nn do not display notes\n" " -nn do not display notes\n"
" -nw do not display warnings\n" " -nw do not display warnings\n"
" @<file> read additional options from file\n" " @<file> read additional options from file\n"
@ -156,6 +157,7 @@ QByteArray composePreprocessorOutput(const Symbols &symbols) {
int runMoc(int _argc, char **_argv) int runMoc(int _argc, char **_argv)
{ {
bool autoInclude = true; bool autoInclude = true;
bool defaultInclude = true;
Preprocessor pp; Preprocessor pp;
Moc moc; Moc moc;
pp.macros["Q_MOC_RUN"]; pp.macros["Q_MOC_RUN"];
@ -226,8 +228,21 @@ int runMoc(int _argc, char **_argv)
break; break;
moc.noInclude = false; moc.noInclude = false;
autoInclude = false; autoInclude = false;
if (opt[1]) // -fsomething.h if (opt[1]) { // -fsomething.h
moc.includeFiles.append(opt.mid(1)); moc.includeFiles.append(opt.mid(1));
defaultInclude = false;
}
break;
case 'b':
if (ignoreConflictingOptions)
break;
if (!more) {
if (!(n < argc-1))
error("Missing file name for the -b option.");
moc.includeFiles.prepend(argv[++n]);
} else if (opt[1]) {
moc.includeFiles.prepend(opt.mid(1));
}
break; break;
case 'p': // include file path case 'p': // include file path
if (ignoreConflictingOptions) if (ignoreConflictingOptions)
@ -341,7 +356,7 @@ int runMoc(int _argc, char **_argv)
// spos >= -1 && ppos > spos => ppos >= 0 // spos >= -1 && ppos > spos => ppos >= 0
moc.noInclude = (ppos > spos && tolower(filename[ppos + 1]) != 'h'); moc.noInclude = (ppos > spos && tolower(filename[ppos + 1]) != 'h');
} }
if (moc.includeFiles.isEmpty()) { if (defaultInclude) {
if (moc.includePath.isEmpty()) { if (moc.includePath.isEmpty()) {
if (filename.size()) { if (filename.size()) {
if (output.size()) if (output.size())

View File

@ -1,27 +1,27 @@
From e13ce09287a56c920d5ffdc5d4662d49f1838f16 Mon Sep 17 00:00:00 2001 From 3dff2e903674d8ab5310d44281b57de36db659c9 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Mon, 23 May 2011 15:47:20 +1000 Date: Mon, 23 May 2011 15:47:20 +1000
Subject: [PATCH 01/16] Add hashing and comparison methods to v8::String Subject: [PATCH 01/15] Add hashing and comparison methods to v8::String
This allows us to more rapidly search for a v8::String inside This allows us to more rapidly search for a v8::String inside
a hash of QStrings. a hash of QStrings.
--- ---
include/v8.h | 44 ++++++++++++++++++++++++++++++ include/v8.h | 45 +++++++++++++++++++++++++++++++
src/api.cc | 43 +++++++++++++++++++++++++++++ src/api.cc | 43 +++++++++++++++++++++++++++++
src/heap-inl.h | 2 + src/heap-inl.h | 2 +
src/heap.cc | 3 ++ src/heap.cc | 3 ++
src/objects-inl.h | 1 + src/objects-inl.h | 1 +
src/objects.cc | 77 ++++++++++++++++++++++++++++++++++++++++++++++++++++- src/objects.cc | 77 ++++++++++++++++++++++++++++++++++++++++++++++++++++-
src/objects.h | 15 +++++++++- src/objects.h | 15 +++++++++-
7 files changed, 182 insertions(+), 3 deletions(-) 7 files changed, 183 insertions(+), 3 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index d15d024..bbd29e9 100644 index d15d024..be1ee71 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -994,6 +994,48 @@ class String : public Primitive { @@ -994,6 +994,49 @@ class String : public Primitive {
V8EXPORT int Utf8Length() const; V8EXPORT int Utf8Length() const;
/** /**
+ * Returns the hash of this string. + * Returns the hash of this string.
+ */ + */
@ -35,7 +35,7 @@ index d15d024..bbd29e9 100644
+ }; + };
+ +
+ /** + /**
+ * Returns the "complete" hash of the string. This is + * Returns the "complete" hash of the string. This is
+ * all the information about the string needed to implement + * all the information about the string needed to implement
+ * a very efficient hash keyed on the string. + * a very efficient hash keyed on the string.
+ * + *
@ -43,7 +43,7 @@ index d15d024..bbd29e9 100644
+ * length: The length of the string. Equivalent to Length() + * length: The length of the string. Equivalent to Length()
+ * hash: The hash of the string. Equivalent to Hash() + * hash: The hash of the string. Equivalent to Hash()
+ * symbol_id: If the string is a sequential symbol, the symbol + * symbol_id: If the string is a sequential symbol, the symbol
+ * id, otherwise 0. If the symbol ids of two strings are + * id, otherwise 0. If the symbol ids of two strings are
+ * the same (and non-zero) the two strings are identical. + * the same (and non-zero) the two strings are identical.
+ * If the symbol ids are different the strings may still be + * If the symbol ids are different the strings may still be
+ * identical, but an Equals() check must be performed. + * identical, but an Equals() check must be performed.
@ -63,15 +63,16 @@ index d15d024..bbd29e9 100644
+ */ + */
+ V8EXPORT bool Equals(uint16_t *string, int length); + V8EXPORT bool Equals(uint16_t *string, int length);
+ V8EXPORT bool Equals(char *string, int length); + V8EXPORT bool Equals(char *string, int length);
+ inline bool Equals(Handle<Value> that) const { return v8::Value::Equals(that); }
+ +
+ /** + /**
* Write the contents of the string to an external buffer. * Write the contents of the string to an external buffer.
* If no arguments are given, expects the buffer to be large * If no arguments are given, expects the buffer to be large
* enough to hold the entire string and NULL terminator. Copies * enough to hold the entire string and NULL terminator. Copies
@@ -1023,6 +1065,8 @@ class String : public Primitive { @@ -1023,6 +1066,8 @@ class String : public Primitive {
HINT_MANY_WRITES_EXPECTED = 1 HINT_MANY_WRITES_EXPECTED = 1
}; };
+ V8EXPORT uint16_t GetCharacter(int index); + V8EXPORT uint16_t GetCharacter(int index);
+ +
V8EXPORT int Write(uint16_t* buffer, V8EXPORT int Write(uint16_t* buffer,
@ -84,7 +85,7 @@ index a2373cd..381935b 100644
@@ -3284,6 +3284,49 @@ int String::Utf8Length() const { @@ -3284,6 +3284,49 @@ int String::Utf8Length() const {
return str->Utf8Length(); return str->Utf8Length();
} }
+uint32_t String::Hash() const { +uint32_t String::Hash() const {
+ i::Handle<i::String> str = Utils::OpenHandle(this); + i::Handle<i::String> str = Utils::OpenHandle(this);
+ if (IsDeadCheck(str->GetIsolate(), "v8::String::Hash()")) return 0; + if (IsDeadCheck(str->GetIsolate(), "v8::String::Hash()")) return 0;
@ -128,7 +129,7 @@ index a2373cd..381935b 100644
+ if (IsDeadCheck(str->GetIsolate(), "v8::String::Equals()")) return 0; + if (IsDeadCheck(str->GetIsolate(), "v8::String::Equals()")) return 0;
+ return str->SlowEqualsExternal(string, length); + return str->SlowEqualsExternal(string, length);
+} +}
int String::WriteUtf8(char* buffer, int String::WriteUtf8(char* buffer,
int capacity, int capacity,
diff --git a/src/heap-inl.h b/src/heap-inl.h diff --git a/src/heap-inl.h b/src/heap-inl.h
@ -140,17 +141,17 @@ index 99737ed..f4fce7b 100644
answer->set_length(str.length()); answer->set_length(str.length());
answer->set_hash_field(hash_field); answer->set_hash_field(hash_field);
+ SeqString::cast(answer)->set_symbol_id(0); + SeqString::cast(answer)->set_symbol_id(0);
ASSERT_EQ(size, answer->Size()); ASSERT_EQ(size, answer->Size());
@@ -126,6 +127,7 @@ MaybeObject* Heap::AllocateTwoByteSymbol(Vector<const uc16> str, @@ -126,6 +127,7 @@ MaybeObject* Heap::AllocateTwoByteSymbol(Vector<const uc16> str,
String* answer = String::cast(result); String* answer = String::cast(result);
answer->set_length(str.length()); answer->set_length(str.length());
answer->set_hash_field(hash_field); answer->set_hash_field(hash_field);
+ SeqString::cast(answer)->set_symbol_id(0); + SeqString::cast(answer)->set_symbol_id(0);
ASSERT_EQ(size, answer->Size()); ASSERT_EQ(size, answer->Size());
diff --git a/src/heap.cc b/src/heap.cc diff --git a/src/heap.cc b/src/heap.cc
index 2b6c11f..930c97b 100644 index 2b6c11f..930c97b 100644
--- a/src/heap.cc --- a/src/heap.cc
@ -160,9 +161,9 @@ index 2b6c11f..930c97b 100644
answer->set_length(chars); answer->set_length(chars);
answer->set_hash_field(hash_field); answer->set_hash_field(hash_field);
+ SeqString::cast(result)->set_symbol_id(0); + SeqString::cast(result)->set_symbol_id(0);
ASSERT_EQ(size, answer->Size()); ASSERT_EQ(size, answer->Size());
@@ -3561,6 +3562,7 @@ MaybeObject* Heap::AllocateRawAsciiString(int length, PretenureFlag pretenure) { @@ -3561,6 +3562,7 @@ MaybeObject* Heap::AllocateRawAsciiString(int length, PretenureFlag pretenure) {
HeapObject::cast(result)->set_map(ascii_string_map()); HeapObject::cast(result)->set_map(ascii_string_map());
String::cast(result)->set_length(length); String::cast(result)->set_length(length);
@ -184,12 +185,12 @@ index 65aec5d..c82080d 100644
--- a/src/objects-inl.h --- a/src/objects-inl.h
+++ b/src/objects-inl.h +++ b/src/objects-inl.h
@@ -1924,6 +1924,7 @@ INT_ACCESSORS(ExternalArray, length, kLengthOffset) @@ -1924,6 +1924,7 @@ INT_ACCESSORS(ExternalArray, length, kLengthOffset)
SMI_ACCESSORS(String, length, kLengthOffset) SMI_ACCESSORS(String, length, kLengthOffset)
+SMI_ACCESSORS(SeqString, symbol_id, kSymbolIdOffset) +SMI_ACCESSORS(SeqString, symbol_id, kSymbolIdOffset)
uint32_t String::hash_field() { uint32_t String::hash_field() {
diff --git a/src/objects.cc b/src/objects.cc diff --git a/src/objects.cc b/src/objects.cc
index df61956..dc4b260 100644 index df61956..dc4b260 100644
@ -198,7 +199,7 @@ index df61956..dc4b260 100644
@@ -5346,6 +5346,66 @@ static inline bool CompareStringContentsPartial(Isolate* isolate, @@ -5346,6 +5346,66 @@ static inline bool CompareStringContentsPartial(Isolate* isolate,
} }
} }
+bool String::SlowEqualsExternal(uc16 *string, int length) { +bool String::SlowEqualsExternal(uc16 *string, int length) {
+ int len = this->length(); + int len = this->length();
+ if (len != length) return false; + if (len != length) return false;
@ -259,11 +260,11 @@ index df61956..dc4b260 100644
+ return CompareStringContents(isolate->objects_string_compare_buffer_a(), &ib); + return CompareStringContents(isolate->objects_string_compare_buffer_a(), &ib);
+ } + }
+} +}
bool String::SlowEquals(String* other) { bool String::SlowEquals(String* other) {
// Fast check: negative check with lengths. // Fast check: negative check with lengths.
@@ -8655,9 +8715,24 @@ class AsciiSymbolKey : public SequentialSymbolKey<char> { @@ -8655,9 +8715,24 @@ class AsciiSymbolKey : public SequentialSymbolKey<char> {
MaybeObject* AsObject() { MaybeObject* AsObject() {
if (hash_field_ == 0) Hash(); if (hash_field_ == 0) Hash();
- return HEAP->AllocateAsciiSymbol(string_, hash_field_); - return HEAP->AllocateAsciiSymbol(string_, hash_field_);
@ -285,8 +286,8 @@ index df61956..dc4b260 100644
+ static Atomic32 next_symbol_id; + static Atomic32 next_symbol_id;
}; };
+Atomic32 AsciiSymbolKey::next_symbol_id = 1; +Atomic32 AsciiSymbolKey::next_symbol_id = 1;
class TwoByteSymbolKey : public SequentialSymbolKey<uc16> { class TwoByteSymbolKey : public SequentialSymbolKey<uc16> {
diff --git a/src/objects.h b/src/objects.h diff --git a/src/objects.h b/src/objects.h
index e966b3d..6e26f57 100644 index e966b3d..6e26f57 100644
@ -295,7 +296,7 @@ index e966b3d..6e26f57 100644
@@ -5359,6 +5359,9 @@ class String: public HeapObject { @@ -5359,6 +5359,9 @@ class String: public HeapObject {
bool IsAsciiEqualTo(Vector<const char> str); bool IsAsciiEqualTo(Vector<const char> str);
bool IsTwoByteEqualTo(Vector<const uc16> str); bool IsTwoByteEqualTo(Vector<const uc16> str);
+ bool SlowEqualsExternal(uc16 *string, int length); + bool SlowEqualsExternal(uc16 *string, int length);
+ bool SlowEqualsExternal(char *string, int length); + bool SlowEqualsExternal(char *string, int length);
+ +
@ -305,14 +306,14 @@ index e966b3d..6e26f57 100644
@@ -5610,9 +5613,17 @@ class String: public HeapObject { @@ -5610,9 +5613,17 @@ class String: public HeapObject {
class SeqString: public String { class SeqString: public String {
public: public:
+ // Get and set the symbol id of the string + // Get and set the symbol id of the string
+ inline int symbol_id(); + inline int symbol_id();
+ inline void set_symbol_id(int value); + inline void set_symbol_id(int value);
+ +
// Casting. // Casting.
static inline SeqString* cast(Object* obj); static inline SeqString* cast(Object* obj);
+ // Layout description. + // Layout description.
+ static const int kSymbolIdOffset = String::kSize; + static const int kSymbolIdOffset = String::kSize;
+ static const int kSize = kSymbolIdOffset + kPointerSize; + static const int kSize = kSymbolIdOffset + kPointerSize;
@ -322,22 +323,22 @@ index e966b3d..6e26f57 100644
}; };
@@ -5647,7 +5658,7 @@ class SeqAsciiString: public SeqString { @@ -5647,7 +5658,7 @@ class SeqAsciiString: public SeqString {
} }
// Layout description. // Layout description.
- static const int kHeaderSize = String::kSize; - static const int kHeaderSize = String::kSize;
+ static const int kHeaderSize = SeqString::kSize; + static const int kHeaderSize = SeqString::kSize;
static const int kAlignedSize = POINTER_SIZE_ALIGN(kHeaderSize); static const int kAlignedSize = POINTER_SIZE_ALIGN(kHeaderSize);
// Maximal memory usage for a single sequential ASCII string. // Maximal memory usage for a single sequential ASCII string.
@@ -5701,7 +5712,7 @@ class SeqTwoByteString: public SeqString { @@ -5701,7 +5712,7 @@ class SeqTwoByteString: public SeqString {
} }
// Layout description. // Layout description.
- static const int kHeaderSize = String::kSize; - static const int kHeaderSize = String::kSize;
+ static const int kHeaderSize = SeqString::kSize; + static const int kHeaderSize = SeqString::kSize;
static const int kAlignedSize = POINTER_SIZE_ALIGN(kHeaderSize); static const int kAlignedSize = POINTER_SIZE_ALIGN(kHeaderSize);
// Maximal memory usage for a single sequential two-byte string. // Maximal memory usage for a single sequential two-byte string.
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From 7c9cfff80b7864d5687432d424074e51712c4a07 Mon Sep 17 00:00:00 2001 From 01f7bd262fb1be893fe4bdc6b98a1b43c5a0bb7d Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Mon, 23 May 2011 15:55:26 +1000 Date: Mon, 23 May 2011 15:55:26 +1000
Subject: [PATCH 02/16] Add a bit field 3 to Map Subject: [PATCH 02/15] Add a bit field 3 to Map
Bit field 3 will be used to add QML specific map flags. Bit field 3 will be used to add QML specific map flags.
--- ---
@ -22,13 +22,13 @@ index 930c97b..900f462 100644
+ reinterpret_cast<Map*>(result)->set_bit_field3(0); + reinterpret_cast<Map*>(result)->set_bit_field3(0);
return result; return result;
} }
@@ -1599,6 +1600,7 @@ MaybeObject* Heap::AllocateMap(InstanceType instance_type, int instance_size) { @@ -1599,6 +1600,7 @@ MaybeObject* Heap::AllocateMap(InstanceType instance_type, int instance_size) {
map->set_unused_property_fields(0); map->set_unused_property_fields(0);
map->set_bit_field(0); map->set_bit_field(0);
map->set_bit_field2((1 << Map::kIsExtensible) | (1 << Map::kHasFastElements)); map->set_bit_field2((1 << Map::kIsExtensible) | (1 << Map::kHasFastElements));
+ map->set_bit_field3(0); + map->set_bit_field3(0);
// If the map object is aligned fill the padding area with Smi 0 objects. // If the map object is aligned fill the padding area with Smi 0 objects.
if (Map::kPadStart < Map::kSize) { if (Map::kPadStart < Map::kSize) {
diff --git a/src/objects-inl.h b/src/objects-inl.h diff --git a/src/objects-inl.h b/src/objects-inl.h
@ -37,8 +37,8 @@ index c82080d..cce3edd 100644
+++ b/src/objects-inl.h +++ b/src/objects-inl.h
@@ -2430,6 +2430,16 @@ void Map::set_bit_field2(byte value) { @@ -2430,6 +2430,16 @@ void Map::set_bit_field2(byte value) {
} }
+byte Map::bit_field3() { +byte Map::bit_field3() {
+ return READ_BYTE_FIELD(this, kBitField3Offset); + return READ_BYTE_FIELD(this, kBitField3Offset);
+} +}
@ -65,13 +65,13 @@ index dc4b260..79d7240 100644
Map::cast(result)->ClearCodeCache(heap); Map::cast(result)->ClearCodeCache(heap);
return result; return result;
@@ -3642,6 +3643,7 @@ MaybeObject* Map::CopyNormalized(PropertyNormalizationMode mode, @@ -3642,6 +3643,7 @@ MaybeObject* Map::CopyNormalized(PropertyNormalizationMode mode,
Map::cast(result)->set_bit_field(bit_field()); Map::cast(result)->set_bit_field(bit_field());
Map::cast(result)->set_bit_field2(bit_field2()); Map::cast(result)->set_bit_field2(bit_field2());
+ Map::cast(result)->set_bit_field3(bit_field3()); + Map::cast(result)->set_bit_field3(bit_field3());
Map::cast(result)->set_is_shared(sharing == SHARED_NORMALIZED_MAP); Map::cast(result)->set_is_shared(sharing == SHARED_NORMALIZED_MAP);
diff --git a/src/objects.h b/src/objects.h diff --git a/src/objects.h b/src/objects.h
index 6e26f57..07e1089 100644 index 6e26f57..07e1089 100644
--- a/src/objects.h --- a/src/objects.h
@ -79,7 +79,7 @@ index 6e26f57..07e1089 100644
@@ -3597,6 +3597,10 @@ class Map: public HeapObject { @@ -3597,6 +3597,10 @@ class Map: public HeapObject {
inline byte bit_field2(); inline byte bit_field2();
inline void set_bit_field2(byte value); inline void set_bit_field2(byte value);
+ // Bit field 3. + // Bit field 3.
+ inline byte bit_field3(); + inline byte bit_field3();
+ inline void set_bit_field3(byte value); + inline void set_bit_field3(byte value);
@ -101,18 +101,18 @@ index 6e26f57..07e1089 100644
static const int kBitFieldOffset = kInstanceAttributesOffset + 2; static const int kBitFieldOffset = kInstanceAttributesOffset + 2;
static const int kBitField2Offset = kInstanceAttributesOffset + 3; static const int kBitField2Offset = kInstanceAttributesOffset + 3;
+ static const int kBitField3Offset = kInstanceAttributesOffset + 4; + static const int kBitField3Offset = kInstanceAttributesOffset + 4;
STATIC_CHECK(kInstanceTypeOffset == Internals::kMapInstanceTypeOffset); STATIC_CHECK(kInstanceTypeOffset == Internals::kMapInstanceTypeOffset);
@@ -3898,6 +3903,8 @@ class Map: public HeapObject { @@ -3898,6 +3903,8 @@ class Map: public HeapObject {
static const int kIsShared = 5; static const int kIsShared = 5;
static const int kHasExternalArrayElements = 6; static const int kHasExternalArrayElements = 6;
+ // Bit positions for bit field 3 + // Bit positions for bit field 3
+ +
// Layout of the default cache. It holds alternating name and code objects. // Layout of the default cache. It holds alternating name and code objects.
static const int kCodeCacheEntrySize = 2; static const int kCodeCacheEntrySize = 2;
static const int kCodeCacheEntryNameOffset = 0; static const int kCodeCacheEntryNameOffset = 0;
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From ae8688b53d67044f2c9b0cce25fc282b078610c1 Mon Sep 17 00:00:00 2001 From 530ded6ea634bccb96652cd3e0cf67725449ed63 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Mon, 23 May 2011 16:21:02 +1000 Date: Mon, 23 May 2011 16:21:02 +1000
Subject: [PATCH 03/16] Add a "fallback" mode for named property interceptors Subject: [PATCH 03/15] Add a "fallback" mode for named property interceptors
By default interceptors are called before the normal property By default interceptors are called before the normal property
resolution on objects. When an interceptor is installed as a resolution on objects. When an interceptor is installed as a
@ -24,10 +24,10 @@ declarations.
9 files changed, 99 insertions(+), 18 deletions(-) 9 files changed, 99 insertions(+), 18 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index bbd29e9..85452aa 100644 index be1ee71..bb31ea0 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -2169,6 +2169,7 @@ class V8EXPORT FunctionTemplate : public Template { @@ -2170,6 +2170,7 @@ class V8EXPORT FunctionTemplate : public Template {
NamedPropertyQuery query, NamedPropertyQuery query,
NamedPropertyDeleter remover, NamedPropertyDeleter remover,
NamedPropertyEnumerator enumerator, NamedPropertyEnumerator enumerator,
@ -35,10 +35,10 @@ index bbd29e9..85452aa 100644
Handle<Value> data); Handle<Value> data);
void SetIndexedInstancePropertyHandler(IndexedPropertyGetter getter, void SetIndexedInstancePropertyHandler(IndexedPropertyGetter getter,
IndexedPropertySetter setter, IndexedPropertySetter setter,
@@ -2253,6 +2254,13 @@ class V8EXPORT ObjectTemplate : public Template { @@ -2254,6 +2255,13 @@ class V8EXPORT ObjectTemplate : public Template {
NamedPropertyEnumerator enumerator = 0, NamedPropertyEnumerator enumerator = 0,
Handle<Value> data = Handle<Value>()); Handle<Value> data = Handle<Value>());
+ void SetFallbackPropertyHandler(NamedPropertyGetter getter, + void SetFallbackPropertyHandler(NamedPropertyGetter getter,
+ NamedPropertySetter setter = 0, + NamedPropertySetter setter = 0,
+ NamedPropertyQuery query = 0, + NamedPropertyQuery query = 0,
@ -66,7 +66,7 @@ index 381935b..8b0b32a 100644
if (remover != 0) SET_FIELD_WRAPPED(obj, set_deleter, remover); if (remover != 0) SET_FIELD_WRAPPED(obj, set_deleter, remover);
if (enumerator != 0) SET_FIELD_WRAPPED(obj, set_enumerator, enumerator); if (enumerator != 0) SET_FIELD_WRAPPED(obj, set_enumerator, enumerator);
+ obj->set_is_fallback(i::Smi::FromInt(is_fallback)); + obj->set_is_fallback(i::Smi::FromInt(is_fallback));
if (data.IsEmpty()) data = v8::Undefined(); if (data.IsEmpty()) data = v8::Undefined();
obj->set_data(*Utils::OpenHandle(*data)); obj->set_data(*Utils::OpenHandle(*data));
@@ -1143,6 +1145,33 @@ void ObjectTemplate::SetNamedPropertyHandler(NamedPropertyGetter getter, @@ -1143,6 +1145,33 @@ void ObjectTemplate::SetNamedPropertyHandler(NamedPropertyGetter getter,
@ -102,7 +102,7 @@ index 381935b..8b0b32a 100644
+ true, + true,
data); data);
} }
diff --git a/src/factory.cc b/src/factory.cc diff --git a/src/factory.cc b/src/factory.cc
index 7dee66f..dcdc645 100644 index 7dee66f..dcdc645 100644
--- a/src/factory.cc --- a/src/factory.cc
@ -131,11 +131,11 @@ index 326de86..dd3a86c 100644
+ bool skip_fallback_interceptor) { + bool skip_fallback_interceptor) {
CALL_HEAP_FUNCTION(object->GetIsolate(), CALL_HEAP_FUNCTION(object->GetIsolate(),
- object->SetProperty(*key, *value, attributes, strict_mode), - object->SetProperty(*key, *value, attributes, strict_mode),
+ object->SetProperty(*key, *value, attributes, strict_mode, + object->SetProperty(*key, *value, attributes, strict_mode,
+ skip_fallback_interceptor), + skip_fallback_interceptor),
Object); Object);
} }
diff --git a/src/handles.h b/src/handles.h diff --git a/src/handles.h b/src/handles.h
index 3839f37..4b42506 100644 index 3839f37..4b42506 100644
--- a/src/handles.h --- a/src/handles.h
@ -147,7 +147,7 @@ index 3839f37..4b42506 100644
- StrictModeFlag strict_mode); - StrictModeFlag strict_mode);
+ StrictModeFlag strict_mode, + StrictModeFlag strict_mode,
+ bool skip_fallback_interceptor = false); + bool skip_fallback_interceptor = false);
Handle<Object> SetProperty(Handle<Object> object, Handle<Object> SetProperty(Handle<Object> object,
Handle<Object> key, Handle<Object> key,
diff --git a/src/objects-inl.h b/src/objects-inl.h diff --git a/src/objects-inl.h b/src/objects-inl.h
@ -156,8 +156,8 @@ index cce3edd..6aaca2f 100644
+++ b/src/objects-inl.h +++ b/src/objects-inl.h
@@ -2521,6 +2521,21 @@ bool Map::is_shared() { @@ -2521,6 +2521,21 @@ bool Map::is_shared() {
} }
+void Map::set_named_interceptor_is_fallback(bool value) +void Map::set_named_interceptor_is_fallback(bool value)
+{ +{
+ if (value) { + if (value) {
@ -181,7 +181,7 @@ index cce3edd..6aaca2f 100644
ACCESSORS(InterceptorInfo, enumerator, Object, kEnumeratorOffset) ACCESSORS(InterceptorInfo, enumerator, Object, kEnumeratorOffset)
ACCESSORS(InterceptorInfo, data, Object, kDataOffset) ACCESSORS(InterceptorInfo, data, Object, kDataOffset)
+ACCESSORS(InterceptorInfo, is_fallback, Smi, kFallbackOffset) +ACCESSORS(InterceptorInfo, is_fallback, Smi, kFallbackOffset)
ACCESSORS(CallHandlerInfo, callback, Object, kCallbackOffset) ACCESSORS(CallHandlerInfo, callback, Object, kCallbackOffset)
ACCESSORS(CallHandlerInfo, data, Object, kDataOffset) ACCESSORS(CallHandlerInfo, data, Object, kDataOffset)
diff --git a/src/objects.cc b/src/objects.cc diff --git a/src/objects.cc b/src/objects.cc
@ -200,20 +200,20 @@ index 79d7240..15e2cdb 100644
+ LocalLookup(name, &result, skip_fallback_interceptor); + LocalLookup(name, &result, skip_fallback_interceptor);
return SetProperty(&result, name, value, attributes, strict_mode); return SetProperty(&result, name, value, attributes, strict_mode);
} }
@@ -3148,7 +3149,8 @@ AccessorDescriptor* Map::FindAccessor(String* name) { @@ -3148,7 +3149,8 @@ AccessorDescriptor* Map::FindAccessor(String* name) {
} }
-void JSObject::LocalLookup(String* name, LookupResult* result) { -void JSObject::LocalLookup(String* name, LookupResult* result) {
+void JSObject::LocalLookup(String* name, LookupResult* result, +void JSObject::LocalLookup(String* name, LookupResult* result,
+ bool skip_fallback_interceptor) { + bool skip_fallback_interceptor) {
ASSERT(name->IsString()); ASSERT(name->IsString());
Heap* heap = GetHeap(); Heap* heap = GetHeap();
@@ -3174,22 +3176,30 @@ void JSObject::LocalLookup(String* name, LookupResult* result) { @@ -3174,22 +3176,30 @@ void JSObject::LocalLookup(String* name, LookupResult* result) {
} }
// Check for lookup interceptor except when bootstrapping. // Check for lookup interceptor except when bootstrapping.
- if (HasNamedInterceptor() && !heap->isolate()->bootstrapper()->IsActive()) { - if (HasNamedInterceptor() && !heap->isolate()->bootstrapper()->IsActive()) {
+ bool wouldIntercept = HasNamedInterceptor() && !heap->isolate()->bootstrapper()->IsActive(); + bool wouldIntercept = HasNamedInterceptor() && !heap->isolate()->bootstrapper()->IsActive();
@ -221,19 +221,19 @@ index 79d7240..15e2cdb 100644
result->InterceptorResult(this); result->InterceptorResult(this);
return; return;
} }
LocalLookupRealNamedProperty(name, result); LocalLookupRealNamedProperty(name, result);
+ +
+ if (wouldIntercept && !skip_fallback_interceptor && !result->IsProperty() && + if (wouldIntercept && !skip_fallback_interceptor && !result->IsProperty() &&
+ map()->named_interceptor_is_fallback()) { + map()->named_interceptor_is_fallback()) {
+ result->InterceptorResult(this); + result->InterceptorResult(this);
+ return; + return;
+ } + }
} }
-void JSObject::Lookup(String* name, LookupResult* result) { -void JSObject::Lookup(String* name, LookupResult* result) {
+void JSObject::Lookup(String* name, LookupResult* result, +void JSObject::Lookup(String* name, LookupResult* result,
+ bool skip_fallback_interceptor) { + bool skip_fallback_interceptor) {
// Ecma-262 3rd 8.6.2.4 // Ecma-262 3rd 8.6.2.4
Heap* heap = GetHeap(); Heap* heap = GetHeap();
@ -260,21 +260,21 @@ index 07e1089..a209cd0 100644
String* key, String* key,
Object* value, Object* value,
@@ -1637,8 +1638,8 @@ class JSObject: public HeapObject { @@ -1637,8 +1638,8 @@ class JSObject: public HeapObject {
// Lookup a property. If found, the result is valid and has // Lookup a property. If found, the result is valid and has
// detailed information. // detailed information.
- void LocalLookup(String* name, LookupResult* result); - void LocalLookup(String* name, LookupResult* result);
- void Lookup(String* name, LookupResult* result); - void Lookup(String* name, LookupResult* result);
+ void LocalLookup(String* name, LookupResult* result, bool skip_fallback_interceptor = false); + void LocalLookup(String* name, LookupResult* result, bool skip_fallback_interceptor = false);
+ void Lookup(String* name, LookupResult* result, bool skip_fallback_interceptor = false); + void Lookup(String* name, LookupResult* result, bool skip_fallback_interceptor = false);
// The following lookup functions skip interceptors. // The following lookup functions skip interceptors.
void LocalLookupRealNamedProperty(String* name, LookupResult* result); void LocalLookupRealNamedProperty(String* name, LookupResult* result);
@@ -3714,6 +3715,12 @@ class Map: public HeapObject { @@ -3714,6 +3715,12 @@ class Map: public HeapObject {
inline void set_is_access_check_needed(bool access_check_needed); inline void set_is_access_check_needed(bool access_check_needed);
inline bool is_access_check_needed(); inline bool is_access_check_needed();
+ +
+ // Whether the named interceptor is a fallback interceptor or not + // Whether the named interceptor is a fallback interceptor or not
+ inline void set_named_interceptor_is_fallback(bool value); + inline void set_named_interceptor_is_fallback(bool value);
+ inline bool named_interceptor_is_fallback(); + inline bool named_interceptor_is_fallback();
@ -282,13 +282,13 @@ index 07e1089..a209cd0 100644
+ +
// [prototype]: implicit prototype object. // [prototype]: implicit prototype object.
DECL_ACCESSORS(prototype, Object) DECL_ACCESSORS(prototype, Object)
@@ -3904,6 +3911,7 @@ class Map: public HeapObject { @@ -3904,6 +3911,7 @@ class Map: public HeapObject {
static const int kHasExternalArrayElements = 6; static const int kHasExternalArrayElements = 6;
// Bit positions for bit field 3 // Bit positions for bit field 3
+ static const int kNamedInterceptorIsFallback = 0; + static const int kNamedInterceptorIsFallback = 0;
// Layout of the default cache. It holds alternating name and code objects. // Layout of the default cache. It holds alternating name and code objects.
static const int kCodeCacheEntrySize = 2; static const int kCodeCacheEntrySize = 2;
@@ -6276,6 +6284,7 @@ class InterceptorInfo: public Struct { @@ -6276,6 +6284,7 @@ class InterceptorInfo: public Struct {
@ -296,9 +296,9 @@ index 07e1089..a209cd0 100644
DECL_ACCESSORS(enumerator, Object) DECL_ACCESSORS(enumerator, Object)
DECL_ACCESSORS(data, Object) DECL_ACCESSORS(data, Object)
+ DECL_ACCESSORS(is_fallback, Smi) + DECL_ACCESSORS(is_fallback, Smi)
static inline InterceptorInfo* cast(Object* obj); static inline InterceptorInfo* cast(Object* obj);
@@ -6295,7 +6304,8 @@ class InterceptorInfo: public Struct { @@ -6295,7 +6304,8 @@ class InterceptorInfo: public Struct {
static const int kDeleterOffset = kQueryOffset + kPointerSize; static const int kDeleterOffset = kQueryOffset + kPointerSize;
static const int kEnumeratorOffset = kDeleterOffset + kPointerSize; static const int kEnumeratorOffset = kDeleterOffset + kPointerSize;
@ -306,7 +306,7 @@ index 07e1089..a209cd0 100644
- static const int kSize = kDataOffset + kPointerSize; - static const int kSize = kDataOffset + kPointerSize;
+ static const int kFallbackOffset = kDataOffset + kPointerSize; + static const int kFallbackOffset = kDataOffset + kPointerSize;
+ static const int kSize = kFallbackOffset + kPointerSize; + static const int kSize = kFallbackOffset + kPointerSize;
private: private:
DISALLOW_IMPLICIT_CONSTRUCTORS(InterceptorInfo); DISALLOW_IMPLICIT_CONSTRUCTORS(InterceptorInfo);
diff --git a/src/runtime.cc b/src/runtime.cc diff --git a/src/runtime.cc b/src/runtime.cc
@ -324,11 +324,11 @@ index 7335da8..660352c 100644
// against the global object. The information will be used to // against the global object. The information will be used to
@@ -1152,7 +1152,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) { @@ -1152,7 +1152,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) {
} }
LookupResult lookup; LookupResult lookup;
- global->LocalLookup(*name, &lookup); - global->LocalLookup(*name, &lookup);
+ global->LocalLookup(*name, &lookup, true); + global->LocalLookup(*name, &lookup, true);
PropertyAttributes attributes = is_const_property PropertyAttributes attributes = is_const_property
? static_cast<PropertyAttributes>(base | READ_ONLY) ? static_cast<PropertyAttributes>(base | READ_ONLY)
@@ -1196,7 +1196,8 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) { @@ -1196,7 +1196,8 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) {
@ -340,7 +340,7 @@ index 7335da8..660352c 100644
+ true)); + true));
} }
} }
@@ -1343,7 +1344,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) { @@ -1343,7 +1344,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) {
JSObject* real_holder = global; JSObject* real_holder = global;
LookupResult lookup; LookupResult lookup;
@ -351,7 +351,7 @@ index 7335da8..660352c 100644
// Determine if this is a redeclaration of something read-only. // Determine if this is a redeclaration of something read-only.
if (lookup.IsReadOnly()) { if (lookup.IsReadOnly()) {
@@ -1400,7 +1401,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) { @@ -1400,7 +1401,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) {
global = isolate->context()->global(); global = isolate->context()->global();
if (assign) { if (assign) {
- return global->SetProperty(*name, args[2], attributes, strict_mode); - return global->SetProperty(*name, args[2], attributes, strict_mode);
@ -359,6 +359,6 @@ index 7335da8..660352c 100644
} }
return isolate->heap()->undefined_value(); return isolate->heap()->undefined_value();
} }
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From 4827116b12c50f6662794017c5a662b5dbb2da0b Mon Sep 17 00:00:00 2001 From f9368b52060c31e9532ef26f6cca1a2cb0283f51 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Mon, 23 May 2011 16:55:35 +1000 Date: Mon, 23 May 2011 16:55:35 +1000
Subject: [PATCH 04/16] Generalize external object resources Subject: [PATCH 04/15] Generalize external object resources
V8 was already able to manage and finalize an external string V8 was already able to manage and finalize an external string
resource. This change generalizes that mechanism to handle a resource. This change generalizes that mechanism to handle a
@ -31,13 +31,13 @@ object space.
11 files changed, 280 insertions(+), 115 deletions(-) 11 files changed, 280 insertions(+), 115 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 85452aa..7f06ae7 100644 index bb31ea0..205e856 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -1630,6 +1630,25 @@ class Object : public Value { @@ -1631,6 +1631,25 @@ class Object : public Value {
/** Sets a native pointer in an internal field. */ /** Sets a native pointer in an internal field. */
V8EXPORT void SetPointerInInternalField(int index, void* value); V8EXPORT void SetPointerInInternalField(int index, void* value);
+ class V8EXPORT ExternalResource { // NOLINT + class V8EXPORT ExternalResource { // NOLINT
+ public: + public:
+ ExternalResource() {} + ExternalResource() {}
@ -60,10 +60,10 @@ index 85452aa..7f06ae7 100644
// Testers for local properties. // Testers for local properties.
V8EXPORT bool HasRealNamedProperty(Handle<String> key); V8EXPORT bool HasRealNamedProperty(Handle<String> key);
V8EXPORT bool HasRealIndexedProperty(uint32_t index); V8EXPORT bool HasRealIndexedProperty(uint32_t index);
@@ -2331,6 +2350,12 @@ class V8EXPORT ObjectTemplate : public Template { @@ -2332,6 +2351,12 @@ class V8EXPORT ObjectTemplate : public Template {
*/ */
void SetInternalFieldCount(int value); void SetInternalFieldCount(int value);
+ /** + /**
+ * Sets whether the object can store an "external resource" object. + * Sets whether the object can store an "external resource" object.
+ */ + */
@ -79,8 +79,8 @@ index 8b0b32a..1a6fbbb 100644
+++ b/src/api.cc +++ b/src/api.cc
@@ -1294,6 +1294,34 @@ void ObjectTemplate::SetInternalFieldCount(int value) { @@ -1294,6 +1294,34 @@ void ObjectTemplate::SetInternalFieldCount(int value) {
} }
+bool ObjectTemplate::HasExternalResource() +bool ObjectTemplate::HasExternalResource()
+{ +{
+ if (IsDeadCheck(Utils::OpenHandle(this)->GetIsolate(), + if (IsDeadCheck(Utils::OpenHandle(this)->GetIsolate(),
@ -110,12 +110,12 @@ index 8b0b32a..1a6fbbb 100644
+ +
+ +
// --- S c r i p t D a t a --- // --- S c r i p t D a t a ---
@@ -3652,6 +3680,34 @@ void v8::Object::SetPointerInInternalField(int index, void* value) { @@ -3652,6 +3680,34 @@ void v8::Object::SetPointerInInternalField(int index, void* value) {
} }
+void v8::Object::SetExternalResource(v8::Object::ExternalResource *resource) { +void v8::Object::SetExternalResource(v8::Object::ExternalResource *resource) {
+ i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate(); + i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
+ ENTER_V8(isolate); + ENTER_V8(isolate);
@ -145,8 +145,8 @@ index 8b0b32a..1a6fbbb 100644
+ +
+ +
// --- E n v i r o n m e n t --- // --- E n v i r o n m e n t ---
@@ -4144,7 +4200,7 @@ Local<String> v8::String::NewExternal( @@ -4144,7 +4200,7 @@ Local<String> v8::String::NewExternal(
LOG_API(isolate, "String::NewExternal"); LOG_API(isolate, "String::NewExternal");
ENTER_V8(isolate); ENTER_V8(isolate);
@ -155,7 +155,7 @@ index 8b0b32a..1a6fbbb 100644
+ isolate->heap()->external_resource_table()->AddString(*result); + isolate->heap()->external_resource_table()->AddString(*result);
return Utils::ToLocal(result); return Utils::ToLocal(result);
} }
@@ -4162,7 +4218,7 @@ bool v8::String::MakeExternal(v8::String::ExternalStringResource* resource) { @@ -4162,7 +4218,7 @@ bool v8::String::MakeExternal(v8::String::ExternalStringResource* resource) {
} }
bool result = obj->MakeExternal(resource); bool result = obj->MakeExternal(resource);
@ -173,7 +173,7 @@ index 8b0b32a..1a6fbbb 100644
+ isolate->heap()->external_resource_table()->AddString(*result); + isolate->heap()->external_resource_table()->AddString(*result);
return Utils::ToLocal(result); return Utils::ToLocal(result);
} }
@@ -4194,7 +4250,7 @@ bool v8::String::MakeExternal( @@ -4194,7 +4250,7 @@ bool v8::String::MakeExternal(
} }
bool result = obj->MakeExternal(resource); bool result = obj->MakeExternal(resource);
@ -211,7 +211,7 @@ index dcdc645..d530a75 100644
+++ b/src/factory.cc +++ b/src/factory.cc
@@ -997,15 +997,21 @@ Handle<JSFunction> Factory::CreateApiFunction( @@ -997,15 +997,21 @@ Handle<JSFunction> Factory::CreateApiFunction(
Handle<Code> construct_stub = isolate()->builtins()->JSConstructStubApi(); Handle<Code> construct_stub = isolate()->builtins()->JSConstructStubApi();
int internal_field_count = 0; int internal_field_count = 0;
+ bool has_external_resource = false; + bool has_external_resource = false;
+ +
@ -224,7 +224,7 @@ index dcdc645..d530a75 100644
+ has_external_resource = + has_external_resource =
+ !instance_template->has_external_resource()->IsUndefined(); + !instance_template->has_external_resource()->IsUndefined();
} }
int instance_size = kPointerSize * internal_field_count; int instance_size = kPointerSize * internal_field_count;
+ if (has_external_resource) instance_size += kPointerSize; + if (has_external_resource) instance_size += kPointerSize;
+ +
@ -232,9 +232,9 @@ index dcdc645..d530a75 100644
switch (instance_type) { switch (instance_type) {
case JavaScriptObject: case JavaScriptObject:
@@ -1040,6 +1046,11 @@ Handle<JSFunction> Factory::CreateApiFunction( @@ -1040,6 +1046,11 @@ Handle<JSFunction> Factory::CreateApiFunction(
Handle<Map> map = Handle<Map>(result->initial_map()); Handle<Map> map = Handle<Map>(result->initial_map());
+ // Mark as having external data object if needed + // Mark as having external data object if needed
+ if (has_external_resource) { + if (has_external_resource) {
+ map->set_has_external_resource(true); + map->set_has_external_resource(true);
@ -249,8 +249,8 @@ index f4fce7b..58e7adf 100644
+++ b/src/heap-inl.h +++ b/src/heap-inl.h
@@ -205,21 +205,36 @@ MaybeObject* Heap::NumberFromUint32(uint32_t value) { @@ -205,21 +205,36 @@ MaybeObject* Heap::NumberFromUint32(uint32_t value) {
} }
-void Heap::FinalizeExternalString(String* string) { -void Heap::FinalizeExternalString(String* string) {
- ASSERT(string->IsExternalString()); - ASSERT(string->IsExternalString());
- v8::String::ExternalStringResourceBase** resource_addr = - v8::String::ExternalStringResourceBase** resource_addr =
@ -277,7 +277,7 @@ index f4fce7b..58e7adf 100644
+ if (*resource_addr != NULL) { + if (*resource_addr != NULL) {
+ (*resource_addr)->Dispose(); + (*resource_addr)->Dispose();
+ } + }
- // Clear the resource pointer in the string. - // Clear the resource pointer in the string.
- *resource_addr = NULL; - *resource_addr = NULL;
+ // Clear the resource pointer in the string. + // Clear the resource pointer in the string.
@ -290,18 +290,18 @@ index f4fce7b..58e7adf 100644
+ resource = reinterpret_cast<v8::Object::ExternalResource*>(Internals::GetExternalPointerFromSmi(value)); + resource = reinterpret_cast<v8::Object::ExternalResource*>(Internals::GetExternalPointerFromSmi(value));
+ } else if (value->IsProxy()) { + } else if (value->IsProxy()) {
+ resource = reinterpret_cast<v8::Object::ExternalResource*>(Proxy::cast(value)->proxy()); + resource = reinterpret_cast<v8::Object::ExternalResource*>(Proxy::cast(value)->proxy());
+ } + }
+ if (resource) { + if (resource) {
+ resource->Dispose(); + resource->Dispose();
+ } + }
+ } + }
} }
@@ -556,53 +571,63 @@ inline bool Heap::allow_allocation(bool new_state) { @@ -556,53 +571,63 @@ inline bool Heap::allow_allocation(bool new_state) {
#endif #endif
-void ExternalStringTable::AddString(String* string) { -void ExternalStringTable::AddString(String* string) {
- ASSERT(string->IsExternalString()); - ASSERT(string->IsExternalString());
+void ExternalResourceTable::AddString(String* string) { +void ExternalResourceTable::AddString(String* string) {
@ -324,8 +324,8 @@ index f4fce7b..58e7adf 100644
+ old_space_objects_.Add(object); + old_space_objects_.Add(object);
} }
} }
-void ExternalStringTable::Iterate(ObjectVisitor* v) { -void ExternalStringTable::Iterate(ObjectVisitor* v) {
- if (!new_space_strings_.is_empty()) { - if (!new_space_strings_.is_empty()) {
- Object** start = &new_space_strings_[0]; - Object** start = &new_space_strings_[0];
@ -343,8 +343,8 @@ index f4fce7b..58e7adf 100644
+ v->VisitPointers(start, start + old_space_objects_.length()); + v->VisitPointers(start, start + old_space_objects_.length());
} }
} }
// Verify() is inline to avoid ifdef-s around its calls in release // Verify() is inline to avoid ifdef-s around its calls in release
// mode. // mode.
-void ExternalStringTable::Verify() { -void ExternalStringTable::Verify() {
@ -366,8 +366,8 @@ index f4fce7b..58e7adf 100644
} }
#endif #endif
} }
-void ExternalStringTable::AddOldString(String* string) { -void ExternalStringTable::AddOldString(String* string) {
- ASSERT(string->IsExternalString()); - ASSERT(string->IsExternalString());
- ASSERT(!heap_->InNewSpace(string)); - ASSERT(!heap_->InNewSpace(string));
@ -377,15 +377,15 @@ index f4fce7b..58e7adf 100644
+ ASSERT(!heap_->InNewSpace(object)); + ASSERT(!heap_->InNewSpace(object));
+ old_space_objects_.Add(object); + old_space_objects_.Add(object);
} }
-void ExternalStringTable::ShrinkNewStrings(int position) { -void ExternalStringTable::ShrinkNewStrings(int position) {
- new_space_strings_.Rewind(position); - new_space_strings_.Rewind(position);
+void ExternalResourceTable::ShrinkNewObjects(int position) { +void ExternalResourceTable::ShrinkNewObjects(int position) {
+ new_space_objects_.Rewind(position); + new_space_objects_.Rewind(position);
Verify(); Verify();
} }
diff --git a/src/heap.cc b/src/heap.cc diff --git a/src/heap.cc b/src/heap.cc
index 900f462..bf2940e 100644 index 900f462..bf2940e 100644
--- a/src/heap.cc --- a/src/heap.cc
@ -397,68 +397,68 @@ index 900f462..bf2940e 100644
- external_string_table_.heap_ = this; - external_string_table_.heap_ = this;
+ external_resource_table_.heap_ = this; + external_resource_table_.heap_ = this;
} }
@@ -1030,8 +1030,8 @@ void Heap::Scavenge() { @@ -1030,8 +1030,8 @@ void Heap::Scavenge() {
new_space_front = DoScavenge(&scavenge_visitor, new_space_front); new_space_front = DoScavenge(&scavenge_visitor, new_space_front);
- UpdateNewSpaceReferencesInExternalStringTable( - UpdateNewSpaceReferencesInExternalStringTable(
- &UpdateNewSpaceReferenceInExternalStringTableEntry); - &UpdateNewSpaceReferenceInExternalStringTableEntry);
+ UpdateNewSpaceReferencesInExternalResourceTable( + UpdateNewSpaceReferencesInExternalResourceTable(
+ &UpdateNewSpaceReferenceInExternalResourceTableEntry); + &UpdateNewSpaceReferenceInExternalResourceTableEntry);
LiveObjectList::UpdateReferencesForScavengeGC(); LiveObjectList::UpdateReferencesForScavengeGC();
isolate()->runtime_profiler()->UpdateSamplesAfterScavenge(); isolate()->runtime_profiler()->UpdateSamplesAfterScavenge();
@@ -1053,38 +1053,38 @@ void Heap::Scavenge() { @@ -1053,38 +1053,38 @@ void Heap::Scavenge() {
} }
-String* Heap::UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap, -String* Heap::UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap,
- Object** p) { - Object** p) {
+HeapObject* Heap::UpdateNewSpaceReferenceInExternalResourceTableEntry(Heap* heap, +HeapObject* Heap::UpdateNewSpaceReferenceInExternalResourceTableEntry(Heap* heap,
+ Object** p) { + Object** p) {
MapWord first_word = HeapObject::cast(*p)->map_word(); MapWord first_word = HeapObject::cast(*p)->map_word();
if (!first_word.IsForwardingAddress()) { if (!first_word.IsForwardingAddress()) {
// Unreachable external string can be finalized. // Unreachable external string can be finalized.
- heap->FinalizeExternalString(String::cast(*p)); - heap->FinalizeExternalString(String::cast(*p));
+ heap->FinalizeExternalString(HeapObject::cast(*p)); + heap->FinalizeExternalString(HeapObject::cast(*p));
return NULL; return NULL;
} }
// String is still reachable. // String is still reachable.
- return String::cast(first_word.ToForwardingAddress()); - return String::cast(first_word.ToForwardingAddress());
+ return HeapObject::cast(first_word.ToForwardingAddress()); + return HeapObject::cast(first_word.ToForwardingAddress());
} }
-void Heap::UpdateNewSpaceReferencesInExternalStringTable( -void Heap::UpdateNewSpaceReferencesInExternalStringTable(
- ExternalStringTableUpdaterCallback updater_func) { - ExternalStringTableUpdaterCallback updater_func) {
- external_string_table_.Verify(); - external_string_table_.Verify();
+void Heap::UpdateNewSpaceReferencesInExternalResourceTable( +void Heap::UpdateNewSpaceReferencesInExternalResourceTable(
+ ExternalResourceTableUpdaterCallback updater_func) { + ExternalResourceTableUpdaterCallback updater_func) {
+ external_resource_table_.Verify(); + external_resource_table_.Verify();
- if (external_string_table_.new_space_strings_.is_empty()) return; - if (external_string_table_.new_space_strings_.is_empty()) return;
+ if (external_resource_table_.new_space_objects_.is_empty()) return; + if (external_resource_table_.new_space_objects_.is_empty()) return;
- Object** start = &external_string_table_.new_space_strings_[0]; - Object** start = &external_string_table_.new_space_strings_[0];
- Object** end = start + external_string_table_.new_space_strings_.length(); - Object** end = start + external_string_table_.new_space_strings_.length();
+ Object** start = &external_resource_table_.new_space_objects_[0]; + Object** start = &external_resource_table_.new_space_objects_[0];
+ Object** end = start + external_resource_table_.new_space_objects_.length(); + Object** end = start + external_resource_table_.new_space_objects_.length();
Object** last = start; Object** last = start;
for (Object** p = start; p < end; ++p) { for (Object** p = start; p < end; ++p) {
ASSERT(InFromSpace(*p)); ASSERT(InFromSpace(*p));
- String* target = updater_func(this, p); - String* target = updater_func(this, p);
+ HeapObject* target = updater_func(this, p); + HeapObject* target = updater_func(this, p);
if (target == NULL) continue; if (target == NULL) continue;
- ASSERT(target->IsExternalString()); - ASSERT(target->IsExternalString());
+ ASSERT(target->IsExternalString() || target->map()->has_external_resource()); + ASSERT(target->IsExternalString() || target->map()->has_external_resource());
if (InNewSpace(target)) { if (InNewSpace(target)) {
// String is still in new space. Update the table entry. // String is still in new space. Update the table entry.
@@ -1092,12 +1092,12 @@ void Heap::UpdateNewSpaceReferencesInExternalStringTable( @@ -1092,12 +1092,12 @@ void Heap::UpdateNewSpaceReferencesInExternalStringTable(
@ -469,13 +469,13 @@ index 900f462..bf2940e 100644
+ external_resource_table_.AddOldObject(target); + external_resource_table_.AddOldObject(target);
} }
} }
ASSERT(last <= end); ASSERT(last <= end);
- external_string_table_.ShrinkNewStrings(static_cast<int>(last - start)); - external_string_table_.ShrinkNewStrings(static_cast<int>(last - start));
+ external_resource_table_.ShrinkNewObjects(static_cast<int>(last - start)); + external_resource_table_.ShrinkNewObjects(static_cast<int>(last - start));
} }
@@ -4468,7 +4468,7 @@ void Heap::IterateWeakRoots(ObjectVisitor* v, VisitMode mode) { @@ -4468,7 +4468,7 @@ void Heap::IterateWeakRoots(ObjectVisitor* v, VisitMode mode) {
v->Synchronize("symbol_table"); v->Synchronize("symbol_table");
if (mode != VISIT_ALL_IN_SCAVENGE) { if (mode != VISIT_ALL_IN_SCAVENGE) {
@ -486,18 +486,18 @@ index 900f462..bf2940e 100644
v->Synchronize("external_string_table"); v->Synchronize("external_string_table");
} }
@@ -4970,7 +4970,7 @@ void Heap::TearDown() { @@ -4970,7 +4970,7 @@ void Heap::TearDown() {
isolate_->global_handles()->TearDown(); isolate_->global_handles()->TearDown();
- external_string_table_.TearDown(); - external_string_table_.TearDown();
+ external_resource_table_.TearDown(); + external_resource_table_.TearDown();
new_space_.TearDown(); new_space_.TearDown();
@@ -5835,31 +5835,31 @@ void TranscendentalCache::Clear() { @@ -5835,31 +5835,31 @@ void TranscendentalCache::Clear() {
} }
-void ExternalStringTable::CleanUp() { -void ExternalStringTable::CleanUp() {
+void ExternalResourceTable::CleanUp() { +void ExternalResourceTable::CleanUp() {
int last = 0; int last = 0;
@ -530,8 +530,8 @@ index 900f462..bf2940e 100644
+ old_space_objects_.Rewind(last); + old_space_objects_.Rewind(last);
Verify(); Verify();
} }
-void ExternalStringTable::TearDown() { -void ExternalStringTable::TearDown() {
- new_space_strings_.Free(); - new_space_strings_.Free();
- old_space_strings_.Free(); - old_space_strings_.Free();
@ -539,33 +539,33 @@ index 900f462..bf2940e 100644
+ new_space_objects_.Free(); + new_space_objects_.Free();
+ old_space_objects_.Free(); + old_space_objects_.Free();
} }
diff --git a/src/heap.h b/src/heap.h diff --git a/src/heap.h b/src/heap.h
index ae4e9e7..8cbf378 100644 index ae4e9e7..8cbf378 100644
--- a/src/heap.h --- a/src/heap.h
+++ b/src/heap.h +++ b/src/heap.h
@@ -237,8 +237,8 @@ class Isolate; @@ -237,8 +237,8 @@ class Isolate;
class WeakObjectRetainer; class WeakObjectRetainer;
-typedef String* (*ExternalStringTableUpdaterCallback)(Heap* heap, -typedef String* (*ExternalStringTableUpdaterCallback)(Heap* heap,
- Object** pointer); - Object** pointer);
+typedef HeapObject* (*ExternalResourceTableUpdaterCallback)(Heap* heap, +typedef HeapObject* (*ExternalResourceTableUpdaterCallback)(Heap* heap,
+ Object** pointer); + Object** pointer);
typedef bool (*DirtyRegionCallback)(Heap* heap, typedef bool (*DirtyRegionCallback)(Heap* heap,
Address start, Address start,
@@ -284,43 +284,45 @@ class PromotionQueue { @@ -284,43 +284,45 @@ class PromotionQueue {
}; };
-// External strings table is a place where all external strings are -// External strings table is a place where all external strings are
-// registered. We need to keep track of such strings to properly -// registered. We need to keep track of such strings to properly
-// finalize them. -// finalize them.
-class ExternalStringTable { -class ExternalStringTable {
+// External resource table is a place where all external strings and +// External resource table is a place where all external strings and
+// objects with an external resource are registered. We need to keep +// objects with an external resource are registered. We need to keep
+// track of such strings to properly finalize them. +// track of such strings to properly finalize them.
+class ExternalResourceTable { +class ExternalResourceTable {
public: public:
@ -573,95 +573,95 @@ index ae4e9e7..8cbf378 100644
inline void AddString(String* string); inline void AddString(String* string);
+ // Registers an external object. + // Registers an external object.
+ inline void AddObject(HeapObject* object); + inline void AddObject(HeapObject* object);
inline void Iterate(ObjectVisitor* v); inline void Iterate(ObjectVisitor* v);
// Restores internal invariant and gets rid of collected strings. // Restores internal invariant and gets rid of collected strings.
- // Must be called after each Iterate() that modified the strings. - // Must be called after each Iterate() that modified the strings.
+ // Must be called after each Iterate() that modified the objects. + // Must be called after each Iterate() that modified the objects.
void CleanUp(); void CleanUp();
// Destroys all allocated memory. // Destroys all allocated memory.
void TearDown(); void TearDown();
private: private:
- ExternalStringTable() { } - ExternalStringTable() { }
+ ExternalResourceTable() { } + ExternalResourceTable() { }
friend class Heap; friend class Heap;
inline void Verify(); inline void Verify();
- inline void AddOldString(String* string); - inline void AddOldString(String* string);
+ inline void AddOldObject(HeapObject* object); + inline void AddOldObject(HeapObject* object);
// Notifies the table that only a prefix of the new list is valid. // Notifies the table that only a prefix of the new list is valid.
- inline void ShrinkNewStrings(int position); - inline void ShrinkNewStrings(int position);
+ inline void ShrinkNewObjects(int position); + inline void ShrinkNewObjects(int position);
// To speed up scavenge collections new space string are kept // To speed up scavenge collections new space string are kept
// separate from old space strings. // separate from old space strings.
- List<Object*> new_space_strings_; - List<Object*> new_space_strings_;
- List<Object*> old_space_strings_; - List<Object*> old_space_strings_;
+ List<Object*> new_space_objects_; + List<Object*> new_space_objects_;
+ List<Object*> old_space_objects_; + List<Object*> old_space_objects_;
Heap* heap_; Heap* heap_;
- DISALLOW_COPY_AND_ASSIGN(ExternalStringTable); - DISALLOW_COPY_AND_ASSIGN(ExternalStringTable);
+ DISALLOW_COPY_AND_ASSIGN(ExternalResourceTable); + DISALLOW_COPY_AND_ASSIGN(ExternalResourceTable);
}; };
@@ -753,7 +755,7 @@ class Heap { @@ -753,7 +755,7 @@ class Heap {
// Finalizes an external string by deleting the associated external // Finalizes an external string by deleting the associated external
// data and clearing the resource pointer. // data and clearing the resource pointer.
- inline void FinalizeExternalString(String* string); - inline void FinalizeExternalString(String* string);
+ inline void FinalizeExternalString(HeapObject* string); + inline void FinalizeExternalString(HeapObject* string);
// Allocates an uninitialized object. The memory is non-executable if the // Allocates an uninitialized object. The memory is non-executable if the
// hardware and OS allow. // hardware and OS allow.
@@ -1191,8 +1193,8 @@ class Heap { @@ -1191,8 +1193,8 @@ class Heap {
survived_since_last_expansion_ += survived; survived_since_last_expansion_ += survived;
} }
- void UpdateNewSpaceReferencesInExternalStringTable( - void UpdateNewSpaceReferencesInExternalStringTable(
- ExternalStringTableUpdaterCallback updater_func); - ExternalStringTableUpdaterCallback updater_func);
+ void UpdateNewSpaceReferencesInExternalResourceTable( + void UpdateNewSpaceReferencesInExternalResourceTable(
+ ExternalResourceTableUpdaterCallback updater_func); + ExternalResourceTableUpdaterCallback updater_func);
void ProcessWeakReferences(WeakObjectRetainer* retainer); void ProcessWeakReferences(WeakObjectRetainer* retainer);
@@ -1228,8 +1230,8 @@ class Heap { @@ -1228,8 +1230,8 @@ class Heap {
return &mark_compact_collector_; return &mark_compact_collector_;
} }
- ExternalStringTable* external_string_table() { - ExternalStringTable* external_string_table() {
- return &external_string_table_; - return &external_string_table_;
+ ExternalResourceTable* external_resource_table() { + ExternalResourceTable* external_resource_table() {
+ return &external_resource_table_; + return &external_resource_table_;
} }
inline Isolate* isolate(); inline Isolate* isolate();
@@ -1462,7 +1464,7 @@ class Heap { @@ -1462,7 +1464,7 @@ class Heap {
// Performs a minor collection in new generation. // Performs a minor collection in new generation.
void Scavenge(); void Scavenge();
- static String* UpdateNewSpaceReferenceInExternalStringTableEntry( - static String* UpdateNewSpaceReferenceInExternalStringTableEntry(
+ static HeapObject* UpdateNewSpaceReferenceInExternalResourceTableEntry( + static HeapObject* UpdateNewSpaceReferenceInExternalResourceTableEntry(
Heap* heap, Heap* heap,
Object** pointer); Object** pointer);
@@ -1593,7 +1595,7 @@ class Heap { @@ -1593,7 +1595,7 @@ class Heap {
// configured through the API until it is setup. // configured through the API until it is setup.
bool configured_; bool configured_;
- ExternalStringTable external_string_table_; - ExternalStringTable external_string_table_;
+ ExternalResourceTable external_resource_table_; + ExternalResourceTable external_resource_table_;
bool is_safe_to_read_maps_; bool is_safe_to_read_maps_;
diff --git a/src/liveobjectlist.cc b/src/liveobjectlist.cc diff --git a/src/liveobjectlist.cc b/src/liveobjectlist.cc
index 5795a6b..8866e58 100644 index 5795a6b..8866e58 100644
--- a/src/liveobjectlist.cc --- a/src/liveobjectlist.cc
@ -685,26 +685,26 @@ index 5795a6b..8866e58 100644
} else { } else {
delete resource; delete resource;
diff --git a/src/mark-compact.cc b/src/mark-compact.cc diff --git a/src/mark-compact.cc b/src/mark-compact.cc
index 68a5062..1b1e361 100644 index 68a5062..775f787 100644
--- a/src/mark-compact.cc --- a/src/mark-compact.cc
+++ b/src/mark-compact.cc +++ b/src/mark-compact.cc
@@ -163,7 +163,7 @@ void MarkCompactCollector::Finish() { @@ -163,7 +163,7 @@ void MarkCompactCollector::Finish() {
// objects (empty string, illegal builtin). // objects (empty string, illegal builtin).
heap()->isolate()->stub_cache()->Clear(); heap()->isolate()->stub_cache()->Clear();
- heap()->external_string_table_.CleanUp(); - heap()->external_string_table_.CleanUp();
+ heap()->external_resource_table_.CleanUp(); + heap()->external_resource_table_.CleanUp();
// If we've just compacted old space there's no reason to check the // If we've just compacted old space there's no reason to check the
// fragmentation limit. Just return. // fragmentation limit. Just return.
@@ -1019,8 +1019,9 @@ class SymbolTableCleaner : public ObjectVisitor { @@ -1019,8 +1019,9 @@ class SymbolTableCleaner : public ObjectVisitor {
// Since no objects have yet been moved we can safely access the map of // Since no objects have yet been moved we can safely access the map of
// the object. // the object.
- if ((*p)->IsExternalString()) { - if ((*p)->IsExternalString()) {
- heap_->FinalizeExternalString(String::cast(*p)); - heap_->FinalizeExternalString(String::cast(*p));
+ if ((*p)->IsExternalString() || + if ((*p)->IsExternalString() ||
+ (*p)->IsHeapObject() && HeapObject::cast(*p)->map()->has_external_resource()) { + ((*p)->IsHeapObject() && HeapObject::cast(*p)->map()->has_external_resource())) {
+ heap_->FinalizeExternalString(HeapObject::cast(*p)); + heap_->FinalizeExternalString(HeapObject::cast(*p));
} }
// Set the entry to null_value (as deleted). // Set the entry to null_value (as deleted).
@ -717,13 +717,13 @@ index 68a5062..1b1e361 100644
- heap()->external_string_table_.CleanUp(); - heap()->external_string_table_.CleanUp();
+ heap()->external_resource_table_.Iterate(&v); + heap()->external_resource_table_.Iterate(&v);
+ heap()->external_resource_table_.CleanUp(); + heap()->external_resource_table_.CleanUp();
// Process the weak references. // Process the weak references.
MarkCompactWeakObjectRetainer mark_compact_object_retainer; MarkCompactWeakObjectRetainer mark_compact_object_retainer;
@@ -1948,11 +1949,11 @@ static void UpdatePointerToNewGen(HeapObject** p) { @@ -1948,11 +1949,11 @@ static void UpdatePointerToNewGen(HeapObject** p) {
} }
-static String* UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap, -static String* UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap,
- Object** p) { - Object** p) {
+static HeapObject* UpdateNewSpaceReferenceInExternalResourceTableEntry(Heap* heap, +static HeapObject* UpdateNewSpaceReferenceInExternalResourceTableEntry(Heap* heap,
@ -733,17 +733,17 @@ index 68a5062..1b1e361 100644
- return String::cast(HeapObject::FromAddress(new_addr)); - return String::cast(HeapObject::FromAddress(new_addr));
+ return HeapObject::FromAddress(new_addr); + return HeapObject::FromAddress(new_addr);
} }
@@ -2083,8 +2084,8 @@ static void SweepNewSpace(Heap* heap, NewSpace* space) { @@ -2083,8 +2084,8 @@ static void SweepNewSpace(Heap* heap, NewSpace* space) {
updating_visitor.VisitPointer(heap->global_contexts_list_address()); updating_visitor.VisitPointer(heap->global_contexts_list_address());
// Update pointers from external string table. // Update pointers from external string table.
- heap->UpdateNewSpaceReferencesInExternalStringTable( - heap->UpdateNewSpaceReferencesInExternalStringTable(
- &UpdateNewSpaceReferenceInExternalStringTableEntry); - &UpdateNewSpaceReferenceInExternalStringTableEntry);
+ heap->UpdateNewSpaceReferencesInExternalResourceTable( + heap->UpdateNewSpaceReferencesInExternalResourceTable(
+ &UpdateNewSpaceReferenceInExternalResourceTableEntry); + &UpdateNewSpaceReferenceInExternalResourceTableEntry);
// All pointers were updated. Update auxiliary allocation info. // All pointers were updated. Update auxiliary allocation info.
heap->IncrementYoungSurvivorsCounter(survivors_size); heap->IncrementYoungSurvivorsCounter(survivors_size);
diff --git a/src/objects-inl.h b/src/objects-inl.h diff --git a/src/objects-inl.h b/src/objects-inl.h
@ -757,15 +757,15 @@ index 6aaca2f..231b835 100644
- map()->inobject_properties(); - map()->inobject_properties();
+ map()->inobject_properties() - map()->has_external_resource()?1:0; + map()->inobject_properties() - map()->has_external_resource()?1:0;
} }
int JSObject::GetInternalFieldOffset(int index) { int JSObject::GetInternalFieldOffset(int index) {
ASSERT(index < GetInternalFieldCount() && index >= 0); ASSERT(index < GetInternalFieldCount() && index >= 0);
- return GetHeaderSize() + (kPointerSize * index); - return GetHeaderSize() + (kPointerSize * index);
+ return GetHeaderSize() + (kPointerSize * (index + map()->has_external_resource()?1:0)); + return GetHeaderSize() + (kPointerSize * (index + map()->has_external_resource()?1:0));
} }
@@ -1407,7 +1407,7 @@ Object* JSObject::GetInternalField(int index) { @@ -1407,7 +1407,7 @@ Object* JSObject::GetInternalField(int index) {
// Internal objects do follow immediately after the header, whereas in-object // Internal objects do follow immediately after the header, whereas in-object
// properties are at the end of the object. Therefore there is no need // properties are at the end of the object. Therefore there is no need
@ -773,8 +773,8 @@ index 6aaca2f..231b835 100644
- return READ_FIELD(this, GetHeaderSize() + (kPointerSize * index)); - return READ_FIELD(this, GetHeaderSize() + (kPointerSize * index));
+ return READ_FIELD(this, GetHeaderSize() + (kPointerSize * (index + map()->has_external_resource()?1:0))); + return READ_FIELD(this, GetHeaderSize() + (kPointerSize * (index + map()->has_external_resource()?1:0)));
} }
@@ -1416,12 +1416,29 @@ void JSObject::SetInternalField(int index, Object* value) { @@ -1416,12 +1416,29 @@ void JSObject::SetInternalField(int index, Object* value) {
// Internal objects do follow immediately after the header, whereas in-object // Internal objects do follow immediately after the header, whereas in-object
// properties are at the end of the object. Therefore there is no need // properties are at the end of the object. Therefore there is no need
@ -784,8 +784,8 @@ index 6aaca2f..231b835 100644
WRITE_FIELD(this, offset, value); WRITE_FIELD(this, offset, value);
WRITE_BARRIER(this, offset); WRITE_BARRIER(this, offset);
} }
+void JSObject::SetExternalResourceObject(Object *value) { +void JSObject::SetExternalResourceObject(Object *value) {
+ ASSERT(map()->has_external_resource()); + ASSERT(map()->has_external_resource());
+ int offset = GetHeaderSize(); + int offset = GetHeaderSize();
@ -794,7 +794,7 @@ index 6aaca2f..231b835 100644
+} +}
+ +
+ +
+Object *JSObject::GetExternalResourceObject() { +Object *JSObject::GetExternalResourceObject() {
+ if (map()->has_external_resource()) { + if (map()->has_external_resource()) {
+ return READ_FIELD(this, GetHeaderSize()); + return READ_FIELD(this, GetHeaderSize());
+ } else { + } else {
@ -808,8 +808,8 @@ index 6aaca2f..231b835 100644
// properties stored in the properties array. // properties stored in the properties array.
@@ -2521,6 +2538,20 @@ bool Map::is_shared() { @@ -2521,6 +2538,20 @@ bool Map::is_shared() {
} }
+void Map::set_has_external_resource(bool value) { +void Map::set_has_external_resource(bool value) {
+ if (value) { + if (value) {
+ set_bit_field3(bit_field3() | (1 << kHasExternalResource)); + set_bit_field3(bit_field3() | (1 << kHasExternalResource));
@ -822,7 +822,7 @@ index 6aaca2f..231b835 100644
+{ +{
+ return ((1 << kHasExternalResource) & bit_field3()) != 0; + return ((1 << kHasExternalResource) & bit_field3()) != 0;
+} +}
+ +
+ +
void Map::set_named_interceptor_is_fallback(bool value) void Map::set_named_interceptor_is_fallback(bool value)
{ {
@ -831,9 +831,9 @@ index 6aaca2f..231b835 100644
ACCESSORS(ObjectTemplateInfo, constructor, Object, kConstructorOffset) ACCESSORS(ObjectTemplateInfo, constructor, Object, kConstructorOffset)
ACCESSORS(ObjectTemplateInfo, internal_field_count, Object, ACCESSORS(ObjectTemplateInfo, internal_field_count, Object,
kInternalFieldCountOffset) kInternalFieldCountOffset)
+ACCESSORS(ObjectTemplateInfo, has_external_resource, Object, +ACCESSORS(ObjectTemplateInfo, has_external_resource, Object,
+ kHasExternalResourceOffset) + kHasExternalResourceOffset)
ACCESSORS(SignatureInfo, receiver, Object, kReceiverOffset) ACCESSORS(SignatureInfo, receiver, Object, kReceiverOffset)
ACCESSORS(SignatureInfo, args, Object, kArgsOffset) ACCESSORS(SignatureInfo, args, Object, kArgsOffset)
diff --git a/src/objects.h b/src/objects.h diff --git a/src/objects.h b/src/objects.h
@ -843,7 +843,7 @@ index a209cd0..1bdb5c7 100644
@@ -1636,6 +1636,9 @@ class JSObject: public HeapObject { @@ -1636,6 +1636,9 @@ class JSObject: public HeapObject {
inline Object* GetInternalField(int index); inline Object* GetInternalField(int index);
inline void SetInternalField(int index, Object* value); inline void SetInternalField(int index, Object* value);
+ inline void SetExternalResourceObject(Object *); + inline void SetExternalResourceObject(Object *);
+ inline Object *GetExternalResourceObject(); + inline Object *GetExternalResourceObject();
+ +
@ -853,22 +853,22 @@ index a209cd0..1bdb5c7 100644
@@ -3715,6 +3718,12 @@ class Map: public HeapObject { @@ -3715,6 +3718,12 @@ class Map: public HeapObject {
inline void set_is_access_check_needed(bool access_check_needed); inline void set_is_access_check_needed(bool access_check_needed);
inline bool is_access_check_needed(); inline bool is_access_check_needed();
+ +
+ // Tells whether the instance has the space for an external resource + // Tells whether the instance has the space for an external resource
+ // object + // object
+ inline void set_has_external_resource(bool value); + inline void set_has_external_resource(bool value);
+ inline bool has_external_resource(); + inline bool has_external_resource();
+ +
// Whether the named interceptor is a fallback interceptor or not // Whether the named interceptor is a fallback interceptor or not
inline void set_named_interceptor_is_fallback(bool value); inline void set_named_interceptor_is_fallback(bool value);
@@ -3912,6 +3921,7 @@ class Map: public HeapObject { @@ -3912,6 +3921,7 @@ class Map: public HeapObject {
// Bit positions for bit field 3 // Bit positions for bit field 3
static const int kNamedInterceptorIsFallback = 0; static const int kNamedInterceptorIsFallback = 0;
+ static const int kHasExternalResource = 1; + static const int kHasExternalResource = 1;
// Layout of the default cache. It holds alternating name and code objects. // Layout of the default cache. It holds alternating name and code objects.
static const int kCodeCacheEntrySize = 2; static const int kCodeCacheEntrySize = 2;
@@ -6426,6 +6436,7 @@ class ObjectTemplateInfo: public TemplateInfo { @@ -6426,6 +6436,7 @@ class ObjectTemplateInfo: public TemplateInfo {
@ -876,9 +876,9 @@ index a209cd0..1bdb5c7 100644
DECL_ACCESSORS(constructor, Object) DECL_ACCESSORS(constructor, Object)
DECL_ACCESSORS(internal_field_count, Object) DECL_ACCESSORS(internal_field_count, Object)
+ DECL_ACCESSORS(has_external_resource, Object) + DECL_ACCESSORS(has_external_resource, Object)
static inline ObjectTemplateInfo* cast(Object* obj); static inline ObjectTemplateInfo* cast(Object* obj);
@@ -6442,7 +6453,8 @@ class ObjectTemplateInfo: public TemplateInfo { @@ -6442,7 +6453,8 @@ class ObjectTemplateInfo: public TemplateInfo {
static const int kConstructorOffset = TemplateInfo::kHeaderSize; static const int kConstructorOffset = TemplateInfo::kHeaderSize;
static const int kInternalFieldCountOffset = static const int kInternalFieldCountOffset =
@ -887,8 +887,8 @@ index a209cd0..1bdb5c7 100644
+ static const int kHasExternalResourceOffset = kInternalFieldCountOffset + kPointerSize; + static const int kHasExternalResourceOffset = kInternalFieldCountOffset + kPointerSize;
+ static const int kSize = kHasExternalResourceOffset + kPointerSize; + static const int kSize = kHasExternalResourceOffset + kPointerSize;
}; };
-- --
1.7.6 1.7.4.4

File diff suppressed because it is too large Load Diff

View File

@ -1,7 +1,7 @@
From f890f0d1a1e5bd62711815489c87755a4f382436 Mon Sep 17 00:00:00 2001 From 1209b88e96f253cdc19aa4c95e011c84597844f0 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Wed, 25 May 2011 10:36:13 +1000 Date: Wed, 25 May 2011 10:36:13 +1000
Subject: [PATCH 06/16] Allow access to the calling script data Subject: [PATCH 06/15] Allow access to the calling script data
--- ---
include/v8.h | 1 + include/v8.h | 1 +
@ -9,15 +9,15 @@ Subject: [PATCH 06/16] Allow access to the calling script data
2 files changed, 13 insertions(+), 0 deletions(-) 2 files changed, 13 insertions(+), 0 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index a858eae..9aba4a8 100644 index d78ab1f..2bc0ed1 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -3336,6 +3336,7 @@ class V8EXPORT Context { @@ -3337,6 +3337,7 @@ class V8EXPORT Context {
*/ */
static Local<Context> GetCalling(); static Local<Context> GetCalling();
static Local<Object> GetCallingQmlGlobal(); static Local<Object> GetCallingQmlGlobal();
+ static Local<Value> GetCallingScriptData(); + static Local<Value> GetCallingScriptData();
/** /**
* Sets the security token for the context. To access an object in * Sets the security token for the context. To access an object in
diff --git a/src/api.cc b/src/api.cc diff --git a/src/api.cc b/src/api.cc
@ -27,7 +27,7 @@ index 39767f4..ff74efb 100644
@@ -3976,6 +3976,18 @@ v8::Local<v8::Object> Context::GetCallingQmlGlobal() { @@ -3976,6 +3976,18 @@ v8::Local<v8::Object> Context::GetCallingQmlGlobal() {
} }
} }
+v8::Local<v8::Value> Context::GetCallingScriptData() +v8::Local<v8::Value> Context::GetCallingScriptData()
+{ +{
+ i::Isolate* isolate = i::Isolate::Current(); + i::Isolate* isolate = i::Isolate::Current();
@ -40,9 +40,9 @@ index 39767f4..ff74efb 100644
+ i::Handle<i::Script> script(i::Script::cast(i::JSFunction::cast(it.frame()->function())->shared()->script())); + i::Handle<i::Script> script(i::Script::cast(i::JSFunction::cast(it.frame()->function())->shared()->script()));
+ return Utils::ToLocal(i::Handle<i::Object>(script->data())); + return Utils::ToLocal(i::Handle<i::Object>(script->data()));
+} +}
v8::Local<v8::Object> Context::Global() { v8::Local<v8::Object> Context::Global() {
if (IsDeadCheck(i::Isolate::Current(), "v8::Context::Global()")) { if (IsDeadCheck(i::Isolate::Current(), "v8::Context::Global()")) {
-- --
1.7.6 1.7.4.4

View File

@ -1,17 +1,17 @@
From dac5d9db84cf20564621c679937ca7b9c6a8e880 Mon Sep 17 00:00:00 2001 From 2a5cf85d7fd7912e516138db03e4cda47cc2a1ab Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Fri, 27 May 2011 13:04:15 +1000 Date: Fri, 27 May 2011 13:04:15 +1000
Subject: [PATCH 07/16] Fix warnings Subject: [PATCH 07/15] Fix warnings
--- ---
include/v8.h | 16 ++++++++-------- include/v8.h | 16 ++++++++--------
1 files changed, 8 insertions(+), 8 deletions(-) 1 files changed, 8 insertions(+), 8 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 9aba4a8..8891dab 100644 index 2bc0ed1..99f4b9a 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -2415,7 +2415,7 @@ class V8EXPORT Extension { // NOLINT @@ -2416,7 +2416,7 @@ class V8EXPORT Extension { // NOLINT
const char** deps = 0); const char** deps = 0);
virtual ~Extension() { } virtual ~Extension() { }
virtual v8::Handle<v8::FunctionTemplate> virtual v8::Handle<v8::FunctionTemplate>
@ -19,11 +19,11 @@ index 9aba4a8..8891dab 100644
+ GetNativeFunction(v8::Handle<v8::String>) { + GetNativeFunction(v8::Handle<v8::String>) {
return v8::Handle<v8::FunctionTemplate>(); return v8::Handle<v8::FunctionTemplate>();
} }
@@ -3721,13 +3721,13 @@ class Internals { @@ -3722,13 +3722,13 @@ class Internals {
return *reinterpret_cast<T*>(addr); return *reinterpret_cast<T*>(addr);
} }
- static inline bool CanCastToHeapObject(void* o) { return false; } - static inline bool CanCastToHeapObject(void* o) { return false; }
- static inline bool CanCastToHeapObject(Context* o) { return true; } - static inline bool CanCastToHeapObject(Context* o) { return true; }
- static inline bool CanCastToHeapObject(String* o) { return true; } - static inline bool CanCastToHeapObject(String* o) { return true; }
@ -39,8 +39,8 @@ index 9aba4a8..8891dab 100644
+ static inline bool CanCastToHeapObject(StackTrace*) { return true; } + static inline bool CanCastToHeapObject(StackTrace*) { return true; }
+ static inline bool CanCastToHeapObject(StackFrame*) { return true; } + static inline bool CanCastToHeapObject(StackFrame*) { return true; }
}; };
} // namespace internal } // namespace internal
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From bec11b8b7f89d135e7d9a823ac4fe98c70d017cf Mon Sep 17 00:00:00 2001 From a7c491e6e533110a17fe9f7d47cf92a1b2263180 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Mon, 27 Jun 2011 14:57:28 +1000 Date: Mon, 27 Jun 2011 14:57:28 +1000
Subject: [PATCH 08/16] Add custom object compare callback Subject: [PATCH 08/15] Add custom object compare callback
A global custom object comparison callback can be set with: A global custom object comparison callback can be set with:
V8::SetUserObjectComparisonCallbackFunction() V8::SetUserObjectComparisonCallbackFunction()
@ -28,15 +28,15 @@ instances.
12 files changed, 218 insertions(+), 3 deletions(-) 12 files changed, 218 insertions(+), 3 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 8891dab..d5d6972 100644 index 99f4b9a..7544deb 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -2365,6 +2365,12 @@ class V8EXPORT ObjectTemplate : public Template { @@ -2366,6 +2366,12 @@ class V8EXPORT ObjectTemplate : public Template {
bool HasExternalResource(); bool HasExternalResource();
void SetHasExternalResource(bool value); void SetHasExternalResource(bool value);
+ /** + /**
+ * Mark object instances of the template as using the user object + * Mark object instances of the template as using the user object
+ * comparison callback. + * comparison callback.
+ */ + */
+ void MarkAsUseUserObjectComparison(); + void MarkAsUseUserObjectComparison();
@ -44,21 +44,21 @@ index 8891dab..d5d6972 100644
private: private:
ObjectTemplate(); ObjectTemplate();
static Local<ObjectTemplate> New(Handle<FunctionTemplate> constructor); static Local<ObjectTemplate> New(Handle<FunctionTemplate> constructor);
@@ -2565,6 +2571,10 @@ typedef void (*FailedAccessCheckCallback)(Local<Object> target, @@ -2566,6 +2572,10 @@ typedef void (*FailedAccessCheckCallback)(Local<Object> target,
AccessType type, AccessType type,
Local<Value> data); Local<Value> data);
+// --- U s e r O b j e c t C o m p a r i s o n C a l l b a c k --- +// --- U s e r O b j e c t C o m p a r i s o n C a l l b a c k ---
+typedef bool (*UserObjectComparisonCallback)(Local<Object> lhs, +typedef bool (*UserObjectComparisonCallback)(Local<Object> lhs,
+ Local<Object> rhs); + Local<Object> rhs);
+ +
// --- G a r b a g e C o l l e c t i o n C a l l b a c k s // --- G a r b a g e C o l l e c t i o n C a l l b a c k s
/** /**
@@ -2815,6 +2825,9 @@ class V8EXPORT V8 { @@ -2816,6 +2826,9 @@ class V8EXPORT V8 {
/** Callback function for reporting failed access checks.*/ /** Callback function for reporting failed access checks.*/
static void SetFailedAccessCheckCallbackFunction(FailedAccessCheckCallback); static void SetFailedAccessCheckCallbackFunction(FailedAccessCheckCallback);
+ /** Callback for user object comparisons */ + /** Callback for user object comparisons */
+ static void SetUserObjectComparisonCallbackFunction(UserObjectComparisonCallback); + static void SetUserObjectComparisonCallbackFunction(UserObjectComparisonCallback);
+ +
@ -72,7 +72,7 @@ index ff74efb..2436031 100644
@@ -1321,6 +1321,16 @@ void ObjectTemplate::SetHasExternalResource(bool value) @@ -1321,6 +1321,16 @@ void ObjectTemplate::SetHasExternalResource(bool value)
} }
} }
+void ObjectTemplate::MarkAsUseUserObjectComparison() +void ObjectTemplate::MarkAsUseUserObjectComparison()
+{ +{
+ i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate(); + i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
@ -83,13 +83,13 @@ index ff74efb..2436031 100644
+ EnsureConstructor(this); + EnsureConstructor(this);
+ Utils::OpenHandle(this)->set_use_user_object_comparison(i::Smi::FromInt(1)); + Utils::OpenHandle(this)->set_use_user_object_comparison(i::Smi::FromInt(1));
+} +}
// --- S c r i p t D a t a --- // --- S c r i p t D a t a ---
@@ -4632,6 +4642,15 @@ void V8::SetFailedAccessCheckCallbackFunction( @@ -4632,6 +4642,15 @@ void V8::SetFailedAccessCheckCallbackFunction(
isolate->SetFailedAccessCheckCallback(callback); isolate->SetFailedAccessCheckCallback(callback);
} }
+void V8::SetUserObjectComparisonCallbackFunction( +void V8::SetUserObjectComparisonCallbackFunction(
+ UserObjectComparisonCallback callback) { + UserObjectComparisonCallback callback) {
+ i::Isolate* isolate = i::Isolate::Current(); + i::Isolate* isolate = i::Isolate::Current();
@ -109,7 +109,7 @@ index a2626bf..749c9be 100644
@@ -1563,6 +1563,36 @@ void CompareStub::Generate(MacroAssembler* masm) { @@ -1563,6 +1563,36 @@ void CompareStub::Generate(MacroAssembler* masm) {
// NOTICE! This code is only reached after a smi-fast-case check, so // NOTICE! This code is only reached after a smi-fast-case check, so
// it is certain that at least one operand isn't a smi. // it is certain that at least one operand isn't a smi.
+ { + {
+ Label not_user_equal, user_equal; + Label not_user_equal, user_equal;
+ __ and_(r2, r1, Operand(r0)); + __ and_(r2, r1, Operand(r0));
@ -146,7 +146,7 @@ index a2626bf..749c9be 100644
@@ -5802,10 +5832,18 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) { @@ -5802,10 +5832,18 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) {
__ tst(r2, Operand(kSmiTagMask)); __ tst(r2, Operand(kSmiTagMask));
__ b(eq, &miss); __ b(eq, &miss);
- __ CompareObjectType(r0, r2, r2, JS_OBJECT_TYPE); - __ CompareObjectType(r0, r2, r2, JS_OBJECT_TYPE);
+ __ CompareObjectType(r0, r2, r3, JS_OBJECT_TYPE); + __ CompareObjectType(r0, r2, r3, JS_OBJECT_TYPE);
__ b(ne, &miss); __ b(ne, &miss);
@ -161,7 +161,7 @@ index a2626bf..749c9be 100644
+ __ and_(r2, r2, Operand(1 << Map::kUseUserObjectComparison)); + __ and_(r2, r2, Operand(1 << Map::kUseUserObjectComparison));
+ __ cmp(r2, Operand(1 << Map::kUseUserObjectComparison)); + __ cmp(r2, Operand(1 << Map::kUseUserObjectComparison));
+ __ b(eq, &miss); + __ b(eq, &miss);
ASSERT(GetCondition() == eq); ASSERT(GetCondition() == eq);
__ sub(r0, r0, Operand(r1)); __ sub(r0, r0, Operand(r1));
diff --git a/src/factory.cc b/src/factory.cc diff --git a/src/factory.cc b/src/factory.cc
@ -169,11 +169,11 @@ index d530a75..6f8c7de 100644
--- a/src/factory.cc --- a/src/factory.cc
+++ b/src/factory.cc +++ b/src/factory.cc
@@ -998,6 +998,7 @@ Handle<JSFunction> Factory::CreateApiFunction( @@ -998,6 +998,7 @@ Handle<JSFunction> Factory::CreateApiFunction(
int internal_field_count = 0; int internal_field_count = 0;
bool has_external_resource = false; bool has_external_resource = false;
+ bool use_user_object_comparison = false; + bool use_user_object_comparison = false;
if (!obj->instance_template()->IsUndefined()) { if (!obj->instance_template()->IsUndefined()) {
Handle<ObjectTemplateInfo> instance_template = Handle<ObjectTemplateInfo> instance_template =
@@ -1007,6 +1008,8 @@ Handle<JSFunction> Factory::CreateApiFunction( @@ -1007,6 +1008,8 @@ Handle<JSFunction> Factory::CreateApiFunction(
@ -183,12 +183,12 @@ index d530a75..6f8c7de 100644
+ use_user_object_comparison = + use_user_object_comparison =
+ !instance_template->use_user_object_comparison()->IsUndefined(); + !instance_template->use_user_object_comparison()->IsUndefined();
} }
int instance_size = kPointerSize * internal_field_count; int instance_size = kPointerSize * internal_field_count;
@@ -1051,6 +1054,11 @@ Handle<JSFunction> Factory::CreateApiFunction( @@ -1051,6 +1054,11 @@ Handle<JSFunction> Factory::CreateApiFunction(
map->set_has_external_resource(true); map->set_has_external_resource(true);
} }
+ // Mark as using user object comparison if needed + // Mark as using user object comparison if needed
+ if (use_user_object_comparison) { + if (use_user_object_comparison) {
+ map->set_use_user_object_comparison(true); + map->set_use_user_object_comparison(true);
@ -204,7 +204,7 @@ index afa599e..0964ab9 100644
@@ -3447,6 +3447,40 @@ void CompareStub::Generate(MacroAssembler* masm) { @@ -3447,6 +3447,40 @@ void CompareStub::Generate(MacroAssembler* masm) {
__ Assert(not_zero, "Unexpected smi operands."); __ Assert(not_zero, "Unexpected smi operands.");
} }
+ { + {
+ NearLabel not_user_equal, user_equal; + NearLabel not_user_equal, user_equal;
+ __ test(eax, Immediate(kSmiTagMask)); + __ test(eax, Immediate(kSmiTagMask));
@ -228,22 +228,22 @@ index afa599e..0964ab9 100644
+ __ jmp(&not_user_equal); + __ jmp(&not_user_equal);
+ +
+ __ bind(&user_equal); + __ bind(&user_equal);
+ +
+ __ pop(ebx); // Return address. + __ pop(ebx); // Return address.
+ __ push(eax); + __ push(eax);
+ __ push(edx); + __ push(edx);
+ __ push(ebx); + __ push(ebx);
+ __ TailCallRuntime(Runtime::kUserObjectEquals, 2, 1); + __ TailCallRuntime(Runtime::kUserObjectEquals, 2, 1);
+ +
+ __ bind(&not_user_equal); + __ bind(&not_user_equal);
+ } + }
+ +
+ +
// NOTICE! This code is only reached after a smi-fast-case check, so // NOTICE! This code is only reached after a smi-fast-case check, so
// it is certain that at least one operand isn't a smi. // it is certain that at least one operand isn't a smi.
@@ -5592,8 +5626,14 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) { @@ -5592,8 +5626,14 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) {
__ CmpObjectType(eax, JS_OBJECT_TYPE, ecx); __ CmpObjectType(eax, JS_OBJECT_TYPE, ecx);
__ j(not_equal, &miss, not_taken); __ j(not_equal, &miss, not_taken);
+ __ test_b(FieldOperand(ecx, Map::kBitField3Offset), + __ test_b(FieldOperand(ecx, Map::kBitField3Offset),
@ -254,7 +254,7 @@ index afa599e..0964ab9 100644
+ __ test_b(FieldOperand(ecx, Map::kBitField3Offset), + __ test_b(FieldOperand(ecx, Map::kBitField3Offset),
+ 1 << Map::kUseUserObjectComparison); + 1 << Map::kUseUserObjectComparison);
+ __ j(not_zero, &miss); + __ j(not_zero, &miss);
ASSERT(GetCondition() == equal); ASSERT(GetCondition() == equal);
__ sub(eax, Operand(edx)); __ sub(eax, Operand(edx));
diff --git a/src/isolate.h b/src/isolate.h diff --git a/src/isolate.h b/src/isolate.h
@ -264,19 +264,19 @@ index 35ffcb4..8130397 100644
@@ -267,6 +267,9 @@ class ThreadLocalTop BASE_EMBEDDED { @@ -267,6 +267,9 @@ class ThreadLocalTop BASE_EMBEDDED {
// Call back function to report unsafe JS accesses. // Call back function to report unsafe JS accesses.
v8::FailedAccessCheckCallback failed_access_check_callback_; v8::FailedAccessCheckCallback failed_access_check_callback_;
+ // Call back function for user object comparisons + // Call back function for user object comparisons
+ v8::UserObjectComparisonCallback user_object_comparison_callback_; + v8::UserObjectComparisonCallback user_object_comparison_callback_;
+ +
private: private:
void InitializeInternal(); void InitializeInternal();
@@ -699,6 +702,11 @@ class Isolate { @@ -699,6 +702,11 @@ class Isolate {
void SetFailedAccessCheckCallback(v8::FailedAccessCheckCallback callback); void SetFailedAccessCheckCallback(v8::FailedAccessCheckCallback callback);
void ReportFailedAccessCheck(JSObject* receiver, v8::AccessType type); void ReportFailedAccessCheck(JSObject* receiver, v8::AccessType type);
+ void SetUserObjectComparisonCallback(v8::UserObjectComparisonCallback callback); + void SetUserObjectComparisonCallback(v8::UserObjectComparisonCallback callback);
+ inline v8::UserObjectComparisonCallback UserObjectComparisonCallback() { + inline v8::UserObjectComparisonCallback UserObjectComparisonCallback() {
+ return thread_local_top()->user_object_comparison_callback_; + return thread_local_top()->user_object_comparison_callback_;
+ } + }
+ +
@ -289,8 +289,8 @@ index 1c7f83e..1765441 100644
+++ b/src/objects-inl.h +++ b/src/objects-inl.h
@@ -2552,6 +2552,19 @@ bool Map::has_external_resource() @@ -2552,6 +2552,19 @@ bool Map::has_external_resource()
} }
+void Map::set_use_user_object_comparison(bool value) { +void Map::set_use_user_object_comparison(bool value) {
+ if (value) { + if (value) {
+ set_bit_field3(bit_field3() | (1 << kUseUserObjectComparison)); + set_bit_field3(bit_field3() | (1 << kUseUserObjectComparison));
@ -309,11 +309,11 @@ index 1c7f83e..1765441 100644
if (value) { if (value) {
@@ -3050,6 +3063,8 @@ ACCESSORS(ObjectTemplateInfo, internal_field_count, Object, @@ -3050,6 +3063,8 @@ ACCESSORS(ObjectTemplateInfo, internal_field_count, Object,
kInternalFieldCountOffset) kInternalFieldCountOffset)
ACCESSORS(ObjectTemplateInfo, has_external_resource, Object, ACCESSORS(ObjectTemplateInfo, has_external_resource, Object,
kHasExternalResourceOffset) kHasExternalResourceOffset)
+ACCESSORS(ObjectTemplateInfo, use_user_object_comparison, Object, +ACCESSORS(ObjectTemplateInfo, use_user_object_comparison, Object,
+ kUseUserObjectComparisonOffset) + kUseUserObjectComparisonOffset)
ACCESSORS(SignatureInfo, receiver, Object, kReceiverOffset) ACCESSORS(SignatureInfo, receiver, Object, kReceiverOffset)
ACCESSORS(SignatureInfo, args, Object, kArgsOffset) ACCESSORS(SignatureInfo, args, Object, kArgsOffset)
diff --git a/src/objects.h b/src/objects.h diff --git a/src/objects.h b/src/objects.h
@ -323,13 +323,13 @@ index edbc47a..e75e9f1 100644
@@ -3724,6 +3724,11 @@ class Map: public HeapObject { @@ -3724,6 +3724,11 @@ class Map: public HeapObject {
inline void set_has_external_resource(bool value); inline void set_has_external_resource(bool value);
inline bool has_external_resource(); inline bool has_external_resource();
+ +
+ // Tells whether the user object comparison callback should be used for + // Tells whether the user object comparison callback should be used for
+ // comparisons involving this object + // comparisons involving this object
+ inline void set_use_user_object_comparison(bool value); + inline void set_use_user_object_comparison(bool value);
+ inline bool use_user_object_comparison(); + inline bool use_user_object_comparison();
// Whether the named interceptor is a fallback interceptor or not // Whether the named interceptor is a fallback interceptor or not
inline void set_named_interceptor_is_fallback(bool value); inline void set_named_interceptor_is_fallback(bool value);
@@ -3922,6 +3927,7 @@ class Map: public HeapObject { @@ -3922,6 +3927,7 @@ class Map: public HeapObject {
@ -337,7 +337,7 @@ index edbc47a..e75e9f1 100644
static const int kNamedInterceptorIsFallback = 0; static const int kNamedInterceptorIsFallback = 0;
static const int kHasExternalResource = 1; static const int kHasExternalResource = 1;
+ static const int kUseUserObjectComparison = 2; + static const int kUseUserObjectComparison = 2;
// Layout of the default cache. It holds alternating name and code objects. // Layout of the default cache. It holds alternating name and code objects.
static const int kCodeCacheEntrySize = 2; static const int kCodeCacheEntrySize = 2;
@@ -6442,6 +6448,7 @@ class ObjectTemplateInfo: public TemplateInfo { @@ -6442,6 +6448,7 @@ class ObjectTemplateInfo: public TemplateInfo {
@ -345,9 +345,9 @@ index edbc47a..e75e9f1 100644
DECL_ACCESSORS(internal_field_count, Object) DECL_ACCESSORS(internal_field_count, Object)
DECL_ACCESSORS(has_external_resource, Object) DECL_ACCESSORS(has_external_resource, Object)
+ DECL_ACCESSORS(use_user_object_comparison, Object) + DECL_ACCESSORS(use_user_object_comparison, Object)
static inline ObjectTemplateInfo* cast(Object* obj); static inline ObjectTemplateInfo* cast(Object* obj);
@@ -6459,7 +6466,8 @@ class ObjectTemplateInfo: public TemplateInfo { @@ -6459,7 +6466,8 @@ class ObjectTemplateInfo: public TemplateInfo {
static const int kInternalFieldCountOffset = static const int kInternalFieldCountOffset =
kConstructorOffset + kPointerSize; kConstructorOffset + kPointerSize;
@ -356,16 +356,16 @@ index edbc47a..e75e9f1 100644
+ static const int kUseUserObjectComparisonOffset = kHasExternalResourceOffset + kPointerSize; + static const int kUseUserObjectComparisonOffset = kHasExternalResourceOffset + kPointerSize;
+ static const int kSize = kUseUserObjectComparisonOffset + kPointerSize; + static const int kSize = kUseUserObjectComparisonOffset + kPointerSize;
}; };
diff --git a/src/runtime.cc b/src/runtime.cc diff --git a/src/runtime.cc b/src/runtime.cc
index 827d954..d552ddb 100644 index c13f92d..b50de80 100644
--- a/src/runtime.cc --- a/src/runtime.cc
+++ b/src/runtime.cc +++ b/src/runtime.cc
@@ -6279,6 +6279,29 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StringEquals) { @@ -6279,6 +6279,29 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StringEquals) {
} }
+RUNTIME_FUNCTION(MaybeObject*, Runtime_UserObjectEquals) { +RUNTIME_FUNCTION(MaybeObject*, Runtime_UserObjectEquals) {
+ NoHandleAllocation ha; + NoHandleAllocation ha;
+ ASSERT(args.length() == 2); + ASSERT(args.length() == 2);
@ -419,12 +419,12 @@ index e078ee9..c345383 100644
@@ -387,6 +388,10 @@ void Isolate::SetFailedAccessCheckCallback( @@ -387,6 +388,10 @@ void Isolate::SetFailedAccessCheckCallback(
thread_local_top()->failed_access_check_callback_ = callback; thread_local_top()->failed_access_check_callback_ = callback;
} }
+void Isolate::SetUserObjectComparisonCallback( +void Isolate::SetUserObjectComparisonCallback(
+ v8::UserObjectComparisonCallback callback) { + v8::UserObjectComparisonCallback callback) {
+ thread_local_top()->user_object_comparison_callback_ = callback; + thread_local_top()->user_object_comparison_callback_ = callback;
+} +}
void Isolate::ReportFailedAccessCheck(JSObject* receiver, v8::AccessType type) { void Isolate::ReportFailedAccessCheck(JSObject* receiver, v8::AccessType type) {
if (!thread_local_top()->failed_access_check_callback_) return; if (!thread_local_top()->failed_access_check_callback_) return;
diff --git a/src/x64/code-stubs-x64.cc b/src/x64/code-stubs-x64.cc diff --git a/src/x64/code-stubs-x64.cc b/src/x64/code-stubs-x64.cc
@ -434,7 +434,7 @@ index d923494..10b9b56 100644
@@ -2443,6 +2443,37 @@ void CompareStub::Generate(MacroAssembler* masm) { @@ -2443,6 +2443,37 @@ void CompareStub::Generate(MacroAssembler* masm) {
__ bind(&ok); __ bind(&ok);
} }
+ { + {
+ NearLabel not_user_equal, user_equal; + NearLabel not_user_equal, user_equal;
+ __ JumpIfSmi(rax, &not_user_equal); + __ JumpIfSmi(rax, &not_user_equal);
@ -456,13 +456,13 @@ index d923494..10b9b56 100644
+ __ jmp(&not_user_equal); + __ jmp(&not_user_equal);
+ +
+ __ bind(&user_equal); + __ bind(&user_equal);
+ +
+ __ pop(rbx); // Return address. + __ pop(rbx); // Return address.
+ __ push(rax); + __ push(rax);
+ __ push(rdx); + __ push(rdx);
+ __ push(rbx); + __ push(rbx);
+ __ TailCallRuntime(Runtime::kUserObjectEquals, 2, 1); + __ TailCallRuntime(Runtime::kUserObjectEquals, 2, 1);
+ +
+ __ bind(&not_user_equal); + __ bind(&not_user_equal);
+ } + }
+ +
@ -470,7 +470,7 @@ index d923494..10b9b56 100644
// value in rax, corresponding to result of comparing the two inputs. // value in rax, corresponding to result of comparing the two inputs.
// NOTICE! This code is only reached after a smi-fast-case check, so // NOTICE! This code is only reached after a smi-fast-case check, so
@@ -4471,8 +4502,14 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) { @@ -4471,8 +4502,14 @@ void ICCompareStub::GenerateObjects(MacroAssembler* masm) {
__ CmpObjectType(rax, JS_OBJECT_TYPE, rcx); __ CmpObjectType(rax, JS_OBJECT_TYPE, rcx);
__ j(not_equal, &miss, not_taken); __ j(not_equal, &miss, not_taken);
+ __ testb(FieldOperand(rcx, Map::kBitField3Offset), + __ testb(FieldOperand(rcx, Map::kBitField3Offset),
@ -481,9 +481,9 @@ index d923494..10b9b56 100644
+ __ testb(FieldOperand(rcx, Map::kBitField3Offset), + __ testb(FieldOperand(rcx, Map::kBitField3Offset),
+ Immediate(1 << Map::kUseUserObjectComparison)); + Immediate(1 << Map::kUseUserObjectComparison));
+ __ j(not_zero, &miss); + __ j(not_zero, &miss);
ASSERT(GetCondition() == equal); ASSERT(GetCondition() == equal);
__ subq(rax, rdx); __ subq(rax, rdx);
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From 4183b973ed3bd603784c798dfa63ba48f6b68003 Mon Sep 17 00:00:00 2001 From 15ce2909579aef8c8f6b0c2c07fdebbaf0f4d611 Mon Sep 17 00:00:00 2001
From: "ager@chromium.org" <ager@chromium.org> From: ager@chromium.org <ager@chromium.org>
Date: Wed, 4 May 2011 13:03:08 +0000 Date: Wed, 4 May 2011 13:03:08 +0000
Subject: [PATCH 09/16] Add CallAsFunction method to the Object class in the Subject: [PATCH 09/15] Add CallAsFunction method to the Object class in the
API API
Patch by Peter Varga. Patch by Peter Varga.
@ -21,15 +21,15 @@ git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@7781 ce2b1a6d-e
5 files changed, 163 insertions(+), 37 deletions(-) 5 files changed, 163 insertions(+), 37 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index d5d6972..8a8e1cd 100644 index 7544deb..277153e 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -1757,6 +1757,14 @@ class Object : public Value { @@ -1758,6 +1758,14 @@ class Object : public Value {
V8EXPORT ExternalArrayType GetIndexedPropertiesExternalArrayDataType(); V8EXPORT ExternalArrayType GetIndexedPropertiesExternalArrayDataType();
V8EXPORT int GetIndexedPropertiesExternalArrayDataLength(); V8EXPORT int GetIndexedPropertiesExternalArrayDataLength();
+ /** + /**
+ * Call an Object as a function if a callback is set by the + * Call an Object as a function if a callback is set by the
+ * ObjectTemplate::SetCallAsFunctionHandler method. + * ObjectTemplate::SetCallAsFunctionHandler method.
+ */ + */
+ V8EXPORT Local<Value> CallAsFunction(Handle<Object> recv, + V8EXPORT Local<Value> CallAsFunction(Handle<Object> recv,
@ -45,8 +45,8 @@ index 2436031..e412e51 100644
+++ b/src/api.cc +++ b/src/api.cc
@@ -3259,6 +3259,37 @@ int v8::Object::GetIndexedPropertiesExternalArrayDataLength() { @@ -3259,6 +3259,37 @@ int v8::Object::GetIndexedPropertiesExternalArrayDataLength() {
} }
+Local<v8::Value> Object::CallAsFunction(v8::Handle<v8::Object> recv, int argc, +Local<v8::Value> Object::CallAsFunction(v8::Handle<v8::Object> recv, int argc,
+ v8::Handle<v8::Value> argv[]) { + v8::Handle<v8::Value> argv[]) {
+ i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate(); + i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
@ -87,8 +87,8 @@ index 1632076..894d741 100644
+++ b/src/execution.cc +++ b/src/execution.cc
@@ -254,6 +254,30 @@ Handle<Object> Execution::GetFunctionDelegate(Handle<Object> object) { @@ -254,6 +254,30 @@ Handle<Object> Execution::GetFunctionDelegate(Handle<Object> object) {
} }
+Handle<Object> Execution::TryGetFunctionDelegate(Handle<Object> object, +Handle<Object> Execution::TryGetFunctionDelegate(Handle<Object> object,
+ bool* has_pending_exception) { + bool* has_pending_exception) {
+ ASSERT(!object->IsJSFunction()); + ASSERT(!object->IsJSFunction());
@ -126,7 +126,7 @@ index a476eb4..0a0be51 100644
static Handle<Object> GetFunctionDelegate(Handle<Object> object); static Handle<Object> GetFunctionDelegate(Handle<Object> object);
+ static Handle<Object> TryGetFunctionDelegate(Handle<Object> object, + static Handle<Object> TryGetFunctionDelegate(Handle<Object> object,
+ bool* has_pending_exception); + bool* has_pending_exception);
// Get a function delegate (or undefined) for the given non-function // Get a function delegate (or undefined) for the given non-function
// object. Used for support calling objects as constructors. // object. Used for support calling objects as constructors.
diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc
@ -136,7 +136,7 @@ index d7621d1..693d51e 100644
@@ -6962,50 +6962,111 @@ THREADED_TEST(CallAsFunction) { @@ -6962,50 +6962,111 @@ THREADED_TEST(CallAsFunction) {
v8::HandleScope scope; v8::HandleScope scope;
LocalContext context; LocalContext context;
- Local<v8::FunctionTemplate> t = v8::FunctionTemplate::New(); - Local<v8::FunctionTemplate> t = v8::FunctionTemplate::New();
- Local<ObjectTemplate> instance_template = t->InstanceTemplate(); - Local<ObjectTemplate> instance_template = t->InstanceTemplate();
- instance_template->SetCallAsFunctionHandler(call_as_function); - instance_template->SetCallAsFunctionHandler(call_as_function);
@ -153,21 +153,21 @@ index d7621d1..693d51e 100644
+ v8::TryCatch try_catch; + v8::TryCatch try_catch;
+ Local<Value> value; + Local<Value> value;
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
- value = CompileRun("obj(42)"); - value = CompileRun("obj(42)");
- CHECK(!try_catch.HasCaught()); - CHECK(!try_catch.HasCaught());
- CHECK_EQ(42, value->Int32Value()); - CHECK_EQ(42, value->Int32Value());
+ value = CompileRun("obj(42)"); + value = CompileRun("obj(42)");
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(42, value->Int32Value()); + CHECK_EQ(42, value->Int32Value());
- value = CompileRun("(function(o){return o(49)})(obj)"); - value = CompileRun("(function(o){return o(49)})(obj)");
- CHECK(!try_catch.HasCaught()); - CHECK(!try_catch.HasCaught());
- CHECK_EQ(49, value->Int32Value()); - CHECK_EQ(49, value->Int32Value());
+ value = CompileRun("(function(o){return o(49)})(obj)"); + value = CompileRun("(function(o){return o(49)})(obj)");
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(49, value->Int32Value()); + CHECK_EQ(49, value->Int32Value());
- // test special case of call as function - // test special case of call as function
- value = CompileRun("[obj]['0'](45)"); - value = CompileRun("[obj]['0'](45)");
- CHECK(!try_catch.HasCaught()); - CHECK(!try_catch.HasCaught());
@ -176,7 +176,7 @@ index d7621d1..693d51e 100644
+ value = CompileRun("[obj]['0'](45)"); + value = CompileRun("[obj]['0'](45)");
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(45, value->Int32Value()); + CHECK_EQ(45, value->Int32Value());
- value = CompileRun("obj.call = Function.prototype.call;" - value = CompileRun("obj.call = Function.prototype.call;"
- "obj.call(null, 87)"); - "obj.call(null, 87)");
- CHECK(!try_catch.HasCaught()); - CHECK(!try_catch.HasCaught());
@ -185,7 +185,7 @@ index d7621d1..693d51e 100644
+ "obj.call(null, 87)"); + "obj.call(null, 87)");
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(87, value->Int32Value()); + CHECK_EQ(87, value->Int32Value());
- // Regression tests for bug #1116356: Calling call through call/apply - // Regression tests for bug #1116356: Calling call through call/apply
- // must work for non-function receivers. - // must work for non-function receivers.
- const char* apply_99 = "Function.prototype.call.apply(obj, [this, 99])"; - const char* apply_99 = "Function.prototype.call.apply(obj, [this, 99])";
@ -198,7 +198,7 @@ index d7621d1..693d51e 100644
+ value = CompileRun(apply_99); + value = CompileRun(apply_99);
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(99, value->Int32Value()); + CHECK_EQ(99, value->Int32Value());
- const char* call_17 = "Function.prototype.call.call(obj, this, 17)"; - const char* call_17 = "Function.prototype.call.call(obj, this, 17)";
- value = CompileRun(call_17); - value = CompileRun(call_17);
- CHECK(!try_catch.HasCaught()); - CHECK(!try_catch.HasCaught());
@ -207,7 +207,7 @@ index d7621d1..693d51e 100644
+ value = CompileRun(call_17); + value = CompileRun(call_17);
+ CHECK(!try_catch.HasCaught()); + CHECK(!try_catch.HasCaught());
+ CHECK_EQ(17, value->Int32Value()); + CHECK_EQ(17, value->Int32Value());
- // Check that the call-as-function handler can be called through - // Check that the call-as-function handler can be called through
- // new. - // new.
- value = CompileRun("new obj(43)"); - value = CompileRun("new obj(43)");
@ -280,8 +280,8 @@ index d7621d1..693d51e 100644
+ try_catch.Reset(); + try_catch.Reset();
+ } + }
} }
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From 3d6d4249878f7960eac4c9c94e0f2529f9a58c4a Mon Sep 17 00:00:00 2001 From 3ba270e3b93d292dc53a675a21479bdb0b50bbbe Mon Sep 17 00:00:00 2001
From: "ager@chromium.org" <ager@chromium.org> From: ager@chromium.org <ager@chromium.org>
Date: Fri, 6 May 2011 11:07:52 +0000 Date: Fri, 6 May 2011 11:07:52 +0000
Subject: [PATCH 10/16] Implement CallAsConstructor method for Object in the Subject: [PATCH 10/15] Implement CallAsConstructor method for Object in the
API API
Patch by Peter Varga. Patch by Peter Varga.
@ -21,10 +21,10 @@ git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@7803 ce2b1a6d-e
5 files changed, 276 insertions(+), 8 deletions(-) 5 files changed, 276 insertions(+), 8 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 8a8e1cd..84462b5 100644 index 277153e..18527e1 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -1765,6 +1765,14 @@ class Object : public Value { @@ -1766,6 +1766,14 @@ class Object : public Value {
int argc, int argc,
Handle<Value> argv[]); Handle<Value> argv[]);
@ -96,16 +96,16 @@ index e412e51..1a585d6 100644
+ } + }
+ return Local<v8::Object>(); + return Local<v8::Object>();
} }
diff --git a/src/execution.cc b/src/execution.cc diff --git a/src/execution.cc b/src/execution.cc
index 894d741..afb352c 100644 index 894d741..afb352c 100644
--- a/src/execution.cc --- a/src/execution.cc
+++ b/src/execution.cc +++ b/src/execution.cc
@@ -297,6 +297,34 @@ Handle<Object> Execution::GetConstructorDelegate(Handle<Object> object) { @@ -297,6 +297,34 @@ Handle<Object> Execution::GetConstructorDelegate(Handle<Object> object) {
} }
+Handle<Object> Execution::TryGetConstructorDelegate( +Handle<Object> Execution::TryGetConstructorDelegate(
+ Handle<Object> object, + Handle<Object> object,
+ bool* has_pending_exception) { + bool* has_pending_exception) {
@ -148,8 +148,8 @@ index 0a0be51..ec2a195 100644
+ static Handle<Object> TryGetConstructorDelegate(Handle<Object> object, + static Handle<Object> TryGetConstructorDelegate(Handle<Object> object,
+ bool* has_pending_exception); + bool* has_pending_exception);
}; };
diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc
index 693d51e..1334f63 100644 index 693d51e..1334f63 100644
--- a/test/cctest/test-api.cc --- a/test/cctest/test-api.cc
@ -157,7 +157,7 @@ index 693d51e..1334f63 100644
@@ -6746,6 +6746,200 @@ THREADED_TEST(Constructor) { @@ -6746,6 +6746,200 @@ THREADED_TEST(Constructor) {
CHECK(value->BooleanValue()); CHECK(value->BooleanValue());
} }
+ +
+static Handle<Value> ConstructorCallback(const Arguments& args) { +static Handle<Value> ConstructorCallback(const Arguments& args) {
+ ApiTestFuzzer::Fuzz(); + ApiTestFuzzer::Fuzz();
@ -365,7 +365,7 @@ index 693d51e..1334f63 100644
+ CHECK_EQ("TypeError: Property 'obj2' of object #<Object> is not a function", + CHECK_EQ("TypeError: Property 'obj2' of object #<Object> is not a function",
+ *exception_value1); + *exception_value1);
try_catch.Reset(); try_catch.Reset();
// Call an object without call-as-function handler through the API // Call an object without call-as-function handler through the API
@@ -7040,7 +7233,7 @@ THREADED_TEST(CallAsFunction) { @@ -7040,7 +7233,7 @@ THREADED_TEST(CallAsFunction) {
CHECK(value.IsEmpty()); CHECK(value.IsEmpty());
@ -375,7 +375,7 @@ index 693d51e..1334f63 100644
+ CHECK_EQ("TypeError: [object Object] is not a function", *exception_value2); + CHECK_EQ("TypeError: [object Object] is not a function", *exception_value2);
try_catch.Reset(); try_catch.Reset();
} }
@@ -7057,14 +7250,14 @@ THREADED_TEST(CallAsFunction) { @@ -7057,14 +7250,14 @@ THREADED_TEST(CallAsFunction) {
value = CompileRun("obj3(22)"); value = CompileRun("obj3(22)");
CHECK(try_catch.HasCaught()); CHECK(try_catch.HasCaught());
@ -383,7 +383,7 @@ index 693d51e..1334f63 100644
- CHECK_EQ(*exception_value1, "22"); - CHECK_EQ(*exception_value1, "22");
+ CHECK_EQ("22", *exception_value1); + CHECK_EQ("22", *exception_value1);
try_catch.Reset(); try_catch.Reset();
v8::Handle<Value> args[] = { v8_num(23) }; v8::Handle<Value> args[] = { v8_num(23) };
value = instance->CallAsFunction(instance, 1, args); value = instance->CallAsFunction(instance, 1, args);
CHECK(try_catch.HasCaught()); CHECK(try_catch.HasCaught());
@ -393,6 +393,6 @@ index 693d51e..1334f63 100644
try_catch.Reset(); try_catch.Reset();
} }
} }
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From f22d0312faeb93ced8747d9aae8c6d77e11b4aba Mon Sep 17 00:00:00 2001 From 5f3e5dd6901b54707ea4f868d8fa7317c4ab3852 Mon Sep 17 00:00:00 2001
From: Jedrzej Nowacki <jedrzej.nowacki@nokia.com> From: Jedrzej Nowacki <jedrzej.nowacki@nokia.com>
Date: Tue, 7 Dec 2010 11:56:42 +0100 Date: Tue, 7 Dec 2010 11:56:42 +0100
Subject: [PATCH 11/16] QtScript/V8: Add new v8 api to check if a value is an Subject: [PATCH 11/15] QtScript/V8: Add new v8 api to check if a value is an
error. error.
New function v8::Value::IsError was created. New function v8::Value::IsError was created.
@ -15,13 +15,13 @@ research.
3 files changed, 12 insertions(+), 0 deletions(-) 3 files changed, 12 insertions(+), 0 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 84462b5..08b0ec2 100644 index 18527e1..43e00f5 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -937,6 +937,11 @@ class Value : public Data { @@ -937,6 +937,11 @@ class Value : public Data {
*/ */
V8EXPORT bool IsRegExp() const; V8EXPORT bool IsRegExp() const;
+ /** + /**
+ * Returns true if this value is an Error. + * Returns true if this value is an Error.
+ */ + */
@ -37,14 +37,14 @@ index 1a585d6..bd435eb 100644
@@ -2108,6 +2108,12 @@ bool Value::IsRegExp() const { @@ -2108,6 +2108,12 @@ bool Value::IsRegExp() const {
return obj->IsJSRegExp(); return obj->IsJSRegExp();
} }
+bool Value::IsError() const { +bool Value::IsError() const {
+ if (IsDeadCheck(i::Isolate::Current(), "v8::Value::IsError()")) return false; + if (IsDeadCheck(i::Isolate::Current(), "v8::Value::IsError()")) return false;
+ i::Handle<i::Object> obj = Utils::OpenHandle(this); + i::Handle<i::Object> obj = Utils::OpenHandle(this);
+ return obj->HasSpecificClassOf(HEAP->Error_symbol()); + return obj->HasSpecificClassOf(HEAP->Error_symbol());
+} +}
+ +
Local<String> Value::ToString() const { Local<String> Value::ToString() const {
i::Handle<i::Object> obj = Utils::OpenHandle(this); i::Handle<i::Object> obj = Utils::OpenHandle(this);
diff --git a/src/heap.h b/src/heap.h diff --git a/src/heap.h b/src/heap.h
@ -59,6 +59,6 @@ index 8cbf378..db90bb9 100644
V(this_symbol, "this") \ V(this_symbol, "this") \
V(to_string_symbol, "toString") \ V(to_string_symbol, "toString") \
V(char_at_symbol, "CharAt") \ V(char_at_symbol, "CharAt") \
-- --
1.7.6 1.7.4.4

View File

@ -1,8 +1,7 @@
From 472c04c9e7a64e8734c76d2cf97a7cc5b773b788 Mon Sep 17 00:00:00 2001 From a338d96fe138fbffd4b45c7d13a54e068daa6e12 Mon Sep 17 00:00:00 2001
From: "ager@chromium.org" From: ager@chromium.org <ager@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
<ager@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Date: Mon, 9 May 2011 15:24:48 +0000 Date: Mon, 9 May 2011 15:24:48 +0000
Subject: [PATCH 12/16] Add IsCallable method for Object in the API Subject: [PATCH 12/15] Add IsCallable method for Object in the API
Patch by Peter Varga. Patch by Peter Varga.
@ -19,12 +18,12 @@ git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@7828 ce2b1a6d-e
3 files changed, 61 insertions(+), 0 deletions(-) 3 files changed, 61 insertions(+), 0 deletions(-)
diff --git a/include/v8.h b/include/v8.h diff --git a/include/v8.h b/include/v8.h
index 08b0ec2..4194d4a 100644 index 43e00f5..5e1ce50 100644
--- a/include/v8.h --- a/include/v8.h
+++ b/include/v8.h +++ b/include/v8.h
@@ -1763,6 +1763,13 @@ class Object : public Value { @@ -1764,6 +1764,13 @@ class Object : public Value {
V8EXPORT int GetIndexedPropertiesExternalArrayDataLength(); V8EXPORT int GetIndexedPropertiesExternalArrayDataLength();
/** /**
+ * Checks whether a callback is set by the + * Checks whether a callback is set by the
+ * ObjectTemplate::SetCallAsFunctionHandler method. + * ObjectTemplate::SetCallAsFunctionHandler method.
@ -33,7 +32,7 @@ index 08b0ec2..4194d4a 100644
+ V8EXPORT bool IsCallable(); + V8EXPORT bool IsCallable();
+ +
+ /** + /**
* Call an Object as a function if a callback is set by the * Call an Object as a function if a callback is set by the
* ObjectTemplate::SetCallAsFunctionHandler method. * ObjectTemplate::SetCallAsFunctionHandler method.
*/ */
diff --git a/src/api.cc b/src/api.cc diff --git a/src/api.cc b/src/api.cc
@ -42,8 +41,8 @@ index bd435eb..a5a637f 100644
+++ b/src/api.cc +++ b/src/api.cc
@@ -3265,6 +3265,17 @@ int v8::Object::GetIndexedPropertiesExternalArrayDataLength() { @@ -3265,6 +3265,17 @@ int v8::Object::GetIndexedPropertiesExternalArrayDataLength() {
} }
+bool v8::Object::IsCallable() { +bool v8::Object::IsCallable() {
+ i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate(); + i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
+ ON_BAILOUT(isolate, "v8::Object::IsCallable()", return false); + ON_BAILOUT(isolate, "v8::Object::IsCallable()", return false);
@ -64,8 +63,8 @@ index 1334f63..45db5a1 100644
+++ b/test/cctest/test-api.cc +++ b/test/cctest/test-api.cc
@@ -7263,6 +7263,49 @@ THREADED_TEST(CallAsFunction) { @@ -7263,6 +7263,49 @@ THREADED_TEST(CallAsFunction) {
} }
+// Check whether a non-function object is callable. +// Check whether a non-function object is callable.
+THREADED_TEST(CallableObject) { +THREADED_TEST(CallableObject) {
+ v8::HandleScope scope; + v8::HandleScope scope;
@ -112,6 +111,6 @@ index 1334f63..45db5a1 100644
static int CountHandles() { static int CountHandles() {
return v8::HandleScope::NumberOfHandles(); return v8::HandleScope::NumberOfHandles();
} }
-- --
1.7.6 1.7.4.4

View File

@ -1,7 +1,7 @@
From dc2cad4f8fc88c52fcea09b8d0262d35cd32dc44 Mon Sep 17 00:00:00 2001 From c36be227e9d7952a1952caa529c78ecdc376bd55 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com> From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Thu, 25 Aug 2011 11:09:58 +1000 Date: Thu, 25 Aug 2011 11:09:58 +1000
Subject: [PATCH 13/16] Remove execute flag from v8-debug.h Subject: [PATCH 13/15] Remove execute flag from v8-debug.h
--- ---
0 files changed, 0 insertions(+), 0 deletions(-) 0 files changed, 0 insertions(+), 0 deletions(-)
@ -10,6 +10,6 @@ Subject: [PATCH 13/16] Remove execute flag from v8-debug.h
diff --git a/include/v8-debug.h b/include/v8-debug.h diff --git a/include/v8-debug.h b/include/v8-debug.h
old mode 100755 old mode 100755
new mode 100644 new mode 100644
-- --
1.7.6 1.7.4.4

View File

@ -1,25 +0,0 @@
From d7e876decc00c611d327185bf890a7efecb2cf7e Mon Sep 17 00:00:00 2001
From: Kent Hansen <kent.hansen@nokia.com>
Date: Mon, 29 Aug 2011 13:26:13 +0200
Subject: [PATCH 14/16] Fix build error: "suggest parentheses around '&&'
within '||'"
---
src/mark-compact.cc | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/src/mark-compact.cc b/src/mark-compact.cc
index 1b1e361..775f787 100644
--- a/src/mark-compact.cc
+++ b/src/mark-compact.cc
@@ -1020,7 +1020,7 @@ class SymbolTableCleaner : public ObjectVisitor {
// Since no objects have yet been moved we can safely access the map of
// the object.
if ((*p)->IsExternalString() ||
- (*p)->IsHeapObject() && HeapObject::cast(*p)->map()->has_external_resource()) {
+ ((*p)->IsHeapObject() && HeapObject::cast(*p)->map()->has_external_resource())) {
heap_->FinalizeExternalString(HeapObject::cast(*p));
}
// Set the entry to null_value (as deleted).
--
1.7.6

View File

@ -1,7 +1,7 @@
From 97cb46d421faebd2b139570bcf9aaf2d5eadc333 Mon Sep 17 00:00:00 2001 From ed5cc903d70f73780e5985e7d2de33f6b8d86402 Mon Sep 17 00:00:00 2001
From: Kent Hansen <kent.hansen@nokia.com> From: Kent Hansen <kent.hansen@nokia.com>
Date: Fri, 2 Sep 2011 12:03:09 +0200 Date: Fri, 2 Sep 2011 12:03:09 +0200
Subject: [PATCH 16/16] Fix deprecated Python code Subject: [PATCH 14/15] Fix deprecated Python code
Needed to make the scripts run on Python 3, which is the Needed to make the scripts run on Python 3, which is the
default python interpreter on some newer distros. default python interpreter on some newer distros.
@ -46,5 +46,6 @@ index 646bf14..395441b 100644
new_identifier = self.CharFromNumber(identifier_first_char) new_identifier = self.CharFromNumber(identifier_first_char)
if identifier_second_char != 0: if identifier_second_char != 0:
new_identifier = ( new_identifier = (
-- --
1.7.6 1.7.4.4

View File

@ -0,0 +1,46 @@
From 523f03f03b1ac16d272a13389f8a5654d9ff12e6 Mon Sep 17 00:00:00 2001
From: Aaron Kennedy <aaron.kennedy@nokia.com>
Date: Fri, 9 Sep 2011 14:16:12 +1000
Subject: [PATCH 15/15] Allow a script to be flagged as "native"
Native scripts do not appear in backtraces, or in the source and
line number when exceptions are thrown from within them. This is
useful to be able to write code in JavaScript instead of C++ and
still have it appear sensibly to the user.
---
include/v8.h | 5 +++--
src/compiler.cc | 2 +-
2 files changed, 4 insertions(+), 3 deletions(-)
diff --git a/include/v8.h b/include/v8.h
index 5e1ce50..a2d61d1 100644
--- a/include/v8.h
+++ b/include/v8.h
@@ -578,8 +578,9 @@ class ScriptOrigin {
class V8EXPORT Script {
public:
enum CompileFlags {
- Default = 0x00,
- QmlMode = 0x01
+ Default = 0x00,
+ QmlMode = 0x01,
+ NativeMode = 0x02
};
/**
diff --git a/src/compiler.cc b/src/compiler.cc
index d2191b9..873018c 100755
--- a/src/compiler.cc
+++ b/src/compiler.cc
@@ -507,7 +507,7 @@ Handle<SharedFunctionInfo> Compiler::Compile(Handle<String> source,
// Create a script object describing the script to be compiled.
Handle<Script> script = FACTORY->NewScript(source);
- if (natives == NATIVES_CODE) {
+ if (natives == NATIVES_CODE || compile_flags & v8::Script::NativeMode) {
script->set_type(Smi::FromInt(Script::TYPE_NATIVE));
}
if (!script_name.is_null()) {
--
1.7.4.4

View File

@ -1,25 +0,0 @@
From 0af1e15a3d6b28923c262a02a5ace35812c8f5d6 Mon Sep 17 00:00:00 2001
From: Simon Hausmann <simon.hausmann@nokia.com>
Date: Thu, 4 Aug 2011 21:28:38 +0200
Subject: [PATCH 15/16] Fix source compatibility where the String::Equals
overloads would shadow the Value::Equals function,
breaking the build.
---
include/v8.h | 1 +
1 files changed, 1 insertions(+), 0 deletions(-)
diff --git a/include/v8.h b/include/v8.h
index 4194d4a..5e1ce50 100644
--- a/include/v8.h
+++ b/include/v8.h
@@ -1048,6 +1048,7 @@ class String : public Primitive {
*/
V8EXPORT bool Equals(uint16_t *string, int length);
V8EXPORT bool Equals(char *string, int length);
+ inline bool Equals(Handle<Value> that) const { return v8::Value::Equals(that); }
/**
* Write the contents of the string to an external buffer.
--
1.7.6

View File

@ -213,7 +213,7 @@ void tst_QGlobal::qtry()
// check propper if/else scoping // check propper if/else scoping
i = 0; i = 0;
if (true) if (true) {
QT_TRY { QT_TRY {
i = 2; i = 2;
QT_THROW(42); QT_THROW(42);
@ -222,12 +222,13 @@ void tst_QGlobal::qtry()
QCOMPARE(i, 2); QCOMPARE(i, 2);
i = 4; i = 4;
} }
else } else {
QCOMPARE(i, 0); QCOMPARE(i, 0);
}
QCOMPARE(i, 4); QCOMPARE(i, 4);
i = 0; i = 0;
if (false) if (false) {
QT_TRY { QT_TRY {
i = 2; i = 2;
QT_THROW(42); QT_THROW(42);
@ -236,14 +237,15 @@ void tst_QGlobal::qtry()
QCOMPARE(i, 2); QCOMPARE(i, 2);
i = 2; i = 2;
} }
else } else {
i = 8; i = 8;
}
QCOMPARE(i, 8); QCOMPARE(i, 8);
i = 0; i = 0;
if (false) if (false) {
i = 42; i = 42;
else } else {
QT_TRY { QT_TRY {
i = 2; i = 2;
QT_THROW(42); QT_THROW(42);
@ -252,6 +254,7 @@ void tst_QGlobal::qtry()
QCOMPARE(i, 2); QCOMPARE(i, 2);
i = 4; i = 4;
} }
}
QCOMPARE(i, 4); QCOMPARE(i, 4);
} }

View File

@ -18,3 +18,6 @@ SUBDIRS=\
qdbusthreading \ qdbusthreading \
qdbusxmlparser \ qdbusxmlparser \
!contains(QT_CONFIG,private_tests): SUBDIRS -= \
qdbusmarshall \

View File

@ -146,9 +146,12 @@ win32:SUBDIRS -= qtextpiecetable
qgraphicssceneindex \ qgraphicssceneindex \
qlistwidget \ qlistwidget \
qmainwindow \ qmainwindow \
qnetworkreply \ qpathclipper \
qpixmapcache \
qsidebar \ qsidebar \
qstylesheetstyle \ qstylesheetstyle \
qtextlayout \
qtextpiecetable \
qtipc \ qtipc \
qtoolbar \ qtoolbar \

View File

@ -6,4 +6,4 @@ TEMPLATE=subdirs
SUBDIRS=\ SUBDIRS=\
network \ network \
networkselftest \ networkselftest \
qobjectperformance \ qobjectperformance

View File

@ -118,7 +118,7 @@ void tst_QNetworkProxyFactory::systemProxyForQuery() const
QNetworkProxy proxy; QNetworkProxy proxy;
QList<QNetworkProxy> nativeProxyList; QList<QNetworkProxy> nativeProxyList;
nativeProxyList << QNetworkProxy(QNetworkProxy::HttpProxy, QString("http://test.proxy.com"), 8080) << QNetworkProxy::NoProxy; nativeProxyList << QNetworkProxy(QNetworkProxy::HttpProxy, QString("test.proxy.com"), 8080) << QNetworkProxy::NoProxy;
foreach (proxy, systemProxyList) { foreach (proxy, systemProxyList) {
if (!nativeProxyList.contains(proxy)) { if (!nativeProxyList.contains(proxy)) {

View File

@ -1649,7 +1649,7 @@ void tst_QStyleSheetStyle::QTBUG11658_cachecrash()
void tst_QStyleSheetStyle::QTBUG15910_crashNullWidget() void tst_QStyleSheetStyle::QTBUG15910_crashNullWidget()
{ {
struct : QWidget { struct Widget : QWidget {
virtual void paintEvent(QPaintEvent* ) { virtual void paintEvent(QPaintEvent* ) {
QStyleOption opt; QStyleOption opt;
opt.init(this); opt.init(this);

View File

@ -55,6 +55,7 @@ private slots:
void cleanupTestCase() {} void cleanupTestCase() {}
void eval(); void eval();
void evalwithinwith();
void userobjectcompare(); void userobjectcompare();
}; };
@ -63,6 +64,11 @@ void tst_v8::eval()
QVERIFY(v8test_eval()); QVERIFY(v8test_eval());
} }
void tst_v8::evalwithinwith()
{
QVERIFY(v8test_evalwithinwith());
}
void tst_v8::userobjectcompare() void tst_v8::userobjectcompare()
{ {
QVERIFY(v8test_userobjectcompare()); QVERIFY(v8test_userobjectcompare());

View File

@ -1,3 +1,44 @@
/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the test suite of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** GNU Lesser General Public License Usage
** This file may be used under the terms of the GNU Lesser General Public
** License version 2.1 as published by the Free Software Foundation and
** appearing in the file LICENSE.LGPL included in the packaging of this
** file. Please review the following information to ensure the GNU Lesser
** General Public License version 2.1 requirements will be met:
** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU General
** Public License version 3.0 as published by the Free Software Foundation
** and appearing in the file LICENSE.GPL included in the packaging of this
** file. Please review the following information to ensure the GNU General
** Public License version 3.0 requirements will be met:
** http://www.gnu.org/copyleft/gpl.html.
**
** Other Usage
** Alternatively, this file may be used in accordance with the terms and
** conditions contained in a signed written agreement between you and Nokia.
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "v8test.h" #include "v8test.h"
#include <stdio.h> #include <stdio.h>
@ -11,6 +52,7 @@ int main(int argc, char *argv[])
v8::V8::SetFlagsFromCommandLine(&argc, argv, true); v8::V8::SetFlagsFromCommandLine(&argc, argv, true);
RUN_TEST(eval); RUN_TEST(eval);
RUN_TEST(evalwithinwith);
RUN_TEST(userobjectcompare); RUN_TEST(userobjectcompare);
return -1; return -1;

View File

@ -81,6 +81,49 @@ cleanup:
ENDTEST(); ENDTEST();
} }
bool v8test_evalwithinwith()
{
BEGINTEST();
HandleScope handle_scope;
Persistent<Context> context = Context::New();
Context::Scope context_scope(context);
Local<Object> qmlglobal = Object::New();
qmlglobal->Set(String::New("a"), Integer::New(1922));
// There was a bug that the "eval" lookup would incorrectly resolve
// to the QML global object
qmlglobal->Set(String::New("eval"), Integer::New(1922));
#define SOURCE \
"(function() { " \
" var b = { c: 10 }; " \
" with (b) { " \
" return eval(\"a\"); " \
" } " \
"})"
Local<Script> script = Script::Compile(String::New(SOURCE), NULL, NULL,
Handle<String>(), Script::QmlMode);
#undef SOURCE
TryCatch tc;
Local<Value> result = script->Run(qmlglobal);
VERIFY(!tc.HasCaught());
VERIFY(result->IsFunction());
{
Local<Value> fresult = Handle<Function>::Cast(result)->Call(context->Global(), 0, 0);
VERIFY(!tc.HasCaught());
VERIFY(fresult->Int32Value() == 1922);
}
cleanup:
context.Dispose();
ENDTEST();
}
static int userObjectComparisonCalled = 0; static int userObjectComparisonCalled = 0;
static bool userObjectComparisonReturn = false; static bool userObjectComparisonReturn = false;
static Local<Object> expectedLhs; static Local<Object> expectedLhs;

View File

@ -49,6 +49,7 @@
#endif #endif
bool v8test_eval(); bool v8test_eval();
bool v8test_evalwithinwith();
bool v8test_userobjectcompare(); bool v8test_userobjectcompare();
#endif // V8TEST_H #endif // V8TEST_H

View File

@ -2727,6 +2727,9 @@ void Configure::generateOutputVars()
// We currently have no switch for QtSvg, so add it unconditionally. // We currently have no switch for QtSvg, so add it unconditionally.
qtConfig += "svg"; qtConfig += "svg";
if (dictionary[ "V8" ] == "yes")
qtConfig += "v8";
// Add config levels -------------------------------------------- // Add config levels --------------------------------------------
QStringList possible_configs = QStringList() QStringList possible_configs = QStringList()
<< "minimal" << "minimal"