Skip to content

Commit 901300a

Browse files
committed
Merge remote-tracking branch 'upstream/main' into fuckit
# Conflicts: # src/mips/tests/Makefile
2 parents e2f4eb6 + a5d1a6d commit 901300a

File tree

27 files changed

+823
-85
lines changed

27 files changed

+823
-85
lines changed

src/core/debug.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,7 @@ void PCSX::Debug::checkBP(uint32_t address, BreakpointType type, uint32_t width,
247247
auto end = m_breakpoints.end();
248248
uint32_t normalizedAddress = normalizeAddress(address & ~0xe0000000);
249249

250-
BreakpointUserListType torun;
250+
BreakpointTemporaryListType torun;
251251
for (auto it = m_breakpoints.find(normalizedAddress, normalizedAddress + width - 1); it != end; it++) {
252252
if (it->type() != type) continue;
253253
auto bp = &*it;

src/core/debug.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,11 +62,15 @@ class Debug {
6262
class Breakpoint;
6363
typedef Intrusive::Tree<uint32_t, Breakpoint> BreakpointTreeType;
6464
typedef Intrusive::List<Breakpoint> BreakpointUserListType;
65+
struct InternalTemporaryList {};
66+
typedef Intrusive::List<Breakpoint, InternalTemporaryList> BreakpointTemporaryListType;
6567

6668
typedef std::function<bool(const Breakpoint*, uint32_t address, unsigned width, const char* cause)>
6769
BreakpointInvoker;
6870

69-
class Breakpoint : public BreakpointTreeType::Node, public BreakpointUserListType::Node {
71+
class Breakpoint : public BreakpointTreeType::Node,
72+
public BreakpointUserListType::Node,
73+
public BreakpointTemporaryListType::Node {
7074
public:
7175
Breakpoint(BreakpointType type, const std::string& source, BreakpointInvoker invoker, uint32_t base,
7276
std::string label = "")

src/core/gdb-server.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -608,7 +608,7 @@ void PCSX::GdbClient::processCommand() {
608608
auto& tree = g_emulator->m_debug->getTree();
609609
auto bp = tree.find(addr, Debug::BreakpointTreeType::INTERVAL_SEARCH);
610610
while (bp != tree.end()) {
611-
if (bp->type() == type && !bp->Debug::BreakpointUserListType::Node::isLinked()) {
611+
if (bp->type() == type && !m_breakpoints.isLinked(&*bp)) {
612612
bp++;
613613
} else {
614614
g_emulator->m_debug->removeBreakpoint(&*bp);

src/gpu/soft/soft.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3378,7 +3378,7 @@ void PCSX::SoftGPU::SoftRenderer::drawPoly3TD(int16_t x1, int16_t y1, int16_t x2
33783378
auto dnY = ((posY >> 16) & maskY) + globalTextAddrY + textureWindow.y0;
33793379
uint32_t color = vram16[upX + (upY << 10)];
33803380
color <<= 16;
3381-
color |= vram[dnX + (dnY << 10)];
3381+
color |= vram16[dnX + (dnY << 10)];
33823382
getTextureTransColShade32Solid(pdest, color);
33833383

33843384
posX += difX2;

src/mips/common.mk

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ $(BINDIR)$(TARGET).elf: $(OBJS) $(LIBRARIES) $(EXTRA_DEPS)
8686
ifneq ($(strip $(BINDIR)),)
8787
mkdir -p $(BINDIR)
8888
endif
89-
$(CC) -g -o $(BINDIR)$(TARGET).elf $(OBJS) $(LDFLAGS) $(LIBRARIES)
89+
$(CC) $(LDFLAGS) -g -o $(BINDIR)$(TARGET).elf $(OBJS) $(LIBRARIES)
9090

9191
$(BINDIR)lib$(TARGET).a: $(OBJS) $(EXTRA_DEPS)
9292
$(AR) rcs $(BINDIR)lib$(TARGET).a $(OBJS)

src/mips/common/crt0/README.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
# Limited C runtime
2+
3+
This directory contains some limited C runtime features. It will take care of booting the binary, setting up some minimal environment and then call the main function. It also contains some basic implementations of standard C functions which are required by the compiler when doing self-hosted compilation.
4+
5+
## Using very bare C runtime
6+
The file `crt0.s` is the entry point of the C runtime. It will set up the stack, and call the `main` function. It will not perform any other initialization beyond clearing the BSS section.
7+
8+
## Using C++ runtime
9+
The file `crt0cxx.s` is the entry point of the C++ runtime. It will set up the stack, and then go to the `cxxglue.c` file for further initialization, which will then call the `main` function. The `cxxglue.c` file also contains the minimal implementation of the C++ runtime that is required by the C++ compiler.
10+
11+
## Memory C runtime functions
12+
The files `memory-c.c` and `memory-s.s` contain the 4 basic memory functions that are required by the self-hosted C and C++ compilers. These are `memcpy`, `memset`, `memcmp`, and `memmove`. These are implemented in a very basic way, being very small, and are not optimized for speed. They also contain optimized versions of `memcpy` and `memset` for the MIPS architecture, available using the LDFLAGS `-Wl,-wrap,memcpy` and `-Wl,-wrap,memset` toggles. They are somewhat bigger, but much faster. Note that these 4 functions are available directly when writing C or C++ code using the `__builtin_memcpy`, `__builtin_memset`, `__builtin_memcmp` and `__builtin_memmove` functions, with no need to include any header file.

src/mips/common/crt0/cxxglue.c

Lines changed: 5 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -25,13 +25,11 @@ SOFTWARE.
2525
*/
2626

2727
/* Properly using C++ on the PSX requires a form of the libstdc++ that's
28-
typically called "freestanding", which isn't really buildable at the moment.
29-
See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100057 for details.
30-
This means however that using a full linux compiler such as the Ubuntu
31-
mipsel compiler package will bring in a libstdc++ that utilizes all of
32-
the existing libc. Properly filling in portions of the required ABI, while
33-
avoiding the bits that won't work can be tricky, but is doable. Using a
34-
freestanding compiler won't have the libstdc++, and this wouldn't work. */
28+
typically called "freestanding". While it would contain enough to support
29+
metaprogramming and other C++ features, it would not contain any of the
30+
standard library, as the PSX doesn't have an operating system to speak of.
31+
This code is a minimal implementation of the C++ ABI that's required to
32+
fill in the gaps that the freestanding libstdc++ would have. */
3533

3634
#include <stdatomic.h>
3735
#include <stddef.h>
@@ -135,57 +133,6 @@ __attribute__((weak)) void __cxa_atexit(void (*func)(void*), void* arg, void* ds
135133
// no, we're not going to have shared libraries
136134
__attribute__((weak)) void* __dso_handle = NULL;
137135

138-
__attribute__((weak)) void* memcpy(void* s1_, const void* s2_, size_t n) {
139-
uint8_t* s1 = (uint8_t*)s1_;
140-
const uint8_t* s2 = (uint8_t*)s2_;
141-
size_t i;
142-
143-
for (i = 0; i < n; i++) *s1++ = *s2++;
144-
145-
return s1_;
146-
}
147-
148-
__attribute__((weak)) void* memmove(void* s1_, const void* s2_, size_t n) {
149-
uint8_t* s1 = (uint8_t*)s1_;
150-
const uint8_t* s2 = (uint8_t*)s2_;
151-
size_t i;
152-
153-
if (s1 < s2) {
154-
for (i = 0; i < n; i++) *s1++ = *s2++;
155-
} else if (s1 > s2) {
156-
s1 += n;
157-
s2 += n;
158-
for (i = 0; i < n; i++) *--s1 = *--s2;
159-
}
160-
161-
return s1_;
162-
}
163-
164-
__attribute__((weak)) int memcmp(const void* s1_, const void* s2_, size_t n) {
165-
uint8_t* s1 = (uint8_t*)s1_;
166-
const uint8_t* s2 = (uint8_t*)s2_;
167-
size_t i;
168-
169-
for (i = 0; i < n; i++, s1++, s2++) {
170-
if (*s1 < *s2) {
171-
return -1;
172-
} else if (*s1 > *s2) {
173-
return 1;
174-
}
175-
}
176-
177-
return 0;
178-
}
179-
180-
__attribute__((weak)) void* memset(void* s_, int c, size_t n) {
181-
uint8_t* s = (uint8_t*)s_;
182-
size_t i;
183-
184-
for (i = 0; i < n; i++) *s++ = (uint8_t)c;
185-
186-
return s_;
187-
}
188-
189136
/* Some helpers to make sure we're not going to be preempted during object creation */
190137
static inline uint32_t getCop0Status() {
191138
uint32_t r;

src/mips/common/crt0/memory-c.c

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
/*
2+
3+
MIT License
4+
5+
Copyright (c) 2024 PCSX-Redux authors
6+
7+
Permission is hereby granted, free of charge, to any person obtaining a copy
8+
of this software and associated documentation files (the "Software"), to deal
9+
in the Software without restriction, including without limitation the rights
10+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11+
copies of the Software, and to permit persons to whom the Software is
12+
furnished to do so, subject to the following conditions:
13+
14+
The above copyright notice and this permission notice shall be included in all
15+
copies or substantial portions of the Software.
16+
17+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23+
SOFTWARE.
24+
25+
*/
26+
27+
#include <stdint.h>
28+
#include <stddef.h>
29+
30+
// These are the 4 essential functions expected by gcc for a naked build.
31+
// The implementation of memcpy is in memory-s.s, and the rest are here.
32+
// The weak attribute is used to allow the user to override these functions
33+
// with their own implementation if they so desire. The memory-s.s implementation
34+
// is a simple byte copy, and is not optimized for speed. The file also contains
35+
// a faster but bigger implementation that can be used instead, called
36+
// __wrap_memcpy. The user can override memcpy with __wrap_memcpy to use it using
37+
// the -Wl,--wrap=memcpy switch to the linker using LDFLAGS. The same file also
38+
// contains a fast implementation of memset, called __wrap_memset, that can be
39+
// used in the same way.
40+
41+
void* memcpy(void* s1_, const void* s2_, size_t n);
42+
43+
__attribute__((weak)) void* memmove(void* s1_, const void* s2_, size_t n) {
44+
uint8_t* s1 = (uint8_t*)s1_;
45+
const uint8_t* s2 = (uint8_t*)s2_;
46+
size_t i;
47+
48+
uint8_t* e1 = s1 + n;
49+
const uint8_t* e2 = s2 + n;
50+
51+
if ((s1 <= s2) && (s2 <= e1) || ((s2 <= s1) && (s1 <= e2))) {
52+
if (s1 < s2) {
53+
for (i = 0; i < n; i++) *s1++ = *s2++;
54+
} else if (s1 > s2) {
55+
s1 += n;
56+
s2 += n;
57+
for (i = 0; i < n; i++) *--s1 = *--s2;
58+
}
59+
} else {
60+
return memcpy(s1_, s2_, n);
61+
}
62+
63+
return s1_;
64+
}
65+
66+
__attribute__((weak)) int memcmp(const void* s1_, const void* s2_, size_t n) {
67+
uint8_t* s1 = (uint8_t*)s1_;
68+
const uint8_t* s2 = (uint8_t*)s2_;
69+
size_t i;
70+
71+
for (i = 0; i < n; i++, s1++, s2++) {
72+
if (*s1 < *s2) {
73+
return -1;
74+
} else if (*s1 > *s2) {
75+
return 1;
76+
}
77+
}
78+
79+
return 0;
80+
}
81+
82+
__attribute__((weak)) void* memset(void* s_, int c, size_t n) {
83+
uint8_t* s = (uint8_t*)s_;
84+
size_t i;
85+
86+
for (i = 0; i < n; i++) *s++ = (uint8_t)c;
87+
88+
return s_;
89+
}
90+

0 commit comments

Comments
 (0)