mirror of
https://github.com/dart-lang/sdk
synced 2024-10-14 10:48:25 +00:00
Fix null-read in RegExpMatch.groupNames.
Fixes VM, DDC and Dart2js. BUG= http://dartbug.com/39406 Change-Id: If181eaf50905c571614b656a232564e394e1b35d Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/136635 Commit-Queue: Lasse R.H. Nielsen <lrn@google.com> Reviewed-by: Lasse R.H. Nielsen <lrn@google.com> Reviewed-by: Teagan Strickland <sstrickl@google.com> Reviewed-by: Bob Nystrom <rnystrom@google.com>
This commit is contained in:
parent
5ae4448779
commit
9e10ef4458
|
@ -203,7 +203,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
String namedGroup(String name) {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var result = JS('String|Null', '#[#]', groups, name);
|
||||
if (result != null || JS<bool>('!', '# in #', name, groups)) {
|
||||
|
@ -214,7 +214,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
Iterable<String> get groupNames {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var keys = JSArray<String>.of(JS('', 'Object.keys(#)', groups));
|
||||
return SubListIterable(keys, 0, null);
|
||||
|
|
|
@ -212,7 +212,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
String namedGroup(String name) {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var result = JS('String|Null', '#[#]', groups, name);
|
||||
if (result != null || JS('bool', '# in #', name, groups)) {
|
||||
|
@ -223,7 +223,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
Iterable<String> get groupNames {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var keys = new JSArray<String>.markGrowable(
|
||||
JS('returns:JSExtendableArray;new:true', 'Object.keys(#)', groups));
|
||||
|
|
|
@ -274,13 +274,18 @@ class _RegExp implements RegExp {
|
|||
|
||||
int get _groupCount native "RegExp_getGroupCount";
|
||||
|
||||
// Returns a List [String, int, String, int, ...] where each
|
||||
// String is the name of a capture group and the following
|
||||
// int is that capture group's index.
|
||||
/// The names and indices of named capture group.
|
||||
///
|
||||
/// Returns a [List] of alternating strings and integers,
|
||||
/// `[String, int, String, int, ...]` where each
|
||||
/// [String] is the name of a capture group and the following
|
||||
/// [int] is that capture group's index.
|
||||
/// Returns `null` if there are no group names.
|
||||
List get _groupNameList native "RegExp_getGroupNameMap";
|
||||
|
||||
Iterable<String> get _groupNames sync* {
|
||||
final nameList = _groupNameList;
|
||||
if (nameList == null) return;
|
||||
for (var i = 0; i < nameList.length; i += 2) {
|
||||
yield nameList[i] as String;
|
||||
}
|
||||
|
@ -288,9 +293,10 @@ class _RegExp implements RegExp {
|
|||
|
||||
int _groupNameIndex(String name) {
|
||||
var nameList = _groupNameList;
|
||||
if (nameList == null) return -1;
|
||||
for (var i = 0; i < nameList.length; i += 2) {
|
||||
if (name == nameList[i]) {
|
||||
return nameList[i + 1];
|
||||
return nameList[i + 1] as int;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
|
|
|
@ -204,7 +204,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
String? namedGroup(String name) {
|
||||
var groups = JS<Object?>('', '#.groups', _match);
|
||||
var groups = JS<Object?>('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var result = JS<String?>('', '#[#]', groups, name);
|
||||
if (result != null || JS<bool>('!', '# in #', name, groups)) {
|
||||
|
@ -215,7 +215,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
Iterable<String> get groupNames {
|
||||
var groups = JS<Object?>('', '#.groups', _match);
|
||||
var groups = JS<Object?>('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var keys = JSArray<String>.of(JS('', 'Object.keys(#)', groups));
|
||||
return SubListIterable(keys, 0, null);
|
||||
|
|
|
@ -209,7 +209,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
String namedGroup(String name) {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var result = JS('String|Null', '#[#]', groups, name);
|
||||
if (result != null || JS('bool', '# in #', name, groups)) {
|
||||
|
@ -220,7 +220,7 @@ class _MatchImplementation implements RegExpMatch {
|
|||
}
|
||||
|
||||
Iterable<String> get groupNames {
|
||||
var groups = JS('Object', '#.groups', _match);
|
||||
var groups = JS('Object|Null', '#.groups', _match);
|
||||
if (groups != null) {
|
||||
var keys = new JSArray<String>.markGrowable(
|
||||
JS('returns:JSExtendableArray;new:true', 'Object.keys(#)', groups));
|
||||
|
|
|
@ -277,13 +277,18 @@ class _RegExp implements RegExp {
|
|||
|
||||
int get _groupCount native "RegExp_getGroupCount";
|
||||
|
||||
// Returns a List [String, int, String, int, ...] where each
|
||||
// String is the name of a capture group and the following
|
||||
// int is that capture group's index.
|
||||
List get _groupNameList native "RegExp_getGroupNameMap";
|
||||
/// The names and indices of named capture group.
|
||||
///
|
||||
/// Returns a [List] of alternating strings and integers,
|
||||
/// `[String, int, String, int, ...]` where each
|
||||
/// [String] is the name of a capture group and the following
|
||||
/// [int] is that capture group's index.
|
||||
/// Returns `null` if there are no group names.
|
||||
List? get _groupNameList native "RegExp_getGroupNameMap";
|
||||
|
||||
Iterable<String> get _groupNames sync* {
|
||||
final nameList = _groupNameList;
|
||||
if (nameList == null) return;
|
||||
for (var i = 0; i < nameList.length; i += 2) {
|
||||
yield nameList[i] as String;
|
||||
}
|
||||
|
@ -291,9 +296,10 @@ class _RegExp implements RegExp {
|
|||
|
||||
int _groupNameIndex(String name) {
|
||||
var nameList = _groupNameList;
|
||||
if (nameList == null) return -1;
|
||||
for (var i = 0; i < nameList.length; i += 2) {
|
||||
if (name == nameList[i]) {
|
||||
return nameList[i + 1];
|
||||
return nameList[i + 1] as int;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
|
|
18
tests/corelib/regexp/regexp_regression_39406_test.dart
Normal file
18
tests/corelib/regexp/regexp_regression_39406_test.dart
Normal file
|
@ -0,0 +1,18 @@
|
|||
// Copyright (c) 2020, the Dart project authors. Please see the AUTHORS file
|
||||
// for details. All rights reserved. Use of this source code is governed by a
|
||||
// BSD-style license that can be found in the LICENSE file.
|
||||
|
||||
import "package:expect/expect.dart";
|
||||
|
||||
// See http://dartbug.com/39406
|
||||
//
|
||||
// The following code must not throw.
|
||||
|
||||
void main() {
|
||||
var regExp = RegExp(r'\w+');
|
||||
var message = 'Hello world!';
|
||||
var match = regExp.firstMatch(message);
|
||||
var groupNames = match!.groupNames.toList();
|
||||
Expect.listEquals([], groupNames);
|
||||
Expect.throwsArgumentError(() => match.namedGroup("x"));
|
||||
}
|
18
tests/corelib_2/regexp/regexp_regression_39406_test.dart
Normal file
18
tests/corelib_2/regexp/regexp_regression_39406_test.dart
Normal file
|
@ -0,0 +1,18 @@
|
|||
// Copyright (c) 2020, the Dart project authors. Please see the AUTHORS file
|
||||
// for details. All rights reserved. Use of this source code is governed by a
|
||||
// BSD-style license that can be found in the LICENSE file.
|
||||
|
||||
import "package:expect/expect.dart";
|
||||
|
||||
// See http://dartbug.com/39406
|
||||
//
|
||||
// The following code must not throw.
|
||||
|
||||
void main() {
|
||||
var regExp = RegExp(r'\w+');
|
||||
var message = 'Hello world!';
|
||||
var match = regExp.firstMatch(message);
|
||||
var groupNames = match.groupNames.toList();
|
||||
Expect.listEquals([], groupNames);
|
||||
Expect.throwsArgumentError(() => match.namedGroup("x"));
|
||||
}
|
Loading…
Reference in a new issue