GeezerVison is showing github.com — src: prevent URLPattern property accessors from crashing on invalid this · nodejs/node@edb194b
File treeExpand file treeCollapse file tree Open diff view settings Expand file treeCollapse file tree Open diff view settings Collapse file Copy file name to clipboardExpand all lines: src/node_url_pattern.cc +23-9Lines changed: 23 additions & 9 deletions | Original file line number | Diff line number | Diff line change |
|---|
@@ -26,6 +26,7 @@ using v8::Object; | 26 | 26 | using v8::PropertyAttribute; | 27 | 27 | using v8::ReadOnly; | 28 | 28 | using v8::RegExp; | | 29 | +using v8::Signature; | 29 | 30 | using v8::String; | 30 | 31 | using v8::Value; | 31 | 32 |
| @@ -682,58 +683,71 @@ static void Initialize(Local<Object> target, | 682 | 683 | auto prototype_template = ctor_tmpl->PrototypeTemplate(); | 683 | 684 | ctor_tmpl->SetClassName(FIXED_ONE_BYTE_STRING(isolate, "URLPattern")); | 684 | 685 |
| | 686 | + // The signature is used to prevent the property accessors from being | | 687 | + // called on the wrong receiver object (`this`) | | 688 | + auto signature = Signature::New(isolate, ctor_tmpl); | | 689 | + | 685 | 690 | instance_template->SetInternalFieldCount(URLPattern::kInternalFieldCount); | 686 | 691 | prototype_template->SetAccessorProperty( | 687 | 692 | env->protocol_string(), | 688 | | - FunctionTemplate::New(isolate, URLPattern::Protocol), | | 693 | + FunctionTemplate::New( | | 694 | + isolate, URLPattern::Protocol, Local<Value>(), signature), | 689 | 695 | Local<FunctionTemplate>(), | 690 | 696 | attributes); | 691 | 697 |
| 692 | 698 | prototype_template->SetAccessorProperty( | 693 | 699 | env->username_string(), | 694 | | - FunctionTemplate::New(isolate, URLPattern::Username), | | 700 | + FunctionTemplate::New( | | 701 | + isolate, URLPattern::Username, Local<Value>(), signature), | 695 | 702 | Local<FunctionTemplate>(), | 696 | 703 | attributes); | 697 | 704 |
| 698 | 705 | prototype_template->SetAccessorProperty( | 699 | 706 | env->password_string(), | 700 | | - FunctionTemplate::New(isolate, URLPattern::Password), | | 707 | + FunctionTemplate::New( | | 708 | + isolate, URLPattern::Password, Local<Value>(), signature), | 701 | 709 | Local<FunctionTemplate>(), | 702 | 710 | attributes); | 703 | 711 |
| 704 | 712 | prototype_template->SetAccessorProperty( | 705 | 713 | env->hostname_string(), | 706 | | - FunctionTemplate::New(isolate, URLPattern::Hostname), | | 714 | + FunctionTemplate::New( | | 715 | + isolate, URLPattern::Hostname, Local<Value>(), signature), | 707 | 716 | Local<FunctionTemplate>(), | 708 | 717 | attributes); | 709 | 718 |
| 710 | 719 | prototype_template->SetAccessorProperty( | 711 | 720 | env->port_string(), | 712 | | - FunctionTemplate::New(isolate, URLPattern::Port), | | 721 | + FunctionTemplate::New( | | 722 | + isolate, URLPattern::Port, Local<Value>(), signature), | 713 | 723 | Local<FunctionTemplate>(), | 714 | 724 | attributes); | 715 | 725 |
| 716 | 726 | prototype_template->SetAccessorProperty( | 717 | 727 | env->pathname_string(), | 718 | | - FunctionTemplate::New(isolate, URLPattern::Pathname), | | 728 | + FunctionTemplate::New( | | 729 | + isolate, URLPattern::Pathname, Local<Value>(), signature), | 719 | 730 | Local<FunctionTemplate>(), | 720 | 731 | attributes); | 721 | 732 |
| 722 | 733 | prototype_template->SetAccessorProperty( | 723 | 734 | env->search_string(), | 724 | | - FunctionTemplate::New(isolate, URLPattern::Search), | | 735 | + FunctionTemplate::New( | | 736 | + isolate, URLPattern::Search, Local<Value>(), signature), | 725 | 737 | Local<FunctionTemplate>(), | 726 | 738 | attributes); | 727 | 739 |
| 728 | 740 | prototype_template->SetAccessorProperty( | 729 | 741 | env->hash_string(), | 730 | | - FunctionTemplate::New(isolate, URLPattern::Hash), | | 742 | + FunctionTemplate::New( | | 743 | + isolate, URLPattern::Hash, Local<Value>(), signature), | 731 | 744 | Local<FunctionTemplate>(), | 732 | 745 | attributes); | 733 | 746 |
| 734 | 747 | prototype_template->SetAccessorProperty( | 735 | 748 | env->has_regexp_groups_string(), | 736 | | - FunctionTemplate::New(isolate, URLPattern::HasRegexpGroups), | | 749 | + FunctionTemplate::New( | | 750 | + isolate, URLPattern::HasRegexpGroups, Local<Value>(), signature), | 737 | 751 | Local<FunctionTemplate>(), | 738 | 752 | attributes); | 739 | 753 |
| |
Collapse file Copy file name to clipboard +40Lines changed: 40 additions & 0 deletions | Original file line number | Diff line number | Diff line change |
|---|
| | 1 | +'use strict'; | | 2 | + | | 3 | +require('../common'); | | 4 | + | | 5 | +const { URLPattern } = require('url'); | | 6 | +const { throws } = require('assert'); | | 7 | + | | 8 | +const pattern = new URLPattern(); | | 9 | +const proto = Object.getPrototypeOf(pattern); | | 10 | + | | 11 | +// Verifies that attempts to call the property getters on a URLPattern | | 12 | +// with the incorrect `this` will not crash the process. | | 13 | +[ | | 14 | + 'protocol', | | 15 | + 'username', | | 16 | + 'password', | | 17 | + 'hostname', | | 18 | + 'port', | | 19 | + 'pathname', | | 20 | + 'search', | | 21 | + 'hash', | | 22 | + 'hasRegExpGroups', | | 23 | +].forEach((i) => { | | 24 | + const prop = Object.getOwnPropertyDescriptor(proto, i).get; | | 25 | + throws(() => prop({}), { | | 26 | + message: 'Illegal invocation', | | 27 | + }, i); | | 28 | +}); | | 29 | + | | 30 | +// Verifies that attempts to call the exec and test functions | | 31 | +// with the wrong this also throw | | 32 | + | | 33 | +const { test, exec } = pattern; | | 34 | + | | 35 | +throws(() => test({}), { | | 36 | + message: 'Illegal invocation', | | 37 | +}); | | 38 | +throws(() => exec({}), { | | 39 | + message: 'Illegal invocation', | | 40 | +}); |
|