Commit d579f5b7 authored by darin's avatar darin

- add self-check to property map in hopes of finding the cnet.com bug

        * kjs/property_map.h: Add check() function.
        * kjs/property_map.cpp: Add the checking, controlled by DO_CONSISTENCY_CHECK.

	 - fixed UChar interface so it's not so slow in debug builds

        * kjs/ustring.h: Nothing in UChar needs to be private.

        * kjs/function.cpp: (GlobalFuncImp::call):
        * kjs/function_object.cpp: (FunctionObjectImp::construct):
        * kjs/identifier.cpp:
        * kjs/lexer.cpp: (Lexer::setCode), (Lexer::shift):
        * kjs/lookup.cpp: (keysMatch):
        * kjs/ustring.cpp: (UString::Rep::computeHash), (KJS::compare):
	Use the "uc" field instead of the "unicode()" inline function.


git-svn-id: http://svn.webkit.org/repository/webkit/trunk@2800 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent 8488c964
2002-11-21 Darin Adler <darin@apple.com>
- add self-check to property map in hopes of finding the cnet.com bug
* kjs/property_map.h: Add check() function.
* kjs/property_map.cpp: Add the checking, controlled by DO_CONSISTENCY_CHECK.
- fixed UChar interface so it's not so slow in debug builds
* kjs/ustring.h: Nothing in UChar needs to be private.
* kjs/function.cpp: (GlobalFuncImp::call):
* kjs/function_object.cpp: (FunctionObjectImp::construct):
* kjs/identifier.cpp:
* kjs/lexer.cpp: (Lexer::setCode), (Lexer::shift):
* kjs/lookup.cpp: (keysMatch):
* kjs/ustring.cpp: (UString::Rep::computeHash), (KJS::compare):
Use the "uc" field instead of the "unicode()" inline function.
2002-11-21 Darin Adler <darin@apple.com>
- fixed a null-dereference I ran into while trying to reproduce bug 3107351
......
2002-11-21 Darin Adler <darin@apple.com>
- add self-check to property map in hopes of finding the cnet.com bug
* kjs/property_map.h: Add check() function.
* kjs/property_map.cpp: Add the checking, controlled by DO_CONSISTENCY_CHECK.
- fixed UChar interface so it's not so slow in debug builds
* kjs/ustring.h: Nothing in UChar needs to be private.
* kjs/function.cpp: (GlobalFuncImp::call):
* kjs/function_object.cpp: (FunctionObjectImp::construct):
* kjs/identifier.cpp:
* kjs/lexer.cpp: (Lexer::setCode), (Lexer::shift):
* kjs/lookup.cpp: (keysMatch):
* kjs/ustring.cpp: (UString::Rep::computeHash), (KJS::compare):
Use the "uc" field instead of the "unicode()" inline function.
2002-11-21 Darin Adler <darin@apple.com>
- fixed a null-dereference I ran into while trying to reproduce bug 3107351
......
2002-11-21 Darin Adler <darin@apple.com>
- add self-check to property map in hopes of finding the cnet.com bug
* kjs/property_map.h: Add check() function.
* kjs/property_map.cpp: Add the checking, controlled by DO_CONSISTENCY_CHECK.
- fixed UChar interface so it's not so slow in debug builds
* kjs/ustring.h: Nothing in UChar needs to be private.
* kjs/function.cpp: (GlobalFuncImp::call):
* kjs/function_object.cpp: (FunctionObjectImp::construct):
* kjs/identifier.cpp:
* kjs/lexer.cpp: (Lexer::setCode), (Lexer::shift):
* kjs/lookup.cpp: (keysMatch):
* kjs/ustring.cpp: (UString::Rep::computeHash), (KJS::compare):
Use the "uc" field instead of the "unicode()" inline function.
2002-11-21 Darin Adler <darin@apple.com>
- fixed a null-dereference I ran into while trying to reproduce bug 3107351
......
......@@ -505,7 +505,7 @@ Value GlobalFuncImp::call(ExecState *exec, Object &/*thisObj*/, const List &args
UString r = "", s, str = args[0].toString(exec);
const UChar *c = str.data();
for (int k = 0; k < str.size(); k++, c++) {
int u = c->unicode();
int u = c->uc;
if (u > 255) {
char tmp[7];
sprintf(tmp, "%%u%04X", u);
......@@ -529,12 +529,12 @@ Value GlobalFuncImp::call(ExecState *exec, Object &/*thisObj*/, const List &args
while (k < len) {
const UChar *c = str.data() + k;
if (*c == UChar('%') && k <= len - 6 && *(c+1) == UChar('u')) {
u = Lexer::convertUnicode((c+2)->unicode(), (c+3)->unicode(),
(c+4)->unicode(), (c+5)->unicode());
u = Lexer::convertUnicode((c+2)->uc, (c+3)->uc,
(c+4)->uc, (c+5)->uc);
c = &u;
k += 5;
} else if (*c == UChar('%') && k <= len - 3) {
u = UChar(Lexer::convertHex((c+1)->unicode(), (c+2)->unicode()));
u = UChar(Lexer::convertHex((c+1)->uc, (c+2)->uc));
c = &u;
k += 2;
}
......
......@@ -249,11 +249,11 @@ Object FunctionObjectImp::construct(ExecState *exec, const List &args)
while (i < len) {
while (*c == ' ' && i < len)
c++, i++;
if (Lexer::isIdentLetter(c->unicode())) { // else error
if (Lexer::isIdentLetter(c->uc)) { // else error
param = UString(c, 1);
c++, i++;
while (i < len && (Lexer::isIdentLetter(c->unicode()) ||
Lexer::isDecimalDigit(c->unicode()))) {
while (i < len && (Lexer::isIdentLetter(c->uc) ||
Lexer::isDecimalDigit(c->uc))) {
param += UString(c, 1);
c++, i++;
}
......
......@@ -49,7 +49,7 @@ bool Identifier::equal(UString::Rep *r, const char *s)
int length = r->len;
const UChar *d = r->dat;
for (int i = 0; i != length; ++i)
if (d[i].unicode() != (unsigned char)s[i])
if (d[i].uc != (unsigned char)s[i])
return false;
return s[length] == 0;
}
......@@ -60,7 +60,7 @@ bool Identifier::equal(UString::Rep *r, const UChar *s, int length)
return false;
const UChar *d = r->dat;
for (int i = 0; i != length; ++i)
if (d[i].unicode() != s[i].unicode())
if (d[i].uc != s[i].uc)
return false;
return true;
}
......@@ -73,7 +73,7 @@ bool Identifier::equal(UString::Rep *r, UString::Rep *b)
const UChar *d = r->dat;
const UChar *s = b->dat;
for (int i = 0; i != length; ++i)
if (d[i].unicode() != s[i].unicode())
if (d[i].uc != s[i].uc)
return false;
return true;
}
......
......@@ -117,10 +117,10 @@ void Lexer::setCode(const UChar *c, unsigned int len)
#endif
// read first characters
current = (length > 0) ? code[0].unicode() : 0;
next1 = (length > 1) ? code[1].unicode() : 0;
next2 = (length > 2) ? code[2].unicode() : 0;
next3 = (length > 3) ? code[3].unicode() : 0;
current = (length > 0) ? code[0].uc : 0;
next1 = (length > 1) ? code[1].uc : 0;
next2 = (length > 2) ? code[2].uc : 0;
next3 = (length > 3) ? code[3].uc : 0;
}
void Lexer::shift(unsigned int p)
......@@ -130,7 +130,7 @@ void Lexer::shift(unsigned int p)
current = next1;
next1 = next2;
next2 = next3;
next3 = (pos + 3 < length) ? code[pos+3].unicode() : 0;
next3 = (pos + 3 < length) ? code[pos+3].uc : 0;
}
}
......
......@@ -33,7 +33,7 @@ using namespace KJS;
static bool keysMatch(const UChar *c, unsigned len, const char *s)
{
for (unsigned i = 0; i != len; i++, c++, s++)
if (c->unicode() != (unsigned char)*s)
if (c->uc != (unsigned char)*s)
return false;
return *s == 0;
}
......
......@@ -25,9 +25,15 @@
#include "object.h"
#include "reference_list.h"
#define DO_CONSISTENCY_CHECK 0
// At the time I added this switch, the optimization still gave a 1.5% performance boost so I couldn't remove it.
#define USE_SINGLE_ENTRY 1
#if !DO_CONSISTENCY_CHECK
#define check() ((void)0)
#endif
namespace KJS {
class SavedProperty {
......@@ -131,6 +137,8 @@ ValueImp *PropertyMap::get(const Identifier &name) const
void PropertyMap::put(const Identifier &name, ValueImp *value, int attributes)
{
check();
UString::Rep *rep = name._ustring.rep;
#if USE_SINGLE_ENTRY
......@@ -138,7 +146,7 @@ void PropertyMap::put(const Identifier &name, ValueImp *value, int attributes)
UString::Rep *key = _singleEntry.key;
if (key) {
if (rep == key) {
_singleEntry.value = value;
_singleEntry.value = value;
return;
}
} else {
......@@ -147,6 +155,7 @@ void PropertyMap::put(const Identifier &name, ValueImp *value, int attributes)
_singleEntry.value = value;
_singleEntry.attributes = attributes;
_keyCount = 1;
check();
return;
}
}
......@@ -172,6 +181,8 @@ void PropertyMap::put(const Identifier &name, ValueImp *value, int attributes)
_table[i].value = value;
_table[i].attributes = attributes;
++_keyCount;
check();
}
inline void PropertyMap::insert(UString::Rep *key, ValueImp *value, int attributes)
......@@ -187,6 +198,8 @@ inline void PropertyMap::insert(UString::Rep *key, ValueImp *value, int attribut
void PropertyMap::expand()
{
check();
int oldTableSize = _tableSize;
Entry *oldTable = _table;
......@@ -209,10 +222,14 @@ void PropertyMap::expand()
}
free(oldTable);
check();
}
void PropertyMap::remove(const Identifier &name)
{
check();
UString::Rep *rep = name._ustring.rep;
UString::Rep *key;
......@@ -224,6 +241,7 @@ void PropertyMap::remove(const Identifier &name)
key->deref();
_singleEntry.key = 0;
_keyCount = 0;
check();
}
#endif
return;
......@@ -253,6 +271,8 @@ void PropertyMap::remove(const Identifier &name)
_table[i].key = 0;
insert(key, _table[i].value, _table[i].attributes);
}
check();
}
void PropertyMap::mark() const
......@@ -328,4 +348,36 @@ void PropertyMap::restore(const SavedProperties &p)
put(p._properties[i].key, p._properties[i].value.imp(), 0);
}
#if DO_CONSISTENCY_CHECK
void PropertyMap::check()
{
int count = 0;
for (int j = 0; j != _tableSize; ++j) {
UString::Rep *rep = _table[j].key;
if (!rep)
continue;
int i = hash(rep);
while (UString::Rep *key = _table[i].key) {
if (rep == key)
break;
i = (i + 1) & _tableSizeMask;
}
assert(i == j);
count++;
}
#if USE_SINGLE_ENTRY
if (_singleEntry.key)
count++;
#endif
assert(count == _keyCount);
if (_table) {
assert(_tableSize);
assert(_tableSizeMask);
assert(_tableSize == _tableSizeMask + 1);
}
}
#endif // DO_CONSISTENCY_CHECK
} // namespace KJS
......@@ -80,6 +80,8 @@ namespace KJS {
void insert(UString::Rep *, ValueImp *value, int attributes);
void check();
typedef PropertyMapHashTableEntry Entry;
int _tableSizeMask;
......
......@@ -182,9 +182,9 @@ unsigned UString::Rep::computeHash(const UChar *s, int length)
unsigned h = length;
for (int i = 0; i < prefixLength; i++)
h = 127 * h + s[i].unicode();
h = 127 * h + s[i].uc;
for (int i = suffixPosition; i < length; i++)
h = 127 * h + s[i].unicode();
h = 127 * h + s[i].uc;
if (h == 0)
h = 0x80000000;
return h;
......@@ -720,7 +720,7 @@ int KJS::compare(const UString& s1, const UString& s2)
l++;
}
if (l < lmin)
return (c1->unicode() > c2->unicode()) ? 1 : -1;
return (c1->uc > c2->uc) ? 1 : -1;
if (l1 == l2) {
return 0;
......
......@@ -98,12 +98,6 @@ namespace KJS {
* A static instance of UChar(0).
*/
static UChar null;
private:
friend class UCharReference;
friend class UString;
friend bool operator==(const UChar &c1, const UChar &c2);
friend bool operator==(const UString& s1, const char *s2);
friend bool operator<(const UString& s1, const UString& s2);
unsigned short uc;
};
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment