New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
dart2js: fails to eliminate range check in code accessing array elements in pairs #6070
Comments
Set owner to ngeoffray@google.com. |
Removed this from the M2 milestone. |
This comment was originally written by ngeoffray@google.com Note that the reason in your second version, the second check is not eliminated is because we treat the $.S call has side effects, and therefore the size of the array can change. |
Interesting. |
Added TriageForM5 label. |
Removed TriageForM5 label. |
This comment was originally written by ngeoffray@google.com Added Triaged label. |
This comment was originally written by ngeoffray@google.com Set owner to @floitschG. |
Fwiw this is what we generate now. So we still have the second check. It doesn't look like side-effects are the reason we do the bounds-check. for (i = 0; i < a.length; i += 2) { Removed the owner. |
Could still be side-effects. |
Removed this from the Later milestone. |
Removed Oldschool-Milestone-Later label. |
This example is distilled from some code where I am storing pairs of elements in an array.
The compiler should be able to eliminate the index bounds check.
pr(List a) {
for (int i = 0; i + 1 < a.length; i += 2) {
print('${a[i]} ${a[i+1]}');
}
}
main() {
var f = pr;
f([1,2]);
f([1,2,3,4,5]);
}
$.pr = function(a) {
if (typeof a !== 'string' && (typeof a !== 'object' || a === null || a.constructor !== Array && !a.is$JavaScriptIndexingBehavior))
return $.pr$bailout(1, a);
for (var i = 0; t1 = i + 1, t2 = a.length, t1 < t2; i += 2) {
if (i >= t2)
throw $.ioore(i);
var t3 = $.S(a[i]) + ' ';
if (t1 >= a.length)
throw $.ioore(t1);
$.print(t3 + $.S(a[t1]));
}
var t2, t1;
};
If I change the check to i < a.length - 1, one access check is eliminated, but the other is not:
(I prefer the first version since the loop condition states the quantity (i+1) that must be in range.)
$.pr = function(a) {
if (typeof a !== 'string' && (typeof a !== 'object' || a === null || a.constructor !== Array && !a.is$JavaScriptIndexingBehavior))
return $.pr$bailout(1, a);
for (var i = 0; i < a.length - 1; i += 2) {
var t1 = $.S(a[i]) + ' ';
var t2 = i + 1;
if (t2 >= a.length)
throw $.ioore(t2);
$.print(t1 + $.S(a[t2]));
}
};
The text was updated successfully, but these errors were encountered: