mirror of
https://github.com/hrydgard/ppsspp.git
synced 2026-10-01 14:58:14 +00:00
NotifyWriteFormattedFromMemory appends to videos_ unconditionally. A game blitting its decoded frame to the display buffer does that every displayed frame while it waits for the next one to decode, so the same two or three addresses come back over and over: Death Jr pushes 733 entries where there are two distinct buffers, Tekken 6 around 53,000 where there are three. IsVideo() walks that vector linearly on every texture. Refresh the matching entry instead of appending a new one - Death Jr now holds 2 entries and Tekken 6 holds 18, peak size 2 and 3. The other half is the two TODOs that were already sitting there. A video texture is new every frame by definition, so re-hashing it only confirms what the VIDEO flag already said, and the secondary cache has nothing to offer a frame that will never recur. Skip both, and with them the secondary lookup that would otherwise key off a hash we no longer compute. Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>
181 lines
4.5 KiB
C++
181 lines
4.5 KiB
C++
// Copyright (c) 2015- PPSSPP Project.
|
|
|
|
// This program is free software: you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License as published by
|
|
// the Free Software Foundation, version 2.0 or later versions.
|
|
|
|
// This program is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
// GNU General Public License 2.0 for more details.
|
|
|
|
// A copy of the GPL 2.0 should have been included with the program.
|
|
// If not, see http://www.gnu.org/licenses/
|
|
|
|
// Official git repository and contact information can be found at
|
|
// https://github.com/hrydgard/ppsspp and http://www.ppsspp.org/.
|
|
|
|
|
|
#pragma once
|
|
|
|
#include <cstring>
|
|
#include <cstdint>
|
|
|
|
enum GPUCore : int;
|
|
|
|
class GPUCommon;
|
|
class GPUCommon;
|
|
class GraphicsContext;
|
|
|
|
// PSP rasterization has two outputs, color and depth. Stencil is packed
|
|
// into the alpha channel of color (if exists), so possibly RASTER_COLOR
|
|
// should be named RASTER_COLOR_STENCIL but it gets kinda hard to read.
|
|
enum RasterChannel : uint8_t {
|
|
RASTER_COLOR = 0,
|
|
RASTER_DEPTH = 1,
|
|
};
|
|
|
|
enum SkipDrawReasonFlags {
|
|
SKIPDRAW_SKIPFRAME = 1,
|
|
SKIPDRAW_NON_DISPLAYED_FB = 2, // Skip drawing to FBO:s that have not been displayed.
|
|
SKIPDRAW_BAD_FB_TEXTURE = 4,
|
|
SKIPDRAW_WINDOW_MINIMIZED = 8, // Don't draw when the host window is minimized.
|
|
};
|
|
|
|
enum class ShaderDepalMode {
|
|
OFF = 0,
|
|
NORMAL = 1,
|
|
SMOOTHED = 2,
|
|
CLUT8_8888 = 3, // Read 8888 framebuffer as 8-bit CLUT.
|
|
};
|
|
|
|
// Global GPU-related utility functions.
|
|
// Nothing directly Ge-related in here.
|
|
|
|
// PSP uses a curious 24-bit float - it's the top 24 bits of a regular IEEE754 32-bit float.
|
|
// This is used for light positions, transform matrices, you name it.
|
|
inline float getFloat24(unsigned int data) {
|
|
data <<= 8;
|
|
float f;
|
|
memcpy(&f, &data, 4);
|
|
return f;
|
|
}
|
|
|
|
// in case we ever want to generate PSP display lists...
|
|
inline unsigned int toFloat24(float f) {
|
|
unsigned int i;
|
|
memcpy(&i, &f, 4);
|
|
return i >> 8;
|
|
}
|
|
|
|
// TODO: Not completely sure about the exact mechanics here, or where we need to use this.
|
|
// Useful to experiment with.
|
|
inline float roundToFloat24(float f) {
|
|
unsigned int i;
|
|
memcpy(&i, &f, 4);
|
|
i &= 0xFFFFFF00;
|
|
i += 0x80; // TODO: Subtract for negative numbers?
|
|
float retval;
|
|
memcpy(&retval, &i, 4);
|
|
return retval;
|
|
}
|
|
|
|
inline float truncateToFloat24(float f) {
|
|
unsigned int i;
|
|
memcpy(&i, &f, 4);
|
|
i &= 0xFFFFFF00;
|
|
float retval;
|
|
memcpy(&retval, &i, 4);
|
|
return retval;
|
|
}
|
|
|
|
// TODO: Possibly use macros to disable expensive parts of stats tracking in release builds.
|
|
struct GPUStatsPerFrame {
|
|
int numEnqueue;
|
|
int numUpdateStall;
|
|
int numDrawSyncs;
|
|
int numListSyncs;
|
|
int numGEInterrupts;
|
|
int numDrawCalls;
|
|
int numVertexDecodes;
|
|
int numCulledDraws;
|
|
int numFlushes;
|
|
int numSoftTransformedDraws;
|
|
int numSoftClippedTriangles;
|
|
int numBBOXJumps;
|
|
int numVertsSubmitted;
|
|
int numVertsDecoded;
|
|
int numVertsDrawn;
|
|
int numTextureInvalidations;
|
|
int numTexturesChanged;
|
|
int numTextureInvalidationsByFramebuffer;
|
|
int numTexturesHashed;
|
|
int numTextureDataBytesHashed;
|
|
int numTexturesDecoded;
|
|
int numVideoTextures;
|
|
int numFramebufferEvaluations;
|
|
int numFBOsCreated;
|
|
int numBlockingReadbacks;
|
|
int numReadbacks;
|
|
int numUploads;
|
|
int numCachedUploads;
|
|
int numDepal;
|
|
int numClears;
|
|
int numDepthCopies;
|
|
int numReinterpretCopies;
|
|
int numColorCopies;
|
|
int numCopiesForShaderBlend;
|
|
int numCopiesForSelfTex;
|
|
int numBlockTransfers;
|
|
int numReplacerTrackedTex;
|
|
int numCachedReplacedTextures;
|
|
int numClutTextures;
|
|
double msProcessingDisplayLists;
|
|
double msPrepareDepth;
|
|
double msCullDepth;
|
|
double msRasterizeDepth;
|
|
double msRasterTimeAvailable;
|
|
int vertexGPUCycles;
|
|
int otherGPUCycles;
|
|
int numDepthRasterPrims;
|
|
int numDepthRasterEarlySize;
|
|
int numDepthRasterNoPixels;
|
|
int numDepthRasterTooSmall;
|
|
int numDepthRasterZCulled;
|
|
int numDepthEarlyBoxCulled;
|
|
};
|
|
|
|
struct GPUStatsTotals {
|
|
// Flip count. Doesn't really belong here.
|
|
int numFlips;
|
|
};
|
|
|
|
// The ToString function lives in GPUCommonHW.cpp.
|
|
struct GPUStatistics {
|
|
void Reset() {
|
|
ResetFrame();
|
|
totals = {};
|
|
}
|
|
|
|
void ResetFrame() {
|
|
perFrame = {};
|
|
}
|
|
|
|
// Flip count. Doesn't really belong here.
|
|
GPUStatsPerFrame perFrame;
|
|
GPUStatsTotals totals;
|
|
};
|
|
|
|
extern GPUStatistics gpuStats;
|
|
extern GPUCommon *gpu;
|
|
extern GPUCommon *gpu;
|
|
|
|
namespace Draw {
|
|
class DrawContext;
|
|
}
|
|
|
|
bool GPU_Init(GPUCore gpuCore, GraphicsContext *ctx, Draw::DrawContext *draw);
|
|
void GPU_Shutdown();
|
|
|
|
const char *RasterChannelToString(RasterChannel channel);
|