diff --git a/src/mesa/main/fbobject.c b/src/mesa/main/fbobject.c index fef538a8c14..2d242135a42 100644 --- a/src/mesa/main/fbobject.c +++ b/src/mesa/main/fbobject.c @@ -4290,6 +4290,25 @@ frame_buffer_texture(GLuint framebuffer, GLenum target, } if (!no_error) { + /* EXT_multisampled_render_to_texture: + + If samples is greater than the + value of MAX_SAMPLES_EXT, then the error INVALID_VALUE is generated. + An INVALID_OPERATION error is generated if samples is greater than + the maximum number of samples supported for target and its + internalformat. If samples is zero, then TEXTURE_SAMPLES_EXT is set + to zero, and FramebufferTexture2DMultisampleEXT behaves like + FramebufferTexture2D. + */ + if (samples > ctx->Const.MaxSamples) { + _mesa_error(ctx, GL_INVALID_VALUE, "%s(invalid sample count %u)", + func, samples); + } + if (samples > ctx->Const.MaxFramebufferSamples) { + _mesa_error(ctx, GL_INVALID_OPERATION, "%s(invalid sample count %u)", + func, samples); + } + if (!check_layered) { if (!check_texture_target(ctx, texObj->Target, func)) return; diff --git a/src/mesa/main/renderbuffer.c b/src/mesa/main/renderbuffer.c index af15081fe1c..3b11c5c3e07 100644 --- a/src/mesa/main/renderbuffer.c +++ b/src/mesa/main/renderbuffer.c @@ -630,6 +630,27 @@ _mesa_update_renderbuffer_surface(struct gl_context *ctx, last_layer); } + int nr_samples = rb->rtt_nr_samples; + if (rb->rtt_nr_samples && rb->rtt_nr_samples != resource->nr_samples) { + assert(!resource->nr_samples); + /* EXT_multisampled_render_to_texture: + + Otherwise samples represents a request for a desired minimum number + of samples. Since different implementations may support different + sample counts for multisampled rendering, the actual number of samples + allocated for the image is implementation-dependent. However, the + resulting value for TEXTURE_SAMPLES_EXT is guaranteed to be greater + than or equal to samples and no more than the next larger sample count + supported by the implementation. + */ + for (unsigned i = rb->rtt_nr_samples + 1; i <= ctx->Const.MaxFramebufferSamples; i++) { + if (!ctx->st->screen->is_format_supported(ctx->st->screen, format, resource->target, i, i, resource->bind)) + continue; + nr_samples = i; + break; + } + } + struct pipe_surface **psurf = enable_srgb ? &rb->surface_srgb : &rb->surface_linear; struct pipe_surface *surf = *psurf; @@ -641,7 +662,7 @@ _mesa_update_renderbuffer_surface(struct gl_context *ctx, surf->texture != resource || surf->width != rtt_width || surf->height != rtt_height || - surf->nr_samples != rb->rtt_nr_samples || + surf->nr_samples != nr_samples || surf->u.tex.level != level || surf->u.tex.first_layer != first_layer || surf->u.tex.last_layer != last_layer) { @@ -649,7 +670,7 @@ _mesa_update_renderbuffer_surface(struct gl_context *ctx, struct pipe_surface surf_tmpl; memset(&surf_tmpl, 0, sizeof(surf_tmpl)); surf_tmpl.format = format; - surf_tmpl.nr_samples = rb->rtt_nr_samples; + surf_tmpl.nr_samples = nr_samples; surf_tmpl.u.tex.level = level; surf_tmpl.u.tex.first_layer = first_layer; surf_tmpl.u.tex.last_layer = last_layer;