summaryrefslogtreecommitdiffstats
path: root/src/script/api
diff options
context:
space:
mode:
authorKent Hansen <kent.hansen@nokia.com>2010-02-22 16:59:59 (GMT)
committerKent Hansen <kent.hansen@nokia.com>2010-02-22 17:55:21 (GMT)
commitbab4c3056c11ba3607acce3314ecfe172d00cf96 (patch)
tree74cb0f1a0b0959f6b310aabe5946427283fe36c0 /src/script/api
parent7a328e4f69f10f4fea6d48746ff214030794328d (diff)
downloadQt-bab4c3056c11ba3607acce3314ecfe172d00cf96.zip
Qt-bab4c3056c11ba3607acce3314ecfe172d00cf96.tar.gz
Qt-bab4c3056c11ba3607acce3314ecfe172d00cf96.tar.bz2
Fix memory leak when lazily binding QScriptValue to an engine
Avoid the engine's list of free script values from growing without bounds. When a QScriptValue is initially not bound, its private will be allocated from the normal heap (and not from the engine's pool of privates, because there is no engine at this point). But when a value is later bound (e.g. by setting it as a property of an object, or by passing it as argument to QScriptValue::call()) and is subsequently destroyed, its private will be handed to the engine, which will add it to its free-list (hence the memory is not freed). This allocation/deallocation asymmetry causes this list go keep growing. The solution is to limit the size of the free-list, and free the memory of the private immediately when the list has reached a certain size. Task-number: QTBUG-8400 Reviewed-by: Olivier Goffart
Diffstat (limited to 'src/script/api')
-rw-r--r--src/script/api/qscriptengine.cpp2
-rw-r--r--src/script/api/qscriptengine_p.h12
2 files changed, 11 insertions, 3 deletions
diff --git a/src/script/api/qscriptengine.cpp b/src/script/api/qscriptengine.cpp
index 1bd7377..1199263 100644
--- a/src/script/api/qscriptengine.cpp
+++ b/src/script/api/qscriptengine.cpp
@@ -768,7 +768,7 @@ static QScriptValue __setupPackage__(QScriptContext *ctx, QScriptEngine *eng)
} // namespace QScript
QScriptEnginePrivate::QScriptEnginePrivate()
- : registeredScriptValues(0), freeScriptValues(0),
+ : registeredScriptValues(0), freeScriptValues(0), freeScriptValuesCount(0),
registeredScriptStrings(0), inEval(false)
{
qMetaTypeId<QScriptValue>();
diff --git a/src/script/api/qscriptengine_p.h b/src/script/api/qscriptengine_p.h
index 6780b2c..401d6d2 100644
--- a/src/script/api/qscriptengine_p.h
+++ b/src/script/api/qscriptengine_p.h
@@ -255,6 +255,8 @@ public:
int agentLineNumber;
QScriptValuePrivate *registeredScriptValues;
QScriptValuePrivate *freeScriptValues;
+ static const int maxFreeScriptValues = 256;
+ int freeScriptValuesCount;
QScriptStringPrivate *registeredScriptStrings;
QHash<int, QScriptTypeInfo*> m_typeInfos;
int processEventsInterval;
@@ -377,6 +379,7 @@ inline QScriptValuePrivate *QScriptEnginePrivate::allocateScriptValuePrivate(siz
if (freeScriptValues) {
QScriptValuePrivate *p = freeScriptValues;
freeScriptValues = p->next;
+ --freeScriptValuesCount;
return p;
}
return reinterpret_cast<QScriptValuePrivate*>(qMalloc(size));
@@ -384,8 +387,13 @@ inline QScriptValuePrivate *QScriptEnginePrivate::allocateScriptValuePrivate(siz
inline void QScriptEnginePrivate::freeScriptValuePrivate(QScriptValuePrivate *p)
{
- p->next = freeScriptValues;
- freeScriptValues = p;
+ if (freeScriptValuesCount < maxFreeScriptValues) {
+ p->next = freeScriptValues;
+ freeScriptValues = p;
+ ++freeScriptValuesCount;
+ } else {
+ qFree(p);
+ }
}
inline void QScriptEnginePrivate::registerScriptValue(QScriptValuePrivate *value)