mini_racer 0.17.0.pre4 → 0.17.0.pre5

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 877bcc1b7a601bcd6ef672cc17caeb7e21df723a440b1d07a2a4931e2a4d118a
4
- data.tar.gz: e8ea952ea537c94d1c05998d521555d78349755ab1172925b24a4135d6691d99
3
+ metadata.gz: bd92c74de497ca8b317cb32e02345d204081c50ef44c11a61b0cfef3e32e2cff
4
+ data.tar.gz: b2074ffd330b91006c28e0d6b9a4b346a9a0e6d9de30cffd83bb426189262c4d
5
5
  SHA512:
6
- metadata.gz: d1f45fb9e917632eff3131c9399710fad8f7ef47228e02f72a139122efd13565055b2851dc9348e6852cf009e1c5c93f0adf970544983f7713457f482a976a8d
7
- data.tar.gz: 8ede15ef0dbe8a2b16ad9567d584ef57fcd2e0a2e801931476d7b4107d3c05154f70a5d1d96d7960919b939a4ea496d6d101a994b625d9a8000b79c7ee49bcc9
6
+ metadata.gz: 36dd26be30d9e22f5c227f8864a03e6f55224b9265799d604bf933b7458ead17960fef48de19a8d33f6c3c1578f83740c9c8c704541beb7964f6de23f4ec1fb9
7
+ data.tar.gz: 89067b89d2dbd6cf7b2af79991f30e53c6df8cc7d08e35623f730eb7010c287ccb98a29444375a7593f4494e11ad25b2c74a3d0b73ce104f7fc64edf22fb9e7e
data/CHANGELOG CHANGED
@@ -1,3 +1,10 @@
1
+ - 0.17.0.pre5 - 30-09-2024
2
+
3
+ - Handle segfault from JSON.stringify
4
+ - Fix segfaults around symbol conversion
5
+ - Fix crash on invalid date object
6
+
7
+
1
8
  - 0.17.0.pre4 - 18-09-2024
2
9
 
3
10
  - Attempt to change compilation flags to disable strict aliasing to see if it resolves stability issues
@@ -429,14 +429,17 @@ static void prepare_result(MaybeLocal<Value> v8res,
429
429
  Local<Object> object = local_value->ToObject(context).ToLocalChecked();
430
430
  const unsigned argc = 1;
431
431
  Local<Value> argv[argc] = { object };
432
- MaybeLocal<Value> json = stringify->Call(context, JSON, argc, argv);
432
+ MaybeLocal<Value> maybe_json = stringify->Call(context, JSON, argc, argv);
433
+ Local<Value> json;
433
434
 
434
- if (json.IsEmpty()) {
435
+ if (!maybe_json.ToLocal(&json)) {
435
436
  evalRes.executed = false;
436
437
  } else {
437
- evalRes.json = true;
438
+ // JSON.stringify() returns undefined for inputs that
439
+ // are exotic objects, like WASM function or string refs
440
+ evalRes.json = !json->IsUndefined();
438
441
  Persistent<Value>* persistent = new Persistent<Value>();
439
- persistent->Reset(isolate, json.ToLocalChecked());
442
+ persistent->Reset(isolate, json);
440
443
  evalRes.value = persistent;
441
444
  }
442
445
  }
@@ -565,6 +568,7 @@ static VALUE convert_v8_to_ruby(Isolate* isolate, Local<Context> context,
565
568
 
566
569
  Isolate::Scope isolate_scope(isolate);
567
570
  HandleScope scope(isolate);
571
+ Context::Scope context_scope(context);
568
572
 
569
573
  StackCounter stackCounter(isolate);
570
574
 
@@ -586,10 +590,6 @@ static VALUE convert_v8_to_ruby(Isolate* isolate, Local<Context> context,
586
590
  return INT2FIX(value->Int32Value(context).ToChecked());
587
591
  }
588
592
 
589
- if (value->IsNumber()) {
590
- return rb_float_new(value->NumberValue(context).ToChecked());
591
- }
592
-
593
593
  if (value->IsTrue()) {
594
594
  return Qtrue;
595
595
  }
@@ -598,81 +598,108 @@ static VALUE convert_v8_to_ruby(Isolate* isolate, Local<Context> context,
598
598
  return Qfalse;
599
599
  }
600
600
 
601
- if (value->IsArray()) {
602
- VALUE rb_array = rb_ary_new();
603
- Local<Array> arr = Local<Array>::Cast(value);
604
- for(uint32_t i=0; i < arr->Length(); i++) {
605
- MaybeLocal<Value> element = arr->Get(context, i);
606
- if (element.IsEmpty()) {
607
- continue;
608
- }
609
- VALUE rb_elem = convert_v8_to_ruby(isolate, context, element.ToLocalChecked());
610
- if (rb_funcall(rb_elem, rb_intern("class"), 0) == rb_cFailedV8Conversion) {
611
- return rb_elem;
612
- }
613
- rb_ary_push(rb_array, rb_elem);
614
- }
615
- return rb_array;
616
- }
617
-
618
- if (value->IsFunction()){
619
- return rb_funcall(rb_cJavaScriptFunction, rb_intern("new"), 0);
620
- }
621
-
622
- if (value->IsDate()){
623
- double ts = Local<Date>::Cast(value)->ValueOf();
624
- double secs = ts/1000;
625
- long nanos = round((secs - floor(secs)) * 1000000);
626
-
627
- return rb_time_new(secs, nanos);
628
- }
629
-
630
- if (value->IsObject()) {
631
- VALUE rb_hash = rb_hash_new();
632
- TryCatch trycatch(isolate);
633
-
634
- Local<Object> object = value->ToObject(context).ToLocalChecked();
635
- auto maybe_props = object->GetOwnPropertyNames(context);
636
- if (!maybe_props.IsEmpty()) {
637
- Local<Array> props = maybe_props.ToLocalChecked();
638
- for(uint32_t i=0; i < props->Length(); i++) {
639
- MaybeLocal<Value> key = props->Get(context, i);
640
- if (key.IsEmpty()) {
641
- return rb_funcall(rb_cFailedV8Conversion, rb_intern("new"), 1, rb_str_new2(""));
642
- }
643
- VALUE rb_key = convert_v8_to_ruby(isolate, context, key.ToLocalChecked());
644
-
645
- MaybeLocal<Value> prop_value = object->Get(context, key.ToLocalChecked());
646
- // this may have failed due to Get raising
647
- if (prop_value.IsEmpty() || trycatch.HasCaught()) {
648
- return new_empty_failed_conv_obj();
649
- }
650
-
651
- VALUE rb_value = convert_v8_to_ruby(
652
- isolate, context, prop_value.ToLocalChecked());
653
- rb_hash_aset(rb_hash, rb_key, rb_value);
601
+ struct State {
602
+ Isolate* isolate;
603
+ Local<Value> value;
604
+ Local<Context> context;
605
+ } state = {isolate, value, context};
606
+
607
+ // calls to rb_*() functions can raise exceptions and longjmp,
608
+ // and therefore must be inside this protected block
609
+ auto can_raise = [](VALUE arg) -> VALUE {
610
+ State* state =
611
+ reinterpret_cast<State*>(static_cast<uintptr_t>(RB_NUM2ULL(arg)));
612
+ Isolate* isolate = state->isolate;
613
+ Local<Value> value = state->value;
614
+ Local<Context> context = state->context;
615
+
616
+ if (value->IsNumber()) {
617
+ return rb_float_new(value->NumberValue(context).ToChecked());
618
+ }
619
+
620
+ if (value->IsArray()) {
621
+ VALUE rb_array = rb_ary_new();
622
+ Local<Array> arr = Local<Array>::Cast(value);
623
+ for(uint32_t i = 0; i < arr->Length(); i++) {
624
+ MaybeLocal<Value> element = arr->Get(context, i);
625
+ if (element.IsEmpty()) {
626
+ continue;
627
+ }
628
+ VALUE rb_elem = convert_v8_to_ruby(isolate, context, element.ToLocalChecked());
629
+ if (rb_funcall(rb_elem, rb_intern("class"), 0) == rb_cFailedV8Conversion) {
630
+ return rb_elem;
631
+ }
632
+ rb_ary_push(rb_array, rb_elem);
654
633
  }
634
+ return rb_array;
655
635
  }
656
- return rb_hash;
657
- }
658
636
 
659
- if (value->IsSymbol()) {
660
- v8::String::Utf8Value symbol_name(isolate,
661
- Local<Symbol>::Cast(value)->Description(isolate));
637
+ if (value->IsFunction()){
638
+ return rb_funcall(rb_cJavaScriptFunction, rb_intern("new"), 0);
639
+ }
662
640
 
663
- VALUE str_symbol = rb_utf8_str_new(*symbol_name, symbol_name.length());
641
+ if (value->IsDate()){
642
+ double ts = Local<Date>::Cast(value)->ValueOf();
643
+ double secs = ts/1000;
644
+ long nanos = round((secs - floor(secs)) * 1000000);
664
645
 
665
- return rb_str_intern(str_symbol);
666
- }
646
+ return rb_time_new(secs, nanos);
647
+ }
667
648
 
668
- MaybeLocal<String> rstr_maybe = value->ToString(context);
649
+ if (value->IsObject()) {
650
+ VALUE rb_hash = rb_hash_new();
651
+ TryCatch trycatch(isolate);
652
+
653
+ Local<Object> object = value->ToObject(context).ToLocalChecked();
654
+ auto maybe_props = object->GetOwnPropertyNames(context);
655
+ if (!maybe_props.IsEmpty()) {
656
+ Local<Array> props = maybe_props.ToLocalChecked();
657
+ for (uint32_t i = 0; i < props->Length(); i++) {
658
+ MaybeLocal<Value> key = props->Get(context, i);
659
+ if (key.IsEmpty()) {
660
+ return rb_funcall(rb_cFailedV8Conversion, rb_intern("new"), 1, rb_str_new2(""));
661
+ }
662
+ VALUE rb_key = convert_v8_to_ruby(isolate, context, key.ToLocalChecked());
669
663
 
670
- if (rstr_maybe.IsEmpty()) {
671
- return Qnil;
672
- } else {
673
- Local<String> rstr = rstr_maybe.ToLocalChecked();
674
- return rb_utf8_str_new(*String::Utf8Value(isolate, rstr), rstr->Utf8Length(isolate));
675
- }
664
+ MaybeLocal<Value> prop_value = object->Get(context, key.ToLocalChecked());
665
+ // this may have failed due to Get raising
666
+ if (prop_value.IsEmpty() || trycatch.HasCaught()) {
667
+ return new_empty_failed_conv_obj();
668
+ }
669
+
670
+ VALUE rb_value = convert_v8_to_ruby(
671
+ isolate, context, prop_value.ToLocalChecked());
672
+ rb_hash_aset(rb_hash, rb_key, rb_value);
673
+ }
674
+ }
675
+ return rb_hash;
676
+ }
677
+
678
+ if (value->IsSymbol()) {
679
+ Local<Symbol> symbol = Local<Symbol>::Cast(value);
680
+ Local<Value> description = symbol->Description(isolate);
681
+ v8::String::Utf8Value symbol_name(isolate, description);
682
+
683
+ VALUE str_symbol = rb_utf8_str_new(*symbol_name, symbol_name.length());
684
+
685
+ return rb_str_intern(str_symbol);
686
+ }
687
+
688
+ MaybeLocal<String> rstr_maybe = value->ToString(context);
689
+
690
+ if (rstr_maybe.IsEmpty()) {
691
+ return Qnil;
692
+ } else {
693
+ Local<String> rstr = rstr_maybe.ToLocalChecked();
694
+ return rb_utf8_str_new(*String::Utf8Value(isolate, rstr), rstr->Utf8Length(isolate));
695
+ }
696
+ };
697
+
698
+ // this is kind of slow because RB_ULL2NUM allocs when the pointer
699
+ // doesn't fit in a fixnum but yolo'ing and reinterpret_casting the
700
+ // pointer to a VALUE is probably not very sound
701
+ VALUE arg = RB_ULL2NUM(reinterpret_cast<uintptr_t>(&state));
702
+ return rb_protect(can_raise, arg, nullptr);
676
703
  }
677
704
 
678
705
  static VALUE convert_v8_to_ruby(Isolate* isolate,
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module MiniRacer
4
- VERSION = "0.17.0.pre4"
4
+ VERSION = "0.17.0.pre5"
5
5
  LIBV8_NODE_VERSION = "~> 22.7.0.4"
6
6
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mini_racer
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.17.0.pre4
4
+ version: 0.17.0.pre5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sam Saffron
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-09-17 00:00:00.000000000 Z
11
+ date: 2024-09-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -119,9 +119,9 @@ licenses:
119
119
  - MIT
120
120
  metadata:
121
121
  bug_tracker_uri: https://github.com/discourse/mini_racer/issues
122
- changelog_uri: https://github.com/discourse/mini_racer/blob/v0.17.0.pre4/CHANGELOG
123
- documentation_uri: https://www.rubydoc.info/gems/mini_racer/0.17.0.pre4
124
- source_code_uri: https://github.com/discourse/mini_racer/tree/v0.17.0.pre4
122
+ changelog_uri: https://github.com/discourse/mini_racer/blob/v0.17.0.pre5/CHANGELOG
123
+ documentation_uri: https://www.rubydoc.info/gems/mini_racer/0.17.0.pre5
124
+ source_code_uri: https://github.com/discourse/mini_racer/tree/v0.17.0.pre5
125
125
  post_install_message:
126
126
  rdoc_options: []
127
127
  require_paths: