Skip to content

Commit

Permalink
Merge branch 'stenzek:master' into master
Browse files Browse the repository at this point in the history
  • Loading branch information
yeager authored Jan 2, 2025
2 parents e898a6c + 83b4757 commit 3d8eee0
Show file tree
Hide file tree
Showing 27 changed files with 983 additions and 204 deletions.
2 changes: 0 additions & 2 deletions data/resources/gamedb.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -67726,7 +67726,6 @@ SLES-00032:
- SLES-00032
- SLES-03389
controllers:
- AnalogController
- DigitalController
metadata:
publisher: "Rockstar Games"
Expand Down Expand Up @@ -67757,7 +67756,6 @@ SLUS-00106:
rating: NoIssues
versionTested: "0.1-1308-g622e50fa"
controllers:
- AnalogController
- DigitalController
metadata:
publisher: "Take 2 Interactive, Inc"
Expand Down
129 changes: 109 additions & 20 deletions src/common/gsvector.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -87,25 +87,25 @@ GSMatrix4x4::GSMatrix4x4(float e00, float e01, float e02, float e03, float e10,
E[3][3] = e33;
}

GSMatrix4x4::GSMatrix4x4(const GSMatrix2x2& m)
{
E[0][0] = m.E[0][0];
E[0][1] = m.E[0][1];
E[0][2] = 0.0f;
E[0][3] = 0.0f;
E[1][0] = m.E[1][0];
E[1][1] = m.E[1][1];
E[1][2] = 0.0f;
E[1][3] = 0.0f;
E[2][0] = 0.0f;
E[2][1] = 0.0f;
E[2][2] = 1.0f;
E[2][3] = 0.0f;
E[3][0] = 0.0f;
E[3][1] = 0.0f;
E[3][2] = 0.0f;
E[3][3] = 1.0f;
}
GSMatrix4x4::GSMatrix4x4(const GSMatrix2x2& m)
{
E[0][0] = m.E[0][0];
E[0][1] = m.E[0][1];
E[0][2] = 0.0f;
E[0][3] = 0.0f;
E[1][0] = m.E[1][0];
E[1][1] = m.E[1][1];
E[1][2] = 0.0f;
E[1][3] = 0.0f;
E[2][0] = 0.0f;
E[2][1] = 0.0f;
E[2][2] = 1.0f;
E[2][3] = 0.0f;
E[3][0] = 0.0f;
E[3][1] = 0.0f;
E[3][2] = 0.0f;
E[3][3] = 1.0f;
}

GSMatrix4x4 GSMatrix4x4::operator*(const GSMatrix4x4& m) const
{
Expand Down Expand Up @@ -136,12 +136,41 @@ GSMatrix4x4 GSMatrix4x4::operator*(const GSMatrix4x4& m) const
return res;
}

GSMatrix4x4& GSMatrix4x4::operator*=(const GSMatrix4x4& m)
{
const GSMatrix4x4 copy(*this);

#define MultRC(rw, cl) \
copy.E[rw][0] * m.E[0][cl] + copy.E[rw][1] * m.E[1][cl] + copy.E[rw][2] * m.E[2][cl] + copy.E[rw][3] * m.E[3][cl]

E[0][0] = MultRC(0, 0);
E[0][1] = MultRC(0, 1);
E[0][2] = MultRC(0, 2);
E[0][3] = MultRC(0, 3);
E[1][0] = MultRC(1, 0);
E[1][1] = MultRC(1, 1);
E[1][2] = MultRC(1, 2);
E[1][3] = MultRC(1, 3);
E[2][0] = MultRC(2, 0);
E[2][1] = MultRC(2, 1);
E[2][2] = MultRC(2, 2);
E[2][3] = MultRC(2, 3);
E[3][0] = MultRC(3, 0);
E[3][1] = MultRC(3, 1);
E[3][2] = MultRC(3, 2);
E[3][3] = MultRC(3, 3);

#undef MultRC

return *this;
}

GSVector4 GSMatrix4x4::operator*(const GSVector4& v) const
{
const GSVector4 r0 = row(0);
const GSVector4 r1 = row(1);
const GSVector4 r2 = row(2);
const GSVector4 r3 = row(4);
const GSVector4 r3 = row(3);

return GSVector4(r0.dot(v), r1.dot(v), r2.dot(v), r3.dot(v));
}
Expand Down Expand Up @@ -199,6 +228,11 @@ GSMatrix4x4 GSMatrix4x4::RotationZ(float angle_in_radians)
0.0f, 0.0f, 1.0f);
}

GSMatrix4x4 GSMatrix4x4::Translation(float x, float y, float z)
{
return GSMatrix4x4(1.0f, 0.0f, 0.0f, x, 0.0f, 1.0f, 0.0f, y, 0.0f, 0.0f, 1.0f, z, 0.0f, 0.0f, 0.0f, 1.0f);
}

GSMatrix4x4 GSMatrix4x4::OffCenterOrthographicProjection(float left, float top, float right, float bottom, float zNear,
float zFar)
{
Expand All @@ -222,6 +256,61 @@ GSVector4 GSMatrix4x4::col(size_t i) const
return GSVector4(E[0][i], E[1][i], E[2][i], E[3][i]);
}

GSMatrix4x4 GSMatrix4x4::Invert() const
{
GSMatrix4x4 ret;

float v0 = E[2][0] * E[3][1] - E[2][1] * E[3][0];
float v1 = E[2][0] * E[3][2] - E[2][2] * E[3][0];
float v2 = E[2][0] * E[3][3] - E[2][3] * E[3][0];
float v3 = E[2][1] * E[3][2] - E[2][2] * E[3][1];
float v4 = E[2][1] * E[3][3] - E[2][3] * E[3][1];
float v5 = E[2][2] * E[3][3] - E[2][3] * E[3][2];

const float t00 = +(v5 * E[1][1] - v4 * E[1][2] + v3 * E[1][3]);
const float t10 = -(v5 * E[1][0] - v2 * E[1][2] + v1 * E[1][3]);
const float t20 = +(v4 * E[1][0] - v2 * E[1][1] + v0 * E[1][3]);
const float t30 = -(v3 * E[1][0] - v1 * E[1][1] + v0 * E[1][2]);

const float inv_det = 1.0f / (t00 * E[0][0] + t10 * E[0][1] + t20 * E[0][2] + t30 * E[0][3]);

ret.E[0][0] = t00 * inv_det;
ret.E[1][0] = t10 * inv_det;
ret.E[2][0] = t20 * inv_det;
ret.E[3][0] = t30 * inv_det;

ret.E[0][1] = -(v5 * E[0][1] - v4 * E[0][2] + v3 * E[0][3]) * inv_det;
ret.E[1][1] = +(v5 * E[0][0] - v2 * E[0][2] + v1 * E[0][3]) * inv_det;
ret.E[2][1] = -(v4 * E[0][0] - v2 * E[0][1] + v0 * E[0][3]) * inv_det;
ret.E[3][1] = +(v3 * E[0][0] - v1 * E[0][1] + v0 * E[0][2]) * inv_det;

v0 = E[1][0] * E[3][1] - E[1][1] * E[3][0];
v1 = E[1][0] * E[3][2] - E[1][2] * E[3][0];
v2 = E[1][0] * E[3][3] - E[1][3] * E[3][0];
v3 = E[1][1] * E[3][2] - E[1][2] * E[3][1];
v4 = E[1][1] * E[3][3] - E[1][3] * E[3][1];
v5 = E[1][2] * E[3][3] - E[1][3] * E[3][2];

ret.E[0][2] = +(v5 * E[0][1] - v4 * E[0][2] + v3 * E[0][3]) * inv_det;
ret.E[1][2] = -(v5 * E[0][0] - v2 * E[0][2] + v1 * E[0][3]) * inv_det;
ret.E[2][2] = +(v4 * E[0][0] - v2 * E[0][1] + v0 * E[0][3]) * inv_det;
ret.E[3][2] = -(v3 * E[0][0] - v1 * E[0][1] + v0 * E[0][2]) * inv_det;

v0 = E[2][1] * E[1][0] - E[2][0] * E[1][1];
v1 = E[2][2] * E[1][0] - E[2][0] * E[1][2];
v2 = E[2][3] * E[1][0] - E[2][0] * E[1][3];
v3 = E[2][2] * E[1][1] - E[2][1] * E[1][2];
v4 = E[2][3] * E[1][1] - E[2][1] * E[1][3];
v5 = E[2][3] * E[1][2] - E[2][2] * E[1][3];

ret.E[0][3] = -(v5 * E[0][1] - v4 * E[0][2] + v3 * E[0][3]) * inv_det;
ret.E[1][3] = +(v5 * E[0][0] - v2 * E[0][2] + v1 * E[0][3]) * inv_det;
ret.E[2][3] = -(v4 * E[0][0] - v2 * E[0][1] + v0 * E[0][3]) * inv_det;
ret.E[3][3] = +(v3 * E[0][0] - v1 * E[0][1] + v0 * E[0][2]) * inv_det;

return ret;
}

void GSMatrix4x4::store(void* m)
{
std::memcpy(m, &E[0][0], sizeof(E));
Expand Down
4 changes: 4 additions & 0 deletions src/common/gsvector.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ class alignas(VECTOR_ALIGNMENT) GSMatrix4x4
GSMatrix4x4(const GSMatrix2x2& m);

GSMatrix4x4 operator*(const GSMatrix4x4& m) const;
GSMatrix4x4& operator*=(const GSMatrix4x4& m);

GSVector4 operator*(const GSVector4& v) const;

Expand All @@ -55,6 +56,7 @@ class alignas(VECTOR_ALIGNMENT) GSMatrix4x4
static GSMatrix4x4 RotationX(float angle_in_radians);
static GSMatrix4x4 RotationY(float angle_in_radians);
static GSMatrix4x4 RotationZ(float angle_in_radians);
static GSMatrix4x4 Translation(float x, float y, float z);

static GSMatrix4x4 OffCenterOrthographicProjection(float left, float top, float right, float bottom, float zNear,
float zFar);
Expand All @@ -63,6 +65,8 @@ class alignas(VECTOR_ALIGNMENT) GSMatrix4x4
GSVector4 row(size_t i) const;
GSVector4 col(size_t i) const;

GSMatrix4x4 Invert() const;

void store(void* m);

float E[4][4];
Expand Down
9 changes: 7 additions & 2 deletions src/common/gsvector_sse.h
Original file line number Diff line number Diff line change
Expand Up @@ -2019,13 +2019,13 @@ class alignas(16) GSVector4

ALWAYS_INLINE GSVector4 hsub(const GSVector4& v) const { return GSVector4(_mm_hsub_ps(m, v.m)); }

ALWAYS_INLINE float dot(const GSVector4& v) const
NEVER_INLINE float dot(const GSVector4& v) const
{
#ifdef CPU_ARCH_SSE41
return _mm_cvtss_f32(_mm_dp_ps(m, v.m, 0xf1));
#else
__m128 tmp = _mm_mul_ps(m, v.m);
tmp = _mm_add_ps(tmp, _mm_unpackhi_ps(tmp, tmp)); // (x+z, y+w, ..., ...)
tmp = _mm_add_ps(tmp, _mm_movehl_ps(tmp, tmp)); // (x+z, y+w, ..., ...)
tmp = _mm_add_ss(tmp, _mm_shuffle_ps(tmp, tmp, _MM_SHUFFLE(3, 2, 1, 1)));
return _mm_cvtss_f32(tmp);
#endif
Expand Down Expand Up @@ -2057,7 +2057,12 @@ class alignas(16) GSVector4

ALWAYS_INLINE GSVector4 blend32(const GSVector4& v, const GSVector4& mask) const
{
#ifdef CPU_ARCH_SSE41
return GSVector4(_mm_blendv_ps(m, v, mask));
#else
// NOTE: Assumes the entire lane is set with 1s or 0s.
return (v & mask) | andnot(mask);
#endif
}

ALWAYS_INLINE GSVector4 upl(const GSVector4& v) const { return GSVector4(_mm_unpacklo_ps(m, v)); }
Expand Down
9 changes: 8 additions & 1 deletion src/core/cpu_code_cache.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ static void ClearBlocks();

static Block* LookupBlock(u32 pc);
static Block* CreateBlock(u32 pc, const BlockInstructionList& instructions, const BlockMetadata& metadata);
static bool HasBlockLUT(u32 pc);
static bool IsBlockCodeCurrent(const Block* block);
static bool RevalidateBlock(Block* block);
static PageProtectionMode GetProtectionModeForPC(u32 pc);
Expand Down Expand Up @@ -362,6 +363,12 @@ CPU::CodeCache::Block* CPU::CodeCache::LookupBlock(u32 pc)
return s_block_lut[table][idx];
}

bool CPU::CodeCache::HasBlockLUT(u32 pc)
{
const u32 table = pc >> LUT_TABLE_SHIFT;
return (s_block_lut[table] != nullptr);
}

CPU::CodeCache::Block* CPU::CodeCache::CreateBlock(u32 pc, const BlockInstructionList& instructions,
const BlockMetadata& metadata)
{
Expand Down Expand Up @@ -1372,7 +1379,7 @@ const void* CPU::CodeCache::CreateBlockLink(Block* block, void* code, u32 newpc)
}
else
{
dst = g_compile_or_revalidate_block;
dst = HasBlockLUT(newpc) ? g_compile_or_revalidate_block : g_interpret_block;
}

BlockLinkMap::iterator iter = s_block_links.emplace(newpc, code);
Expand Down
Loading

0 comments on commit 3d8eee0

Please sign in to comment.