Compare commits

...

1 Commits

Author SHA1 Message Date
Jarred Sumner
6c5fcf2617 Experiment: call ZigString__freeGlobal when calling deref on an external string 2025-05-02 22:42:07 -07:00
2 changed files with 46 additions and 36 deletions

View File

@@ -79,6 +79,8 @@ typedef struct BunString {
// This one usually will clone the raw bytes.
WTF::String toWTFString() const;
WTF::String toWTFString();
} BunString;
typedef struct ZigErrorType {
@@ -456,6 +458,46 @@ class ScriptArguments;
using ScriptArguments = Inspector::ScriptArguments;
namespace Zig {
// 8 bit byte
// we tag the final two bits
// so 56 bits are copied over
// rest we zero out for consistentcy
static const unsigned char* untag(const unsigned char* ptr)
{
return reinterpret_cast<const unsigned char*>(
(((reinterpret_cast<uintptr_t>(ptr) & ~(static_cast<uint64_t>(1) << 63) & ~(static_cast<uint64_t>(1) << 62)) & ~(static_cast<uint64_t>(1) << 61)) & ~(static_cast<uint64_t>(1) << 60)));
}
static void* untagVoid(const unsigned char* ptr)
{
return const_cast<void*>(reinterpret_cast<const void*>(untag(ptr)));
}
static void* untagVoid(const char16_t* ptr)
{
return untagVoid(reinterpret_cast<const unsigned char*>(ptr));
}
static bool isTaggedUTF16Ptr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 63)) != 0;
}
// Do we need to convert the string from UTF-8 to UTF-16?
static bool isTaggedUTF8Ptr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 61)) != 0;
}
static bool isTaggedExternalPtr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 62)) != 0;
}
}
ALWAYS_INLINE void BunString::ref()
{
if (this->tag == BunStringTag::WTFStringImpl) {
@@ -466,8 +508,12 @@ ALWAYS_INLINE void BunString::deref()
{
if (this->tag == BunStringTag::WTFStringImpl) {
this->impl.wtf->deref();
} else if (UNLIKELY(this->tag == BunStringTag::ZigString && this->impl.zig.len > 0 && Zig::isTaggedExternalPtr(this->impl.zig.ptr))) {
ZigString__freeGlobal(Zig::untag(this->impl.zig.ptr), this->impl.zig.len);
this->tag = BunStringTag::Dead;
}
}
#endif // __cplusplus
#endif // HEADERS_HANDWRITTEN

View File

@@ -26,42 +26,6 @@ extern "C" const char* Bun__errnoName(int);
namespace Zig {
// 8 bit byte
// we tag the final two bits
// so 56 bits are copied over
// rest we zero out for consistentcy
static const unsigned char* untag(const unsigned char* ptr)
{
return reinterpret_cast<const unsigned char*>(
(((reinterpret_cast<uintptr_t>(ptr) & ~(static_cast<uint64_t>(1) << 63) & ~(static_cast<uint64_t>(1) << 62)) & ~(static_cast<uint64_t>(1) << 61)) & ~(static_cast<uint64_t>(1) << 60)));
}
static void* untagVoid(const unsigned char* ptr)
{
return const_cast<void*>(reinterpret_cast<const void*>(untag(ptr)));
}
static void* untagVoid(const char16_t* ptr)
{
return untagVoid(reinterpret_cast<const unsigned char*>(ptr));
}
static bool isTaggedUTF16Ptr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 63)) != 0;
}
// Do we need to convert the string from UTF-8 to UTF-16?
static bool isTaggedUTF8Ptr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 61)) != 0;
}
static bool isTaggedExternalPtr(const unsigned char* ptr)
{
return (reinterpret_cast<uintptr_t>(ptr) & (static_cast<uint64_t>(1) << 62)) != 0;
}
static void free_global_string(void* str, void* ptr, unsigned len)
{
// i don't understand why this happens