diff --git a/src/r_compiler/llvmdrawers.h b/src/r_compiler/llvmdrawers.h index b2978cabf..abf9598e3 100644 --- a/src/r_compiler/llvmdrawers.h +++ b/src/r_compiler/llvmdrawers.h @@ -181,6 +181,85 @@ struct DrawSkyArgs } }; +struct TriVertex +{ + TriVertex() { } + TriVertex(float x, float y, float z, float w, float u, float v) : x(x), y(y), z(z), w(w) { varying[0] = u; varying[1] = v; } + + enum { NumVarying = 2 }; + float x, y, z, w; + float varying[NumVarying]; +}; + +struct TriMatrix +{ + static TriMatrix null(); + static TriMatrix identity(); + static TriMatrix translate(float x, float y, float z); + static TriMatrix scale(float x, float y, float z); + static TriMatrix rotate(float angle, float x, float y, float z); + static TriMatrix swapYZ(); + static TriMatrix perspective(float fovy, float aspect, float near, float far); + static TriMatrix frustum(float left, float right, float bottom, float top, float near, float far); + + static TriMatrix worldToView(); // Software renderer world to view space transform + static TriMatrix viewToClip(); // Software renderer shearing projection + + TriVertex operator*(TriVertex v) const; + TriMatrix operator*(const TriMatrix &m) const; + + float matrix[16]; +}; + +struct TriUniforms +{ + uint32_t light; + uint32_t subsectorDepth; + + uint16_t light_alpha; + uint16_t light_red; + uint16_t light_green; + uint16_t light_blue; + uint16_t fade_alpha; + uint16_t fade_red; + uint16_t fade_green; + uint16_t fade_blue; + uint16_t desaturate; + uint32_t flags; + enum Flags + { + simple_shade = 1, + nearest_filter = 2, + diminishing_lighting = 4 + }; + + TriMatrix objectToClip; +}; + +struct ScreenPolyTriangleDrawerArgs +{ + uint8_t *dest; + int pitch; + TriVertex *v1; + TriVertex *v2; + TriVertex *v3; + int clipleft; + int clipright; + int cliptop; + int clipbottom; + const uint8_t *texturePixels; + int textureWidth; + int textureHeight; + uint32_t solidcolor; + const TriUniforms *uniforms; + uint8_t *stencilValues; + uint32_t *stencilMasks; + int stencilPitch; + uint8_t stencilTestValue; + uint8_t stencilWriteValue; + uint32_t *subsectorGBuffer; +}; + class LLVMDrawers { public: diff --git a/src/r_poly_triangle.cpp b/src/r_poly_triangle.cpp index fb1874be2..181b011a4 100644 --- a/src/r_poly_triangle.cpp +++ b/src/r_poly_triangle.cpp @@ -48,12 +48,12 @@ void PolyTriangleDrawer::draw(const PolyDrawArgs &args, PolyDrawVariant variant) draw_arrays(args, variant, nullptr); } -void PolyTriangleDrawer::draw_arrays(const PolyDrawArgs &drawargs, PolyDrawVariant variant, DrawerThread *thread) +void PolyTriangleDrawer::draw_arrays(const PolyDrawArgs &drawargs, PolyDrawVariant variant, WorkerThreadData *thread) { if (drawargs.vcount < 3) return; - void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, DrawerThread *); + void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, WorkerThreadData *); switch (variant) { default: @@ -128,7 +128,7 @@ TriVertex PolyTriangleDrawer::shade_vertex(const TriUniforms &uniforms, TriVerte return uniforms.objectToClip * v; } -void PolyTriangleDrawer::draw_shaded_triangle(const TriVertex *vert, bool ccw, ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread, void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, DrawerThread *)) +void PolyTriangleDrawer::draw_shaded_triangle(const TriVertex *vert, bool ccw, ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread, void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, WorkerThreadData *)) { // Cull, clip and generate additional vertices as needed TriVertex clippedvert[max_additional_vertices]; @@ -288,7 +288,7 @@ void PolyTriangleDrawer::clipedge(const TriVertex *verts, TriVertex *clippedvert ///////////////////////////////////////////////////////////////////////////// -void ScreenPolyTriangleDrawer::draw(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::draw(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { uint8_t *dest = args->dest; int pitch = args->pitch; @@ -373,7 +373,7 @@ void ScreenPolyTriangleDrawer::draw(const ScreenPolyTriangleDrawerArgs *args, Dr for (int y = miny; y < maxy; y += q, dest += q * pitch) { // Is this row of blocks done by this thread? - if (thread && thread->skipped_by_thread(y / q)) continue; + if (thread && ((y / q) % thread->num_cores != thread->core)) continue; for (int x = minx; x < maxx; x += q) { @@ -523,7 +523,7 @@ void ScreenPolyTriangleDrawer::draw(const ScreenPolyTriangleDrawerArgs *args, Dr } } -void ScreenPolyTriangleDrawer::fill(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::fill(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { uint8_t *dest = args->dest; int pitch = args->pitch; @@ -594,7 +594,7 @@ void ScreenPolyTriangleDrawer::fill(const ScreenPolyTriangleDrawerArgs *args, Dr for (int y = miny; y < maxy; y += q, dest += q * pitch) { // Is this row of blocks done by this thread? - if (thread && thread->skipped_by_thread(y / q)) continue; + if (thread && ((y / q) % thread->num_cores != thread->core)) continue; for (int x = minx; x < maxx; x += q) { @@ -681,7 +681,7 @@ void ScreenPolyTriangleDrawer::fill(const ScreenPolyTriangleDrawerArgs *args, Dr } } -void ScreenPolyTriangleDrawer::stencil(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::stencil(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { const TriVertex &v1 = *args->v1; const TriVertex &v2 = *args->v2; @@ -753,7 +753,7 @@ void ScreenPolyTriangleDrawer::stencil(const ScreenPolyTriangleDrawerArgs *args, for (int y = miny; y < maxy; y += q) { // Is this row of blocks done by this thread? - if (thread && thread->skipped_by_thread(y / q)) continue; + if (thread && ((y / q) % thread->num_cores != thread->core)) continue; for (int x = minx; x < maxx; x += q) { @@ -833,7 +833,7 @@ void ScreenPolyTriangleDrawer::stencil(const ScreenPolyTriangleDrawerArgs *args, } } -void ScreenPolyTriangleDrawer::draw32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::draw32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { uint32_t *dest = (uint32_t *)args->dest; int pitch = args->pitch; @@ -926,7 +926,7 @@ void ScreenPolyTriangleDrawer::draw32(const ScreenPolyTriangleDrawerArgs *args, for (int y = miny; y < maxy; y += q, dest += q * pitch, subsectorGBuffer += q * pitch) { // Is this row of blocks done by this thread? - if (thread->skipped_by_thread(y / q)) continue; + if ((y / q) % thread->num_cores != thread->core) continue; for (int x = minx; x < maxx; x += q) { @@ -1145,7 +1145,7 @@ void ScreenPolyTriangleDrawer::draw32(const ScreenPolyTriangleDrawerArgs *args, } } -void ScreenPolyTriangleDrawer::drawsubsector32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::drawsubsector32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { uint32_t *dest = (uint32_t *)args->dest; int pitch = args->pitch; @@ -1234,7 +1234,7 @@ void ScreenPolyTriangleDrawer::drawsubsector32(const ScreenPolyTriangleDrawerArg for (int y = miny; y < maxy; y += q, dest += q * pitch, subsectorGBuffer += q * pitch) { // Is this row of blocks done by this thread? - if (thread->skipped_by_thread(y / q)) continue; + if ((y / q) % thread->num_cores != thread->core) continue; for (int x = minx; x < maxx; x += q) { @@ -1412,7 +1412,7 @@ void ScreenPolyTriangleDrawer::drawsubsector32(const ScreenPolyTriangleDrawerArg } } -void ScreenPolyTriangleDrawer::fill32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenPolyTriangleDrawer::fill32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread) { uint32_t *dest = (uint32_t *)args->dest; int pitch = args->pitch; @@ -1487,7 +1487,7 @@ void ScreenPolyTriangleDrawer::fill32(const ScreenPolyTriangleDrawerArgs *args, for (int y = miny; y < maxy; y += q, dest += q * pitch) { // Is this row of blocks done by this thread? - if (thread->skipped_by_thread(y / q)) continue; + if ((y / q) % thread->num_cores != thread->core) continue; for (int x = minx; x < maxx; x += q) { @@ -1603,7 +1603,14 @@ DrawPolyTrianglesCommand::DrawPolyTrianglesCommand(const PolyDrawArgs &args, Pol void DrawPolyTrianglesCommand::Execute(DrawerThread *thread) { - PolyTriangleDrawer::draw_arrays(args, variant, thread); + WorkerThreadData thread_data; + thread_data.core = thread->core; + thread_data.num_cores = thread->num_cores; + thread_data.pass_start_y = thread->pass_start_y; + thread_data.pass_end_y = thread->pass_end_y; + thread_data.temp = thread->dc_temp_rgba; + + PolyTriangleDrawer::draw_arrays(args, variant, &thread_data); } FString DrawPolyTrianglesCommand::DebugInfo() diff --git a/src/r_poly_triangle.h b/src/r_poly_triangle.h index 0861e7186..f0ffd1865 100644 --- a/src/r_poly_triangle.h +++ b/src/r_poly_triangle.h @@ -73,8 +73,8 @@ public: private: static TriVertex shade_vertex(const TriUniforms &uniforms, TriVertex v); - static void draw_arrays(const PolyDrawArgs &args, PolyDrawVariant variant, DrawerThread *thread); - static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread, void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, DrawerThread *)); + static void draw_arrays(const PolyDrawArgs &args, PolyDrawVariant variant, WorkerThreadData *thread); + static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread, void(*drawfunc)(const ScreenPolyTriangleDrawerArgs *, WorkerThreadData *)); static bool cullhalfspace(float clipdistance1, float clipdistance2, float &t1, float &t2); static void clipedge(const TriVertex *verts, TriVertex *clippedvert, int &numclipvert); @@ -225,41 +225,17 @@ private: std::vector masks; }; -struct ScreenPolyTriangleDrawerArgs -{ - uint8_t *dest; - int pitch; - TriVertex *v1; - TriVertex *v2; - TriVertex *v3; - int clipleft; - int clipright; - int cliptop; - int clipbottom; - const uint8_t *texturePixels; - int textureWidth; - int textureHeight; - uint32_t solidcolor; - const TriUniforms *uniforms; - uint8_t *stencilValues; - uint32_t *stencilMasks; - int stencilPitch; - uint8_t stencilTestValue; - uint8_t stencilWriteValue; - uint32_t *subsectorGBuffer; -}; - class ScreenPolyTriangleDrawer { public: - static void draw(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); - static void fill(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); + static void draw(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); + static void fill(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); - static void stencil(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); + static void stencil(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); - static void draw32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); - static void drawsubsector32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); - static void fill32(const ScreenPolyTriangleDrawerArgs *args, DrawerThread *thread); + static void draw32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); + static void drawsubsector32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); + static void fill32(const ScreenPolyTriangleDrawerArgs *args, WorkerThreadData *thread); private: static float gradx(float x0, float y0, float x1, float y1, float x2, float y2, float c0, float c1, float c2); diff --git a/src/r_triangle.cpp b/src/r_triangle.cpp index ff35cc7da..13a8ca292 100644 --- a/src/r_triangle.cpp +++ b/src/r_triangle.cpp @@ -75,7 +75,7 @@ void TriangleDrawer::queue_arrays(const TriUniforms &uniforms, const TriVertex * DrawerCommandQueue::QueueCommand(uniforms, vinput, vcount, mode, ccw, clipleft, clipright, clipdata, texturePixels, textureWidth, textureHeight, solidcolor); } -void TriangleDrawer::draw_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor, DrawerThread *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, DrawerThread *)) +void TriangleDrawer::draw_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *)) { if (vcount < 3) return; @@ -135,7 +135,7 @@ TriVertex TriangleDrawer::shade_vertex(const TriUniforms &uniforms, TriVertex v) return uniforms.objectToClip * v; } -void TriangleDrawer::draw_shaded_triangle(const TriVertex *vert, bool ccw, ScreenTriangleDrawerArgs *args, DrawerThread *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, DrawerThread *)) +void TriangleDrawer::draw_shaded_triangle(const TriVertex *vert, bool ccw, ScreenTriangleDrawerArgs *args, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *)) { // Cull, clip and generate additional vertices as needed TriVertex clippedvert[max_additional_vertices]; @@ -295,7 +295,7 @@ void TriangleDrawer::clipedge(const TriVertex *verts, TriVertex *clippedvert, in ///////////////////////////////////////////////////////////////////////////// -void ScreenTriangleDrawer::draw(const ScreenTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenTriangleDrawer::draw(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread) { uint8_t *dest = args->dest; int pitch = args->pitch; @@ -538,7 +538,7 @@ void ScreenTriangleDrawer::draw(const ScreenTriangleDrawerArgs *args, DrawerThre } } -void ScreenTriangleDrawer::fill(const ScreenTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenTriangleDrawer::fill(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread) { uint8_t *dest = args->dest; int pitch = args->pitch; @@ -706,7 +706,7 @@ void ScreenTriangleDrawer::fill(const ScreenTriangleDrawerArgs *args, DrawerThre } } -void ScreenTriangleDrawer::draw32(const ScreenTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenTriangleDrawer::draw32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread) { uint32_t *dest = (uint32_t *)args->dest; int pitch = args->pitch; @@ -873,7 +873,7 @@ void ScreenTriangleDrawer::draw32(const ScreenTriangleDrawerArgs *args, DrawerTh varyingStep[i] = (uint32_t)(step * 0x100000000LL); } - if (!thread->skipped_by_thread(y + iy)) + if ((y + iy) % thread->num_cores == thread->core) { for (int ix = x; ix < x + q; ix++) { @@ -920,7 +920,7 @@ void ScreenTriangleDrawer::draw32(const ScreenTriangleDrawerArgs *args, DrawerTh varyingStep[i] = (varyingTR[i] + varyingBR[i] * iy - varying[i]) * (1.0f / q); } - if (!thread->skipped_by_thread(y + iy)) + if ((y + iy) % thread->num_cores == thread->core) { for (int ix = x; ix < x + q; ix++) { @@ -967,7 +967,7 @@ void ScreenTriangleDrawer::draw32(const ScreenTriangleDrawerArgs *args, DrawerTh } } -void ScreenTriangleDrawer::fill32(const ScreenTriangleDrawerArgs *args, DrawerThread *thread) +void ScreenTriangleDrawer::fill32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread) { uint32_t *dest = (uint32_t *)args->dest; int pitch = args->pitch; @@ -1088,7 +1088,7 @@ void ScreenTriangleDrawer::fill32(const ScreenTriangleDrawerArgs *args, DrawerTh { for (int iy = 0; iy < q; iy++) { - if (!thread->skipped_by_thread(y + iy)) + if ((y + iy) % thread->num_cores == thread->core) { for (int ix = x; ix < x + q; ix++) { @@ -1111,7 +1111,7 @@ void ScreenTriangleDrawer::fill32(const ScreenTriangleDrawerArgs *args, DrawerTh int CX2 = CY2; int CX3 = CY3; - if (!thread->skipped_by_thread(y + iy)) + if ((y + iy) % thread->num_cores == thread->core) { for (int ix = x; ix < x + q; ix++) { @@ -1318,11 +1318,18 @@ void DrawTrianglesCommand::Execute(DrawerThread *thread) thread->triangle_clip_bottom[clipleft + i] = clipdata[cliplength + i]; } + WorkerThreadData thread_data; + thread_data.core = thread->core; + thread_data.num_cores = thread->num_cores; + thread_data.pass_start_y = thread->pass_start_y; + thread_data.pass_end_y = thread->pass_end_y; + thread_data.temp = thread->dc_temp_rgba; + TriangleDrawer::draw_arrays( uniforms, vinput, vcount, mode, ccw, clipleft, clipright, thread->triangle_clip_top, thread->triangle_clip_bottom, texturePixels, textureWidth, textureHeight, solidcolor, - thread, texturePixels ? ScreenTriangleDrawer::draw32 : ScreenTriangleDrawer::fill32); + &thread_data, texturePixels ? ScreenTriangleDrawer::draw32 : ScreenTriangleDrawer::fill32); } FString DrawTrianglesCommand::DebugInfo() diff --git a/src/r_triangle.h b/src/r_triangle.h index a3bdca5ed..6ec413d3f 100644 --- a/src/r_triangle.h +++ b/src/r_triangle.h @@ -26,65 +26,11 @@ #include "r_draw.h" #include "r_thread.h" +#include "r_compiler/llvmdrawers.h" class FTexture; struct ScreenTriangleDrawerArgs; -struct TriVertex -{ - TriVertex() { } - TriVertex(float x, float y, float z, float w, float u, float v) : x(x), y(y), z(z), w(w) { varying[0] = u; varying[1] = v; } - - enum { NumVarying = 2 }; - float x, y, z, w; - float varying[NumVarying]; -}; - -struct TriMatrix -{ - static TriMatrix null(); - static TriMatrix identity(); - static TriMatrix translate(float x, float y, float z); - static TriMatrix scale(float x, float y, float z); - static TriMatrix rotate(float angle, float x, float y, float z); - static TriMatrix swapYZ(); - static TriMatrix perspective(float fovy, float aspect, float near, float far); - static TriMatrix frustum(float left, float right, float bottom, float top, float near, float far); - - static TriMatrix worldToView(); // Software renderer world to view space transform - static TriMatrix viewToClip(); // Software renderer shearing projection - - TriVertex operator*(TriVertex v) const; - TriMatrix operator*(const TriMatrix &m) const; - - float matrix[16]; -}; - -struct TriUniforms -{ - uint32_t light; - uint32_t subsectorDepth; - - uint16_t light_alpha; - uint16_t light_red; - uint16_t light_green; - uint16_t light_blue; - uint16_t fade_alpha; - uint16_t fade_red; - uint16_t fade_green; - uint16_t fade_blue; - uint16_t desaturate; - uint32_t flags; - enum Flags - { - simple_shade = 1, - nearest_filter = 2, - diminishing_lighting = 4 - }; - - TriMatrix objectToClip; -}; - enum class TriangleDrawMode { Normal, @@ -100,8 +46,8 @@ public: private: static TriVertex shade_vertex(const TriUniforms &uniforms, TriVertex v); - static void draw_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor, DrawerThread *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, DrawerThread *)); - static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, ScreenTriangleDrawerArgs *args, DrawerThread *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, DrawerThread *)); + static void draw_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *)); + static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, ScreenTriangleDrawerArgs *args, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *)); static bool cullhalfspace(float clipdistance1, float clipdistance2, float &t1, float &t2); static void clipedge(const TriVertex *verts, TriVertex *clippedvert, int &numclipvert); @@ -133,11 +79,11 @@ struct ScreenTriangleDrawerArgs class ScreenTriangleDrawer { public: - static void draw(const ScreenTriangleDrawerArgs *args, DrawerThread *thread); - static void fill(const ScreenTriangleDrawerArgs *args, DrawerThread *thread); + static void draw(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread); + static void fill(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread); - static void draw32(const ScreenTriangleDrawerArgs *args, DrawerThread *thread); - static void fill32(const ScreenTriangleDrawerArgs *args, DrawerThread *thread); + static void draw32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread); + static void fill32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread); private: static float gradx(float x0, float y0, float x1, float y1, float x2, float y2, float c0, float c1, float c2);