(svn r27989) -Fix (r27985): VA2 optimisation failed in various special cases:

- nvar=0 is meant to return the calculated result.
  - Missing references resolve to NULL and got identified with the default result.
  - Missing 'break' broke overlapping cases.
  - Splitting into non-overlapping cases could result in more than 256 cases.
This commit is contained in:
frosch
2018-03-11 15:08:51 +00:00
parent 23b21b15eb
commit a537fd5d0e
3 changed files with 8 additions and 4 deletions

View File

@@ -4698,6 +4698,8 @@ static void NewSpriteGroup(ByteReader *buf)
group->default_group = GetGroupFromGroupID(setid, type, buf->ReadWord());
group->error_group = ranges.size() > 0 ? ranges[0].group : group->default_group;
/* nvar == 0 is a special case -- we turn our value into a callback result */
group->calculated_result = ranges.size() == 0;
/* Sort ranges ascending. When ranges overlap, this may required clamping or splitting them */
std::vector<uint32> bounds;
@@ -4711,10 +4713,11 @@ static void NewSpriteGroup(ByteReader *buf)
std::vector<const SpriteGroup *> target;
for (uint j = 0; j < bounds.size(); ++j) {
uint32 v = bounds[j];
const SpriteGroup *t = NULL;
const SpriteGroup *t = group->default_group;
for (uint i = 0; i < ranges.size(); i++) {
if (ranges[i].low <= v && v <= ranges[i].high) {
t = ranges[i].group;
break;
}
}
target.push_back(t);
@@ -4723,7 +4726,7 @@ static void NewSpriteGroup(ByteReader *buf)
std::vector<DeterministicSpriteGroupRange> optimised;
for (uint j = 0; j < bounds.size(); ) {
if (target[j]) {
if (target[j] != group->default_group) {
DeterministicSpriteGroupRange r;
r.group = target[j];
r.low = bounds[j];