[Scummvm-git-logs] scummvm master -> a784a8db940c5f87209664f893f08c2c2804e2f7
aquadran
noreply at scummvm.org
Tue Aug 12 05:22:20 UTC 2025
This automated email contains information about 1 new commit which have been
pushed to the 'scummvm' repo located at https://api.github.com/repos/scummvm/scummvm .
Summary:
a784a8db94 WINTERMUTE: Replace qsort with msvc version
Commit: a784a8db940c5f87209664f893f08c2c2804e2f7
https://github.com/scummvm/scummvm/commit/a784a8db940c5f87209664f893f08c2c2804e2f7
Author: PaweÅ KoÅodziejski (aquadran at gmail.com)
Date: 2025-08-12T07:22:14+02:00
Commit Message:
WINTERMUTE: Replace qsort with msvc version
Changed paths:
engines/wintermute/ad/ad_scene.cpp
engines/wintermute/ad/ad_scene_geometry.cpp
engines/wintermute/base/base_surface_storage.cpp
engines/wintermute/base/particles/part_emitter.cpp
engines/wintermute/utils/utils.cpp
engines/wintermute/utils/utils.h
diff --git a/engines/wintermute/ad/ad_scene.cpp b/engines/wintermute/ad/ad_scene.cpp
index 3400bc80ce8..6fee21fd3e5 100644
--- a/engines/wintermute/ad/ad_scene.cpp
+++ b/engines/wintermute/ad/ad_scene.cpp
@@ -1433,7 +1433,7 @@ bool AdScene::displayRegionContent(AdRegion *region, bool display3DOnly) {
}
// sort by _posY
- qsort(objects.getData(), objects.getSize(), sizeof(AdObject *), AdScene::compareObjs);
+ qsort_msvc(objects.getData(), objects.getSize(), sizeof(AdObject *), AdScene::compareObjs);
// display them
for (int32 i = 0; i < objects.getSize(); i++) {
@@ -3752,7 +3752,7 @@ bool AdScene::getRegionObjects(AdRegion *region, BaseArray<AdObject *> &objects,
}
// sort by _posY
- qsort(objects.getData(), objects.getSize(), sizeof(AdObject *), AdScene::compareObjs);
+ qsort_msvc(objects.getData(), objects.getSize(), sizeof(AdObject *), AdScene::compareObjs);
return STATUS_OK;
}
diff --git a/engines/wintermute/ad/ad_scene_geometry.cpp b/engines/wintermute/ad/ad_scene_geometry.cpp
index f97fbf78b9e..16166e04da8 100644
--- a/engines/wintermute/ad/ad_scene_geometry.cpp
+++ b/engines/wintermute/ad/ad_scene_geometry.cpp
@@ -50,6 +50,7 @@
#include "engines/wintermute/base/gfx/xmath.h"
#include "engines/wintermute/base/gfx/3dutils.h"
#include "engines/wintermute/utils/path_util.h"
+#include "engines/wintermute/utils/utils.h"
#include "engines/wintermute/system/sys_class_registry.h"
#include "engines/wintermute/wintermute.h"
@@ -949,7 +950,7 @@ bool AdSceneGeometry::enableLights(DXVector3 point, BaseArray<char *> &ignoreLig
// sort by distance
if (activeLights.getSize() > 0) {
- qsort(activeLights.getData(), activeLights.getSize(), sizeof(Light3D *), AdSceneGeometry::compareLights);
+ qsort_msvc(activeLights.getData(), activeLights.getSize(), sizeof(Light3D *), AdSceneGeometry::compareLights);
for (int32 i = 0; i < activeLights.getSize(); i++) {
activeLights[i]->_isAvailable = static_cast<int32>(i) < maxLights;
diff --git a/engines/wintermute/base/base_surface_storage.cpp b/engines/wintermute/base/base_surface_storage.cpp
index 9ed354c6063..3ce51f12940 100644
--- a/engines/wintermute/base/base_surface_storage.cpp
+++ b/engines/wintermute/base/base_surface_storage.cpp
@@ -32,6 +32,7 @@
#include "engines/wintermute/base/base_engine.h"
#include "engines/wintermute/base/base_file_manager.h"
#include "engines/wintermute/platform_osystem.h"
+#include "engines/wintermute/utils/utils.h"
#include "common/str.h"
namespace Wintermute {
@@ -170,7 +171,7 @@ bool BaseSurfaceStorage::persist(BasePersistenceManager *persistMgr)
//////////////////////////////////////////////////////////////////////////
bool BaseSurfaceStorage::sortSurfaces() {
- qsort(_surfaces.getData(), _surfaces.getSize(), sizeof(BaseSurface *), surfaceSortCB);
+ qsort_msvc(_surfaces.getData(), _surfaces.getSize(), sizeof(BaseSurface *), surfaceSortCB);
return STATUS_OK;
}
diff --git a/engines/wintermute/base/particles/part_emitter.cpp b/engines/wintermute/base/particles/part_emitter.cpp
index 7c92767221a..ac7d089e607 100644
--- a/engines/wintermute/base/particles/part_emitter.cpp
+++ b/engines/wintermute/base/particles/part_emitter.cpp
@@ -366,7 +366,7 @@ bool PartEmitter::start() {
//////////////////////////////////////////////////////////////////////////
bool PartEmitter::sortParticlesByZ() {
// sort particles by _posY
- qsort(_particles.getData(), _particles.getSize(), sizeof(PartParticle *), PartEmitter::compareZ);
+ qsort_msvc(_particles.getData(), _particles.getSize(), sizeof(PartParticle *), PartEmitter::compareZ);
return STATUS_OK;
}
diff --git a/engines/wintermute/utils/utils.cpp b/engines/wintermute/utils/utils.cpp
index 49c8d861e19..34a3a778df3 100644
--- a/engines/wintermute/utils/utils.cpp
+++ b/engines/wintermute/utils/utils.cpp
@@ -25,6 +25,12 @@
* Copyright (c) 2011 Jan Nedoma
*/
+/*
+ * qsort code originated from Wine sources.
+ * Copyright 2000 Jon Griffiths
+ * Copyright 2014 Piotr Caban
+ */
+
#include "engines/wintermute/utils/utils.h"
#include "engines/wintermute/wintermute.h"
#include "engines/wintermute/base/base_engine.h"
@@ -302,4 +308,116 @@ float BaseUtils::Hue2RGB(float v1, float v2, float vH) {
return (v1);
}
+static inline void swapBytes(byte *l, byte *r, uint32 size) {
+ byte tmp;
+
+ while (size--) {
+ tmp = *l;
+ *l++ = *r;
+ *r++ = tmp;
+ }
+}
+
+static void smallSort(void *base, uint32 num, uint32 size,
+ int32 (*compare)(const void *, const void *)) {
+ byte *max, *p;
+
+ for (uint32 e = num; e > 1; e--) {
+ max = (byte *)base;
+ for (uint32 i = 1; i < e; i++) {
+ p = (byte *)base + i * size;
+ if (compare(p, max) > 0)
+ max = p;
+ }
+
+ if (p != max)
+ swapBytes(p, max, size);
+ }
+}
+
+static void quickSort(void *base, uint32 num, uint32 size,
+ int32 (*compare)(const void *, const void *)) {
+ uint32 stackLo[8 * sizeof(uint32)], stackHi[8 * sizeof(uint32)];
+ uint32 beg, end, lo, hi, med;
+ int32 stackPos;
+
+ stackPos = 0;
+ stackLo[stackPos] = 0;
+ stackHi[stackPos] = num - 1;
+
+#define X(i) ((byte *)base + size * (i))
+ while (stackPos >= 0) {
+ beg = stackLo[stackPos];
+ end = stackHi[stackPos--];
+
+ if (end - beg < 8) {
+ smallSort(X(beg), end - beg + 1, size, compare);
+ continue;
+ }
+
+ lo = beg;
+ hi = end;
+ med = lo + (hi - lo + 1) / 2;
+ if (compare(X(lo), X(med)) > 0)
+ swapBytes(X(lo), X(med), size);
+ if (compare(X(lo), X(hi)) > 0)
+ swapBytes(X(lo), X(hi), size);
+ if (compare(X(med), X(hi)) > 0)
+ swapBytes(X(med), X(hi), size);
+
+ lo++;
+ hi--;
+ while (1) {
+ while (lo <= hi) {
+ if (lo != med && compare(X(lo), X(med)) > 0)
+ break;
+ lo++;
+ }
+
+ while (med != hi) {
+ if (compare(X(hi), X(med)) <= 0)
+ break;
+ hi--;
+ }
+
+
+ if (hi < lo)
+ break;
+
+ swapBytes(X(lo), X(hi), size);
+ if (hi == med)
+ med = lo;
+ lo++;
+ hi--;
+ }
+
+ while (hi > beg) {
+ if (hi != med && compare(X(hi), X(med)) != 0)
+ break;
+ hi--;
+ }
+
+ if (hi - beg >= end-lo) {
+ stackLo[++stackPos] = beg;
+ stackHi[stackPos] = hi;
+ stackLo[++stackPos] = lo;
+ stackHi[stackPos] = end;
+ } else {
+ stackLo[++stackPos] = lo;
+ stackHi[stackPos] = end;
+ stackLo[++stackPos] = beg;
+ stackHi[stackPos] = hi;
+ }
+ }
+#undef X
+}
+
+void qsort_msvc(void *base, uint32 num, uint32 size,
+ int32 (*compare)(const void *, const void *)) {
+ if (base == NULL || num == 0)
+ return;
+
+ quickSort(base, num, size, compare);
+}
+
} // End of namespace Wintermute
diff --git a/engines/wintermute/utils/utils.h b/engines/wintermute/utils/utils.h
index 9a796674767..6c467d741fc 100644
--- a/engines/wintermute/utils/utils.h
+++ b/engines/wintermute/utils/utils.h
@@ -60,6 +60,9 @@ private:
static float Hue2RGB(float v1, float v2, float vH);
};
+void qsort_msvc(void *base, uint32 nmemb, uint32 size,
+ int (*compare)(const void *, const void *));
+
} // End of namespace Wintermute
#endif
More information about the Scummvm-git-logs
mailing list