|
13 | 13 | #include "node_api_util.h"
|
14 | 14 |
|
15 | 15 | #import <Foundation/Foundation.h>
|
| 16 | +#import <CoreFoundation/CoreFoundation.h> |
16 | 17 | #include <objc/runtime.h>
|
17 | 18 | #include <stdbool.h>
|
18 | 19 | #include <memory>
|
@@ -531,6 +532,40 @@ void toNative(napi_env env, napi_value value, void* result, bool* shouldFree,
|
531 | 532 | return;
|
532 | 533 | }
|
533 | 534 |
|
| 535 | + case napi_string: { |
| 536 | + size_t len = 0; |
| 537 | + NAPI_GUARD(napi_get_value_string_utf8(env, value, nullptr, len, &len)) { |
| 538 | + NAPI_THROW_LAST_ERROR |
| 539 | + return; |
| 540 | + } |
| 541 | + |
| 542 | + char* str = (char*)malloc(len + 1); |
| 543 | + |
| 544 | + NAPI_GUARD(napi_get_value_string_utf8(env, value, str, len + 1, &len)) { |
| 545 | + NAPI_THROW_LAST_ERROR |
| 546 | + ::free(str); |
| 547 | + return; |
| 548 | + } |
| 549 | + |
| 550 | + str[len] = '\0'; |
| 551 | + |
| 552 | + // Check if we need to create a CFStringRef instead of a C string |
| 553 | + // if (pointeeType && pointeeType->kind == mdTypeNSStringObject) { |
| 554 | + // Create CFStringRef for CF/NS string pointers |
| 555 | + CFStringRef cfStr = CFStringCreateWithCString(kCFAllocatorDefault, str, kCFStringEncodingUTF8); |
| 556 | + ::free(str); // Free the temporary C string |
| 557 | + *res = (void*)cfStr; |
| 558 | + *shouldFree = false; // CFStringRef is reference counted, don't use free() |
| 559 | + *shouldFreeAny = false; |
| 560 | + // } else { |
| 561 | + // // Default behavior: return C string |
| 562 | + // *res = (void*)str; |
| 563 | + // *shouldFree = true; |
| 564 | + // *shouldFreeAny = true; |
| 565 | + // } |
| 566 | + return; |
| 567 | + } |
| 568 | + |
534 | 569 | case napi_external: {
|
535 | 570 | NAPI_GUARD(napi_get_value_external(env, value, res)) {
|
536 | 571 | NAPI_THROW_LAST_ERROR
|
@@ -590,12 +625,26 @@ void toNative(napi_env env, napi_value value, void* result, bool* shouldFree,
|
590 | 625 | }
|
591 | 626 |
|
592 | 627 | default:
|
| 628 | + NSLog(@"value %d", type); |
593 | 629 | napi_throw_error(env, nullptr, "Invalid pointer type");
|
594 | 630 | *res = nullptr;
|
595 | 631 | return;
|
596 | 632 | }
|
597 | 633 | }
|
598 | 634 |
|
| 635 | + void free(napi_env env, void* value) override { |
| 636 | + if (pointeeType && pointeeType->kind == mdTypeNSStringObject) { |
| 637 | + // CFStringRef needs CFRelease, not free() |
| 638 | + CFStringRef cfStr = (CFStringRef)value; |
| 639 | + if (cfStr != nullptr) { |
| 640 | + CFRelease(cfStr); |
| 641 | + } |
| 642 | + } else { |
| 643 | + // Default behavior for C strings |
| 644 | + ::free(value); |
| 645 | + } |
| 646 | + } |
| 647 | + |
599 | 648 | void encode(std::string* encoding) override { *encoding += "^v"; }
|
600 | 649 | };
|
601 | 650 |
|
@@ -941,6 +990,20 @@ void toNative(napi_env env, napi_value value, void* result, bool* shouldFree,
|
941 | 990 | status = napi_unwrap(env, value, (void**)res);
|
942 | 991 |
|
943 | 992 | if (status != napi_ok) {
|
| 993 | + // Check if this is a Pointer instance and use its underlying data |
| 994 | + if (Pointer::isInstance(env, value)) { |
| 995 | + Pointer* ptr = Pointer::unwrap(env, value); |
| 996 | + *res = (id)ptr->data; |
| 997 | + return; |
| 998 | + } |
| 999 | + |
| 1000 | + // Check if this is a Reference instance and use its underlying data |
| 1001 | + if (Reference::isInstance(env, value)) { |
| 1002 | + Reference* ref = Reference::unwrap(env, value); |
| 1003 | + *res = (id)ref->data; |
| 1004 | + return; |
| 1005 | + } |
| 1006 | + |
944 | 1007 | bool isArray = false;
|
945 | 1008 | napi_is_array(env, value, &isArray);
|
946 | 1009 | if (isArray) {
|
|
0 commit comments