1
0
mirror of https://github.com/TomHarte/CLK.git synced 2024-07-11 04:28:58 +00:00

Switching temporarily to an attempt to draw input runs as if RGB: shader compiles, fixed a race condition on out-of-bounds accesses for the source buffer.

This commit is contained in:
Thomas Harte 2016-04-17 15:51:28 -04:00
parent 104f44f27f
commit 6ff9ffba6c
4 changed files with 17 additions and 9 deletions

View File

@ -66,7 +66,7 @@ void Machine::setup_output(float aspect_ratio)
"texValue >>= 4 - (int(icoordinate.x * 8) & 4);" "texValue >>= 4 - (int(icoordinate.x * 8) & 4);"
"return vec3( uvec3(texValue) & uvec3(4u, 2u, 1u));" "return vec3( uvec3(texValue) & uvec3(4u, 2u, 1u));"
"}"); "}");
_crt->set_output_device(Outputs::CRT::Monitor); _crt->set_output_device(Outputs::CRT::Television);
// TODO: as implied below, I've introduced a clock's latency into the graphics pipeline somehow. Investigate. // TODO: as implied below, I've introduced a clock's latency into the graphics pipeline somehow. Investigate.
_crt->set_visible_area(_crt->get_rect_for_area(first_graphics_line - 3, 256, (first_graphics_cycle+1) * crt_cycles_multiplier, 80 * crt_cycles_multiplier, 4.0f / 3.0f)); _crt->set_visible_area(_crt->get_rect_for_area(first_graphics_line - 3, 256, (first_graphics_cycle+1) * crt_cycles_multiplier, 80 * crt_cycles_multiplier, 4.0f / 3.0f));

View File

@ -44,7 +44,7 @@ const int IntermediateBufferHeight = 2048;
// Some internal buffer sizes // Some internal buffer sizes
const GLsizeiptr OutputVertexBufferDataSize = 262080; // a multiple of 6 * OutputVertexSize const GLsizeiptr OutputVertexBufferDataSize = 262080; // a multiple of 6 * OutputVertexSize
const GLsizeiptr SourceVertexBufferDataSize = 87360; // a multiple of 2 * OutputVertexSize const GLsizeiptr SourceVertexBufferDataSize = 87360; // a multiple of 2 * SourceVertexSize
// Runs are divided discretely by vertical syncs in order to put a usable bounds on the uniform used to track // Runs are divided discretely by vertical syncs in order to put a usable bounds on the uniform used to track

View File

@ -53,7 +53,8 @@ OpenGLOutputBuilder::OpenGLOutputBuilder(unsigned int buffer_depth) :
_output_buffer_data(nullptr), _output_buffer_data(nullptr),
_source_buffer_data(nullptr), _source_buffer_data(nullptr),
_input_texture_data(nullptr), _input_texture_data(nullptr),
_output_buffer_data_pointer(0) _output_buffer_data_pointer(0),
_source_buffer_data_pointer(0)
{ {
_run_builders = new CRTRunBuilder *[NumberOfFields]; _run_builders = new CRTRunBuilder *[NumberOfFields];
for(int builder = 0; builder < NumberOfFields; builder++) for(int builder = 0; builder < NumberOfFields; builder++)
@ -211,7 +212,7 @@ void OpenGLOutputBuilder::draw_frame(unsigned int output_width, unsigned int out
// Ensure we're back on the output framebuffer, drawing from the output array buffer // Ensure we're back on the output framebuffer, drawing from the output array buffer
glBindFramebuffer(GL_FRAMEBUFFER, defaultFramebuffer); glBindFramebuffer(GL_FRAMEBUFFER, defaultFramebuffer);
// glBindBuffer(GL_ARRAY_BUFFER, output_array_buffer); glBindVertexArray(output_vertex_array);
// clear the buffer // clear the buffer
glClear(GL_COLOR_BUFFER_BIT); glClear(GL_COLOR_BUFFER_BIT);
@ -254,7 +255,6 @@ void OpenGLOutputBuilder::draw_frame(unsigned int output_width, unsigned int out
glBindBuffer(GL_ARRAY_BUFFER, source_array_buffer); glBindBuffer(GL_ARRAY_BUFFER, source_array_buffer);
_source_buffer_data = (uint8_t *)glMapBufferRange(GL_ARRAY_BUFFER, 0, SourceVertexBufferDataSize, GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT); _source_buffer_data = (uint8_t *)glMapBufferRange(GL_ARRAY_BUFFER, 0, SourceVertexBufferDataSize, GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
_source_buffer_data_pointer = 0;
_input_texture_data = (uint8_t *)glMapBufferRange(GL_PIXEL_UNPACK_BUFFER, 0, _input_texture_array_size, GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT); _input_texture_data = (uint8_t *)glMapBufferRange(GL_PIXEL_UNPACK_BUFFER, 0, _input_texture_array_size, GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
@ -310,14 +310,18 @@ char *OpenGLOutputBuilder::get_input_vertex_shader()
"in float phaseTime;" "in float phaseTime;"
"uniform float phaseCyclesPerTick;" "uniform float phaseCyclesPerTick;"
"uniform usampler2D texID;"
"uniform ivec2 outputTextureSize;"
"out vec2 inputPositionVarying;" "out vec2 inputPositionVarying;"
"out float phaseVarying;" "out float phaseVarying;"
"void main(void)" "void main(void)"
"{" "{"
"inputPositionVarying = vec2(inputPositionVarying.x / inputTextureSize.x, (inputPositionVarying.y + 0.5) / inputTextureSize.y);" "ivec2 textureSize = textureSize(texID, 0);"
"gl_Position = vec4(outputPosition.x * 2.0 / outputTextureSize - 1.0, outputPosition.y * 2.0 / outputTextureSize - 1.0, 0.0, 1.0);" "inputPositionVarying = vec2(inputPositionVarying.x / textureSize.x, (inputPositionVarying.y + 0.5) / textureSize.y);"
"gl_Position = vec4(outputPosition / outputTextureSize, 0.0, 1.0);"
"phaseVarying = (phaseCyclesPerTick * phaseTime + phaseAndAmplitude.x) * 2.0 * 3.141592654;" "phaseVarying = (phaseCyclesPerTick * phaseTime + phaseAndAmplitude.x) * 2.0 * 3.141592654;"
"}"); "}");
} }
@ -327,6 +331,7 @@ char *OpenGLOutputBuilder::get_input_fragment_shader()
const char *composite_shader = _composite_shader; const char *composite_shader = _composite_shader;
if(!composite_shader) if(!composite_shader)
{ {
composite_shader = _rgb_shader;
// TODO: synthesise an RGB -> (selected colour space) shader // TODO: synthesise an RGB -> (selected colour space) shader
} }
@ -344,7 +349,7 @@ char *OpenGLOutputBuilder::get_input_fragment_shader()
"void main(void)" "void main(void)"
"{" "{"
"fragColour = vec4(composite_sample(inputPositionVarying, phaseVarying), 0.0, 0.0, 1.0);" "fragColour = vec4(rgb_sample(texID, inputPositionVarying, inputPositionVarying), 1.0);" // composite
"}" "}"
, composite_shader); , composite_shader);
} }
@ -470,9 +475,12 @@ void OpenGLOutputBuilder::prepare_composite_input_shader()
GLint texIDUniform = composite_input_shader_program->get_uniform_location("texID"); GLint texIDUniform = composite_input_shader_program->get_uniform_location("texID");
GLint phaseCyclesPerTickUniform = composite_input_shader_program->get_uniform_location("phaseCyclesPerTick"); GLint phaseCyclesPerTickUniform = composite_input_shader_program->get_uniform_location("phaseCyclesPerTick");
GLint outputTextureSizeUniform = composite_input_shader_program->get_uniform_location("outputTextureSize");
composite_input_shader_program->bind();
glUniform1i(texIDUniform, first_supplied_buffer_texture_unit); glUniform1i(texIDUniform, first_supplied_buffer_texture_unit);
glUniform1f(phaseCyclesPerTickUniform, (float)_colour_cycle_numerator / (float)(_colour_cycle_denominator * _cycles_per_line)); glUniform1f(phaseCyclesPerTickUniform, (float)_colour_cycle_numerator / (float)(_colour_cycle_denominator * _cycles_per_line));
glUniform2i(outputTextureSizeUniform, IntermediateBufferWidth, IntermediateBufferHeight);
} }
free(vertex_shader); free(vertex_shader);
free(fragment_shader); free(fragment_shader);

View File

@ -112,7 +112,7 @@ class OpenGLOutputBuilder {
inline void complete_source_run() inline void complete_source_run()
{ {
_source_buffer_data_pointer += 2 * SourceVertexSize; _source_buffer_data_pointer = (_source_buffer_data_pointer + 2 * SourceVertexSize) % SourceVertexBufferDataSize;
_output_mutex->unlock(); _output_mutex->unlock();
} }