1c1f859d4Smrg/*
2c1f859d4Smrg * Mesa 3-D graphics library
3c1f859d4Smrg *
4c1f859d4Smrg * Copyright (C) 1999-2007  Brian Paul   All Rights Reserved.
5c1f859d4Smrg *
6c1f859d4Smrg * Permission is hereby granted, free of charge, to any person obtaining a
7c1f859d4Smrg * copy of this software and associated documentation files (the "Software"),
8c1f859d4Smrg * to deal in the Software without restriction, including without limitation
9c1f859d4Smrg * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10c1f859d4Smrg * and/or sell copies of the Software, and to permit persons to whom the
11c1f859d4Smrg * Software is furnished to do so, subject to the following conditions:
12c1f859d4Smrg *
13c1f859d4Smrg * The above copyright notice and this permission notice shall be included
14c1f859d4Smrg * in all copies or substantial portions of the Software.
15c1f859d4Smrg *
16c1f859d4Smrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
17c1f859d4Smrg * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18c1f859d4Smrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19af69d88dSmrg * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
20af69d88dSmrg * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
21af69d88dSmrg * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
22af69d88dSmrg * OTHER DEALINGS IN THE SOFTWARE.
23c1f859d4Smrg */
24c1f859d4Smrg
25c1f859d4Smrg
26c1f859d4Smrg/**
27c1f859d4Smrg * \file clear.c
28c1f859d4Smrg * glClearColor, glClearIndex, glClear() functions.
29c1f859d4Smrg */
30c1f859d4Smrg
31c1f859d4Smrg
32c1f859d4Smrg
337ec681f3Smrg#include "glformats.h"
34c1f859d4Smrg#include "glheader.h"
35c1f859d4Smrg#include "clear.h"
36c1f859d4Smrg#include "context.h"
37cdc920a0Smrg#include "enums.h"
3801e04c3fSmrg#include "fbobject.h"
3901e04c3fSmrg#include "get.h"
403464ebd5Sriastradh#include "macros.h"
413464ebd5Sriastradh#include "mtypes.h"
42c1f859d4Smrg#include "state.h"
43c1f859d4Smrg
44c1f859d4Smrg
45c1f859d4Smrg
46c1f859d4Smrgvoid GLAPIENTRY
47c1f859d4Smrg_mesa_ClearIndex( GLfloat c )
48c1f859d4Smrg{
49c1f859d4Smrg   GET_CURRENT_CONTEXT(ctx);
50c1f859d4Smrg
517ec681f3Smrg   ctx->PopAttribState |= GL_COLOR_BUFFER_BIT;
52c1f859d4Smrg   ctx->Color.ClearIndex = (GLuint) c;
53c1f859d4Smrg}
54c1f859d4Smrg
55c1f859d4Smrg
56c1f859d4Smrg/**
57c1f859d4Smrg * Specify the clear values for the color buffers.
58c1f859d4Smrg *
59c1f859d4Smrg * \param red red color component.
60c1f859d4Smrg * \param green green color component.
61c1f859d4Smrg * \param blue blue color component.
62c1f859d4Smrg * \param alpha alpha component.
63c1f859d4Smrg *
64c1f859d4Smrg * \sa glClearColor().
65c1f859d4Smrg */
66c1f859d4Smrgvoid GLAPIENTRY
67c1f859d4Smrg_mesa_ClearColor( GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha )
68c1f859d4Smrg{
69c1f859d4Smrg   GET_CURRENT_CONTEXT(ctx);
703464ebd5Sriastradh
717ec681f3Smrg   ctx->PopAttribState |= GL_COLOR_BUFFER_BIT;
72af69d88dSmrg   ctx->Color.ClearColor.f[0] = red;
73af69d88dSmrg   ctx->Color.ClearColor.f[1] = green;
74af69d88dSmrg   ctx->Color.ClearColor.f[2] = blue;
75af69d88dSmrg   ctx->Color.ClearColor.f[3] = alpha;
76c1f859d4Smrg}
77c1f859d4Smrg
78c1f859d4Smrg
793464ebd5Sriastradh/**
803464ebd5Sriastradh * GL_EXT_texture_integer
813464ebd5Sriastradh */
823464ebd5Sriastradhvoid GLAPIENTRY
833464ebd5Sriastradh_mesa_ClearColorIiEXT(GLint r, GLint g, GLint b, GLint a)
843464ebd5Sriastradh{
853464ebd5Sriastradh   GET_CURRENT_CONTEXT(ctx);
863464ebd5Sriastradh
877ec681f3Smrg   ctx->PopAttribState |= GL_COLOR_BUFFER_BIT;
88af69d88dSmrg   ctx->Color.ClearColor.i[0] = r;
89af69d88dSmrg   ctx->Color.ClearColor.i[1] = g;
90af69d88dSmrg   ctx->Color.ClearColor.i[2] = b;
91af69d88dSmrg   ctx->Color.ClearColor.i[3] = a;
923464ebd5Sriastradh}
933464ebd5Sriastradh
943464ebd5Sriastradh
953464ebd5Sriastradh/**
963464ebd5Sriastradh * GL_EXT_texture_integer
973464ebd5Sriastradh */
983464ebd5Sriastradhvoid GLAPIENTRY
993464ebd5Sriastradh_mesa_ClearColorIuiEXT(GLuint r, GLuint g, GLuint b, GLuint a)
1003464ebd5Sriastradh{
1013464ebd5Sriastradh   GET_CURRENT_CONTEXT(ctx);
1023464ebd5Sriastradh
1037ec681f3Smrg   ctx->PopAttribState |= GL_COLOR_BUFFER_BIT;
104af69d88dSmrg   ctx->Color.ClearColor.ui[0] = r;
105af69d88dSmrg   ctx->Color.ClearColor.ui[1] = g;
106af69d88dSmrg   ctx->Color.ClearColor.ui[2] = b;
107af69d88dSmrg   ctx->Color.ClearColor.ui[3] = a;
108af69d88dSmrg}
1093464ebd5Sriastradh
1103464ebd5Sriastradh
111af69d88dSmrg/**
112af69d88dSmrg * Returns true if color writes are enabled for the given color attachment.
113af69d88dSmrg *
114af69d88dSmrg * Beyond checking ColorMask, this uses _mesa_format_has_color_component to
115af69d88dSmrg * ignore components that don't actually exist in the format (such as X in
116af69d88dSmrg * XRGB).
117af69d88dSmrg */
118af69d88dSmrgstatic bool
119af69d88dSmrgcolor_buffer_writes_enabled(const struct gl_context *ctx, unsigned idx)
120af69d88dSmrg{
121af69d88dSmrg   struct gl_renderbuffer *rb = ctx->DrawBuffer->_ColorDrawBuffers[idx];
122af69d88dSmrg   GLuint c;
123af69d88dSmrg
124af69d88dSmrg   if (rb) {
125af69d88dSmrg      for (c = 0; c < 4; c++) {
12601e04c3fSmrg         if (GET_COLORMASK_BIT(ctx->Color.ColorMask, idx, c) &&
12701e04c3fSmrg             _mesa_format_has_color_component(rb->Format, c)) {
12801e04c3fSmrg            return true;
12901e04c3fSmrg         }
130af69d88dSmrg      }
1313464ebd5Sriastradh   }
132af69d88dSmrg
13301e04c3fSmrg   return false;
1343464ebd5Sriastradh}
1353464ebd5Sriastradh
1363464ebd5Sriastradh
137c1f859d4Smrg/**
138c1f859d4Smrg * Clear buffers.
13901e04c3fSmrg *
140c1f859d4Smrg * \param mask bit-mask indicating the buffers to be cleared.
141c1f859d4Smrg *
14201e04c3fSmrg * Flushes the vertices and verifies the parameter.
14301e04c3fSmrg * If __struct gl_contextRec::NewState is set then calls _mesa_update_state()
14401e04c3fSmrg * to update gl_frame_buffer::_Xmin, etc.  If the rasterization mode is set to
14501e04c3fSmrg * GL_RENDER then requests the driver to clear the buffers, via the
14601e04c3fSmrg * dd_function_table::Clear callback.
14701e04c3fSmrg */
14801e04c3fSmrgstatic ALWAYS_INLINE void
14901e04c3fSmrgclear(struct gl_context *ctx, GLbitfield mask, bool no_error)
150c1f859d4Smrg{
1517ec681f3Smrg   FLUSH_VERTICES(ctx, 0, 0);
152c1f859d4Smrg
15301e04c3fSmrg   if (!no_error) {
15401e04c3fSmrg      if (mask & ~(GL_COLOR_BUFFER_BIT |
15501e04c3fSmrg                   GL_DEPTH_BUFFER_BIT |
15601e04c3fSmrg                   GL_STENCIL_BUFFER_BIT |
15701e04c3fSmrg                   GL_ACCUM_BUFFER_BIT)) {
15801e04c3fSmrg         _mesa_error( ctx, GL_INVALID_VALUE, "glClear(0x%x)", mask);
15901e04c3fSmrg         return;
16001e04c3fSmrg      }
161c1f859d4Smrg
16201e04c3fSmrg      /* Accumulation buffers were removed in core contexts, and they never
16301e04c3fSmrg       * existed in OpenGL ES.
16401e04c3fSmrg       */
16501e04c3fSmrg      if ((mask & GL_ACCUM_BUFFER_BIT) != 0
16601e04c3fSmrg          && (ctx->API == API_OPENGL_CORE || _mesa_is_gles(ctx))) {
16701e04c3fSmrg         _mesa_error( ctx, GL_INVALID_VALUE, "glClear(GL_ACCUM_BUFFER_BIT)");
16801e04c3fSmrg         return;
16901e04c3fSmrg      }
170af69d88dSmrg   }
171af69d88dSmrg
172c1f859d4Smrg   if (ctx->NewState) {
173c1f859d4Smrg      _mesa_update_state( ctx );	/* update _Xmin, etc */
174c1f859d4Smrg   }
175c1f859d4Smrg
17601e04c3fSmrg   if (!no_error && ctx->DrawBuffer->_Status != GL_FRAMEBUFFER_COMPLETE_EXT) {
177c1f859d4Smrg      _mesa_error(ctx, GL_INVALID_FRAMEBUFFER_OPERATION_EXT,
178c1f859d4Smrg                  "glClear(incomplete framebuffer)");
179c1f859d4Smrg      return;
180c1f859d4Smrg   }
181c1f859d4Smrg
182af69d88dSmrg   if (ctx->RasterDiscard)
183c1f859d4Smrg      return;
184c1f859d4Smrg
185c1f859d4Smrg   if (ctx->RenderMode == GL_RENDER) {
186c1f859d4Smrg      GLbitfield bufferMask;
187c1f859d4Smrg
188c1f859d4Smrg      /* don't clear depth buffer if depth writing disabled */
189c1f859d4Smrg      if (!ctx->Depth.Mask)
190c1f859d4Smrg         mask &= ~GL_DEPTH_BUFFER_BIT;
191c1f859d4Smrg
192c1f859d4Smrg      /* Build the bitmask to send to device driver's Clear function.
193c1f859d4Smrg       * Note that the GL_COLOR_BUFFER_BIT flag will expand to 0, 1, 2 or 4
194c1f859d4Smrg       * of the BUFFER_BIT_FRONT/BACK_LEFT/RIGHT flags, or one of the
195c1f859d4Smrg       * BUFFER_BIT_COLORn flags.
196c1f859d4Smrg       */
197c1f859d4Smrg      bufferMask = 0;
198c1f859d4Smrg      if (mask & GL_COLOR_BUFFER_BIT) {
199c1f859d4Smrg         GLuint i;
200c1f859d4Smrg         for (i = 0; i < ctx->DrawBuffer->_NumColorDrawBuffers; i++) {
20101e04c3fSmrg            gl_buffer_index buf = ctx->DrawBuffer->_ColorDrawBufferIndexes[i];
202af69d88dSmrg
20301e04c3fSmrg            if (buf != BUFFER_NONE && color_buffer_writes_enabled(ctx, i)) {
204af69d88dSmrg               bufferMask |= 1 << buf;
205af69d88dSmrg            }
206c1f859d4Smrg         }
207c1f859d4Smrg      }
208c1f859d4Smrg
209c1f859d4Smrg      if ((mask & GL_DEPTH_BUFFER_BIT)
2107ec681f3Smrg          && ctx->DrawBuffer->Visual.depthBits > 0) {
211c1f859d4Smrg         bufferMask |= BUFFER_BIT_DEPTH;
212c1f859d4Smrg      }
213c1f859d4Smrg
214c1f859d4Smrg      if ((mask & GL_STENCIL_BUFFER_BIT)
2157ec681f3Smrg          && ctx->DrawBuffer->Visual.stencilBits > 0) {
216c1f859d4Smrg         bufferMask |= BUFFER_BIT_STENCIL;
217c1f859d4Smrg      }
218c1f859d4Smrg
219c1f859d4Smrg      if ((mask & GL_ACCUM_BUFFER_BIT)
2207ec681f3Smrg          && ctx->DrawBuffer->Visual.accumRedBits > 0) {
221c1f859d4Smrg         bufferMask |= BUFFER_BIT_ACCUM;
222c1f859d4Smrg      }
223c1f859d4Smrg
22401e04c3fSmrg      assert(ctx->Driver.Clear);
225c1f859d4Smrg      ctx->Driver.Clear(ctx, bufferMask);
226c1f859d4Smrg   }
227c1f859d4Smrg}
228cdc920a0Smrg
229cdc920a0Smrg
23001e04c3fSmrgvoid GLAPIENTRY
23101e04c3fSmrg_mesa_Clear_no_error(GLbitfield mask)
23201e04c3fSmrg{
23301e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
23401e04c3fSmrg   clear(ctx, mask, true);
23501e04c3fSmrg}
23601e04c3fSmrg
23701e04c3fSmrg
23801e04c3fSmrgvoid GLAPIENTRY
23901e04c3fSmrg_mesa_Clear(GLbitfield mask)
24001e04c3fSmrg{
24101e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
24201e04c3fSmrg
24301e04c3fSmrg   if (MESA_VERBOSE & VERBOSE_API)
24401e04c3fSmrg      _mesa_debug(ctx, "glClear 0x%x\n", mask);
24501e04c3fSmrg
24601e04c3fSmrg   clear(ctx, mask, false);
24701e04c3fSmrg}
24801e04c3fSmrg
24901e04c3fSmrg
250cdc920a0Smrg/** Returned by make_color_buffer_mask() for errors */
25101e04c3fSmrg#define INVALID_MASK ~0x0U
252cdc920a0Smrg
253cdc920a0Smrg
254cdc920a0Smrg/**
255cdc920a0Smrg * Convert the glClearBuffer 'drawbuffer' parameter into a bitmask of
256cdc920a0Smrg * BUFFER_BIT_x values.
257cdc920a0Smrg * Return INVALID_MASK if the drawbuffer value is invalid.
258cdc920a0Smrg */
259cdc920a0Smrgstatic GLbitfield
2603464ebd5Sriastradhmake_color_buffer_mask(struct gl_context *ctx, GLint drawbuffer)
261cdc920a0Smrg{
262cdc920a0Smrg   const struct gl_renderbuffer_attachment *att = ctx->DrawBuffer->Attachment;
263cdc920a0Smrg   GLbitfield mask = 0x0;
264cdc920a0Smrg
265af69d88dSmrg   /* From the GL 4.0 specification:
266af69d88dSmrg    *	If buffer is COLOR, a particular draw buffer DRAW_BUFFERi is
267af69d88dSmrg    *	specified by passing i as the parameter drawbuffer, and value
268af69d88dSmrg    *	points to a four-element vector specifying the R, G, B, and A
269af69d88dSmrg    *	color to clear that draw buffer to. If the draw buffer is one
270af69d88dSmrg    *	of FRONT, BACK, LEFT, RIGHT, or FRONT_AND_BACK, identifying
271af69d88dSmrg    *	multiple buffers, each selected buffer is cleared to the same
272af69d88dSmrg    *	value.
273af69d88dSmrg    *
274af69d88dSmrg    * Note that "drawbuffer" and "draw buffer" have different meaning.
275af69d88dSmrg    * "drawbuffer" specifies DRAW_BUFFERi, while "draw buffer" is what's
276af69d88dSmrg    * assigned to DRAW_BUFFERi. It could be COLOR_ATTACHMENT0, FRONT, BACK,
277af69d88dSmrg    * etc.
278af69d88dSmrg    */
279af69d88dSmrg   if (drawbuffer < 0 || drawbuffer >= (GLint)ctx->Const.MaxDrawBuffers) {
280af69d88dSmrg      return INVALID_MASK;
281af69d88dSmrg   }
282af69d88dSmrg
283af69d88dSmrg   switch (ctx->DrawBuffer->ColorDrawBuffer[drawbuffer]) {
284cdc920a0Smrg   case GL_FRONT:
285cdc920a0Smrg      if (att[BUFFER_FRONT_LEFT].Renderbuffer)
286cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_LEFT;
287cdc920a0Smrg      if (att[BUFFER_FRONT_RIGHT].Renderbuffer)
288cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_RIGHT;
289cdc920a0Smrg      break;
290cdc920a0Smrg   case GL_BACK:
29101e04c3fSmrg      /* For GLES contexts with a single buffered configuration, we actually
29201e04c3fSmrg       * only have a front renderbuffer, so any clear calls to GL_BACK should
29301e04c3fSmrg       * affect that buffer. See draw_buffer_enum_to_bitmask for details.
29401e04c3fSmrg       */
29501e04c3fSmrg      if (_mesa_is_gles(ctx))
29601e04c3fSmrg         if (!ctx->DrawBuffer->Visual.doubleBufferMode)
29701e04c3fSmrg            if (att[BUFFER_FRONT_LEFT].Renderbuffer)
29801e04c3fSmrg               mask |= BUFFER_BIT_FRONT_LEFT;
299cdc920a0Smrg      if (att[BUFFER_BACK_LEFT].Renderbuffer)
300cdc920a0Smrg         mask |= BUFFER_BIT_BACK_LEFT;
301cdc920a0Smrg      if (att[BUFFER_BACK_RIGHT].Renderbuffer)
302cdc920a0Smrg         mask |= BUFFER_BIT_BACK_RIGHT;
303cdc920a0Smrg      break;
304cdc920a0Smrg   case GL_LEFT:
305cdc920a0Smrg      if (att[BUFFER_FRONT_LEFT].Renderbuffer)
306cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_LEFT;
307cdc920a0Smrg      if (att[BUFFER_BACK_LEFT].Renderbuffer)
308cdc920a0Smrg         mask |= BUFFER_BIT_BACK_LEFT;
309cdc920a0Smrg      break;
310cdc920a0Smrg   case GL_RIGHT:
311cdc920a0Smrg      if (att[BUFFER_FRONT_RIGHT].Renderbuffer)
312cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_RIGHT;
313cdc920a0Smrg      if (att[BUFFER_BACK_RIGHT].Renderbuffer)
314cdc920a0Smrg         mask |= BUFFER_BIT_BACK_RIGHT;
315cdc920a0Smrg      break;
316cdc920a0Smrg   case GL_FRONT_AND_BACK:
317cdc920a0Smrg      if (att[BUFFER_FRONT_LEFT].Renderbuffer)
318cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_LEFT;
319cdc920a0Smrg      if (att[BUFFER_BACK_LEFT].Renderbuffer)
320cdc920a0Smrg         mask |= BUFFER_BIT_BACK_LEFT;
321cdc920a0Smrg      if (att[BUFFER_FRONT_RIGHT].Renderbuffer)
322cdc920a0Smrg         mask |= BUFFER_BIT_FRONT_RIGHT;
323cdc920a0Smrg      if (att[BUFFER_BACK_RIGHT].Renderbuffer)
324cdc920a0Smrg         mask |= BUFFER_BIT_BACK_RIGHT;
325cdc920a0Smrg      break;
326cdc920a0Smrg   default:
327af69d88dSmrg      {
32801e04c3fSmrg         gl_buffer_index buf =
32901e04c3fSmrg            ctx->DrawBuffer->_ColorDrawBufferIndexes[drawbuffer];
330af69d88dSmrg
33101e04c3fSmrg         if (buf != BUFFER_NONE && att[buf].Renderbuffer) {
332af69d88dSmrg            mask |= 1 << buf;
333af69d88dSmrg         }
334cdc920a0Smrg      }
335cdc920a0Smrg   }
336cdc920a0Smrg
337cdc920a0Smrg   return mask;
338cdc920a0Smrg}
339cdc920a0Smrg
340cdc920a0Smrg
341cdc920a0Smrg
342cdc920a0Smrg/**
343cdc920a0Smrg * New in GL 3.0
344cdc920a0Smrg * Clear signed integer color buffer or stencil buffer (not depth).
345cdc920a0Smrg */
34601e04c3fSmrgstatic ALWAYS_INLINE void
34701e04c3fSmrgclear_bufferiv(struct gl_context *ctx, GLenum buffer, GLint drawbuffer,
34801e04c3fSmrg               const GLint *value, bool no_error)
349cdc920a0Smrg{
3507ec681f3Smrg   FLUSH_VERTICES(ctx, 0, 0);
351cdc920a0Smrg
352cdc920a0Smrg   if (ctx->NewState) {
353cdc920a0Smrg      _mesa_update_state( ctx );
354cdc920a0Smrg   }
355cdc920a0Smrg
3567ec681f3Smrg   if (!no_error && ctx->DrawBuffer->_Status != GL_FRAMEBUFFER_COMPLETE_EXT) {
3577ec681f3Smrg      _mesa_error(ctx, GL_INVALID_FRAMEBUFFER_OPERATION_EXT,
3587ec681f3Smrg                  "glClearBufferiv(incomplete framebuffer)");
3597ec681f3Smrg      return;
3607ec681f3Smrg   }
3617ec681f3Smrg
362cdc920a0Smrg   switch (buffer) {
363cdc920a0Smrg   case GL_STENCIL:
364af69d88dSmrg      /* Page 264 (page 280 of the PDF) of the OpenGL 3.0 spec says:
365af69d88dSmrg       *
366af69d88dSmrg       *     "ClearBuffer generates an INVALID VALUE error if buffer is
367af69d88dSmrg       *     COLOR and drawbuffer is less than zero, or greater than the
368af69d88dSmrg       *     value of MAX DRAW BUFFERS minus one; or if buffer is DEPTH,
369af69d88dSmrg       *     STENCIL, or DEPTH STENCIL and drawbuffer is not zero."
370af69d88dSmrg       */
37101e04c3fSmrg      if (!no_error && drawbuffer != 0) {
372cdc920a0Smrg         _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferiv(drawbuffer=%d)",
373cdc920a0Smrg                     drawbuffer);
374cdc920a0Smrg         return;
375cdc920a0Smrg      }
37601e04c3fSmrg      else if (ctx->DrawBuffer->Attachment[BUFFER_STENCIL].Renderbuffer
37701e04c3fSmrg               && !ctx->RasterDiscard) {
378cdc920a0Smrg         /* Save current stencil clear value, set to 'value', do the
379cdc920a0Smrg          * stencil clear and restore the clear value.
380cdc920a0Smrg          * XXX in the future we may have a new ctx->Driver.ClearBuffer()
381cdc920a0Smrg          * hook instead.
382cdc920a0Smrg          */
383cdc920a0Smrg         const GLuint clearSave = ctx->Stencil.Clear;
384cdc920a0Smrg         ctx->Stencil.Clear = *value;
385cdc920a0Smrg         ctx->Driver.Clear(ctx, BUFFER_BIT_STENCIL);
386cdc920a0Smrg         ctx->Stencil.Clear = clearSave;
387cdc920a0Smrg      }
388cdc920a0Smrg      break;
389cdc920a0Smrg   case GL_COLOR:
390cdc920a0Smrg      {
391cdc920a0Smrg         const GLbitfield mask = make_color_buffer_mask(ctx, drawbuffer);
39201e04c3fSmrg         if (!no_error && mask == INVALID_MASK) {
393cdc920a0Smrg            _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferiv(drawbuffer=%d)",
394cdc920a0Smrg                        drawbuffer);
395cdc920a0Smrg            return;
396cdc920a0Smrg         }
397af69d88dSmrg         else if (mask && !ctx->RasterDiscard) {
398af69d88dSmrg            union gl_color_union clearSave;
399af69d88dSmrg
400cdc920a0Smrg            /* save color */
401af69d88dSmrg            clearSave = ctx->Color.ClearColor;
402cdc920a0Smrg            /* set color */
403af69d88dSmrg            COPY_4V(ctx->Color.ClearColor.i, value);
404cdc920a0Smrg            /* clear buffer(s) */
405cdc920a0Smrg            ctx->Driver.Clear(ctx, mask);
406cdc920a0Smrg            /* restore color */
407af69d88dSmrg            ctx->Color.ClearColor = clearSave;
408cdc920a0Smrg         }
409cdc920a0Smrg      }
410cdc920a0Smrg      break;
411cdc920a0Smrg   default:
41201e04c3fSmrg      if (!no_error) {
41301e04c3fSmrg         /* Page 498 of the PDF, section '17.4.3.1 Clearing Individual Buffers'
41401e04c3fSmrg          * of the OpenGL 4.5 spec states:
41501e04c3fSmrg          *
41601e04c3fSmrg          *    "An INVALID_ENUM error is generated by ClearBufferiv and
41701e04c3fSmrg          *     ClearNamedFramebufferiv if buffer is not COLOR or STENCIL."
41801e04c3fSmrg          */
41901e04c3fSmrg         _mesa_error(ctx, GL_INVALID_ENUM, "glClearBufferiv(buffer=%s)",
42001e04c3fSmrg                     _mesa_enum_to_string(buffer));
42101e04c3fSmrg      }
422cdc920a0Smrg      return;
423cdc920a0Smrg   }
424cdc920a0Smrg}
425cdc920a0Smrg
426cdc920a0Smrg
42701e04c3fSmrgvoid GLAPIENTRY
42801e04c3fSmrg_mesa_ClearBufferiv_no_error(GLenum buffer, GLint drawbuffer, const GLint *value)
42901e04c3fSmrg{
43001e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
43101e04c3fSmrg   clear_bufferiv(ctx, buffer, drawbuffer, value, true);
43201e04c3fSmrg}
43301e04c3fSmrg
43401e04c3fSmrg
43501e04c3fSmrgvoid GLAPIENTRY
43601e04c3fSmrg_mesa_ClearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *value)
43701e04c3fSmrg{
43801e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
43901e04c3fSmrg   clear_bufferiv(ctx, buffer, drawbuffer, value, false);
44001e04c3fSmrg}
44101e04c3fSmrg
44201e04c3fSmrg
443cdc920a0Smrg/**
44401e04c3fSmrg * The ClearBuffer framework is so complicated and so riddled with the
44501e04c3fSmrg * assumption that the framebuffer is bound that, for now, we will just fake
44601e04c3fSmrg * direct state access clearing for the user.
447cdc920a0Smrg */
448cdc920a0Smrgvoid GLAPIENTRY
44901e04c3fSmrg_mesa_ClearNamedFramebufferiv(GLuint framebuffer, GLenum buffer,
45001e04c3fSmrg                              GLint drawbuffer, const GLint *value)
451cdc920a0Smrg{
45201e04c3fSmrg   GLint oldfb;
45301e04c3fSmrg
45401e04c3fSmrg   _mesa_GetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, &oldfb);
45501e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, framebuffer);
45601e04c3fSmrg   _mesa_ClearBufferiv(buffer, drawbuffer, value);
45701e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, (GLuint) oldfb);
45801e04c3fSmrg}
45901e04c3fSmrg
460cdc920a0Smrg
46101e04c3fSmrg/**
46201e04c3fSmrg * New in GL 3.0
46301e04c3fSmrg * Clear unsigned integer color buffer (not depth, not stencil).
46401e04c3fSmrg */
46501e04c3fSmrgstatic ALWAYS_INLINE void
46601e04c3fSmrgclear_bufferuiv(struct gl_context *ctx, GLenum buffer, GLint drawbuffer,
46701e04c3fSmrg                const GLuint *value, bool no_error)
46801e04c3fSmrg{
4697ec681f3Smrg   FLUSH_VERTICES(ctx, 0, 0);
470cdc920a0Smrg
471cdc920a0Smrg   if (ctx->NewState) {
472cdc920a0Smrg      _mesa_update_state( ctx );
473cdc920a0Smrg   }
474cdc920a0Smrg
4757ec681f3Smrg   if (!no_error && ctx->DrawBuffer->_Status != GL_FRAMEBUFFER_COMPLETE) {
4767ec681f3Smrg      _mesa_error(ctx, GL_INVALID_FRAMEBUFFER_OPERATION,
4777ec681f3Smrg                  "glClearBufferuiv(incomplete framebuffer)");
4787ec681f3Smrg      return;
4797ec681f3Smrg   }
4807ec681f3Smrg
481cdc920a0Smrg   switch (buffer) {
482cdc920a0Smrg   case GL_COLOR:
483cdc920a0Smrg      {
484cdc920a0Smrg         const GLbitfield mask = make_color_buffer_mask(ctx, drawbuffer);
48501e04c3fSmrg         if (!no_error && mask == INVALID_MASK) {
4863464ebd5Sriastradh            _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferuiv(drawbuffer=%d)",
487cdc920a0Smrg                        drawbuffer);
488cdc920a0Smrg            return;
489cdc920a0Smrg         }
490af69d88dSmrg         else if (mask && !ctx->RasterDiscard) {
491af69d88dSmrg            union gl_color_union clearSave;
492af69d88dSmrg
493cdc920a0Smrg            /* save color */
494af69d88dSmrg            clearSave = ctx->Color.ClearColor;
495cdc920a0Smrg            /* set color */
496af69d88dSmrg            COPY_4V(ctx->Color.ClearColor.ui, value);
497cdc920a0Smrg            /* clear buffer(s) */
498cdc920a0Smrg            ctx->Driver.Clear(ctx, mask);
499cdc920a0Smrg            /* restore color */
500af69d88dSmrg            ctx->Color.ClearColor = clearSave;
501cdc920a0Smrg         }
502cdc920a0Smrg      }
503cdc920a0Smrg      break;
504cdc920a0Smrg   default:
50501e04c3fSmrg      if (!no_error) {
50601e04c3fSmrg         /* Page 498 of the PDF, section '17.4.3.1 Clearing Individual Buffers'
50701e04c3fSmrg          * of the OpenGL 4.5 spec states:
50801e04c3fSmrg          *
50901e04c3fSmrg          *    "An INVALID_ENUM error is generated by ClearBufferuiv and
51001e04c3fSmrg          *     ClearNamedFramebufferuiv if buffer is not COLOR."
51101e04c3fSmrg          */
51201e04c3fSmrg         _mesa_error(ctx, GL_INVALID_ENUM, "glClearBufferuiv(buffer=%s)",
51301e04c3fSmrg                     _mesa_enum_to_string(buffer));
51401e04c3fSmrg      }
515cdc920a0Smrg      return;
516cdc920a0Smrg   }
517cdc920a0Smrg}
518cdc920a0Smrg
519cdc920a0Smrg
52001e04c3fSmrgvoid GLAPIENTRY
52101e04c3fSmrg_mesa_ClearBufferuiv_no_error(GLenum buffer, GLint drawbuffer,
52201e04c3fSmrg                              const GLuint *value)
52301e04c3fSmrg{
52401e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
52501e04c3fSmrg   clear_bufferuiv(ctx, buffer, drawbuffer, value, true);
52601e04c3fSmrg}
52701e04c3fSmrg
52801e04c3fSmrg
52901e04c3fSmrgvoid GLAPIENTRY
53001e04c3fSmrg_mesa_ClearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *value)
53101e04c3fSmrg{
53201e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
53301e04c3fSmrg   clear_bufferuiv(ctx, buffer, drawbuffer, value, false);
53401e04c3fSmrg}
53501e04c3fSmrg
53601e04c3fSmrg
537cdc920a0Smrg/**
53801e04c3fSmrg * The ClearBuffer framework is so complicated and so riddled with the
53901e04c3fSmrg * assumption that the framebuffer is bound that, for now, we will just fake
54001e04c3fSmrg * direct state access clearing for the user.
541cdc920a0Smrg */
542cdc920a0Smrgvoid GLAPIENTRY
54301e04c3fSmrg_mesa_ClearNamedFramebufferuiv(GLuint framebuffer, GLenum buffer,
54401e04c3fSmrg                               GLint drawbuffer, const GLuint *value)
545cdc920a0Smrg{
54601e04c3fSmrg   GLint oldfb;
547cdc920a0Smrg
54801e04c3fSmrg   _mesa_GetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, &oldfb);
54901e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, framebuffer);
55001e04c3fSmrg   _mesa_ClearBufferuiv(buffer, drawbuffer, value);
55101e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, (GLuint) oldfb);
55201e04c3fSmrg}
55301e04c3fSmrg
55401e04c3fSmrg
55501e04c3fSmrg/**
55601e04c3fSmrg * New in GL 3.0
55701e04c3fSmrg * Clear fixed-pt or float color buffer or depth buffer (not stencil).
55801e04c3fSmrg */
55901e04c3fSmrgstatic ALWAYS_INLINE void
56001e04c3fSmrgclear_bufferfv(struct gl_context *ctx, GLenum buffer, GLint drawbuffer,
56101e04c3fSmrg               const GLfloat *value, bool no_error)
56201e04c3fSmrg{
5637ec681f3Smrg   FLUSH_VERTICES(ctx, 0, 0);
564cdc920a0Smrg
565cdc920a0Smrg   if (ctx->NewState) {
566cdc920a0Smrg      _mesa_update_state( ctx );
567cdc920a0Smrg   }
568cdc920a0Smrg
5697ec681f3Smrg   if (!no_error && ctx->DrawBuffer->_Status != GL_FRAMEBUFFER_COMPLETE) {
5707ec681f3Smrg      _mesa_error(ctx, GL_INVALID_FRAMEBUFFER_OPERATION,
5717ec681f3Smrg                  "glClearBufferfv(incomplete framebuffer)");
5727ec681f3Smrg      return;
5737ec681f3Smrg   }
5747ec681f3Smrg
575cdc920a0Smrg   switch (buffer) {
576cdc920a0Smrg   case GL_DEPTH:
577af69d88dSmrg      /* Page 264 (page 280 of the PDF) of the OpenGL 3.0 spec says:
578af69d88dSmrg       *
579af69d88dSmrg       *     "ClearBuffer generates an INVALID VALUE error if buffer is
580af69d88dSmrg       *     COLOR and drawbuffer is less than zero, or greater than the
581af69d88dSmrg       *     value of MAX DRAW BUFFERS minus one; or if buffer is DEPTH,
582af69d88dSmrg       *     STENCIL, or DEPTH STENCIL and drawbuffer is not zero."
583af69d88dSmrg       */
58401e04c3fSmrg      if (!no_error && drawbuffer != 0) {
585cdc920a0Smrg         _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferfv(drawbuffer=%d)",
586cdc920a0Smrg                     drawbuffer);
587cdc920a0Smrg         return;
588cdc920a0Smrg      }
58901e04c3fSmrg      else if (ctx->DrawBuffer->Attachment[BUFFER_DEPTH].Renderbuffer
59001e04c3fSmrg               && !ctx->RasterDiscard) {
591cdc920a0Smrg         /* Save current depth clear value, set to 'value', do the
592cdc920a0Smrg          * depth clear and restore the clear value.
593cdc920a0Smrg          * XXX in the future we may have a new ctx->Driver.ClearBuffer()
594cdc920a0Smrg          * hook instead.
595cdc920a0Smrg          */
596cdc920a0Smrg         const GLclampd clearSave = ctx->Depth.Clear;
5977ec681f3Smrg
5987ec681f3Smrg         /* Page 263 (page 279 of the PDF) of the OpenGL 3.0 spec says:
5997ec681f3Smrg          *
6007ec681f3Smrg          *     "If buffer is DEPTH, drawbuffer must be zero, and value points
6017ec681f3Smrg          *     to the single depth value to clear the depth buffer to.
6027ec681f3Smrg          *     Clamping and type conversion for fixed-point depth buffers are
6037ec681f3Smrg          *     performed in the same fashion as for ClearDepth."
6047ec681f3Smrg          */
6057ec681f3Smrg         const struct gl_renderbuffer *rb =
6067ec681f3Smrg            ctx->DrawBuffer->Attachment[BUFFER_DEPTH].Renderbuffer;
6077ec681f3Smrg         const bool is_float_depth =
6087ec681f3Smrg            _mesa_has_depth_float_channel(rb->InternalFormat);
6097ec681f3Smrg         ctx->Depth.Clear = is_float_depth ? *value : SATURATE(*value);
6107ec681f3Smrg
611cdc920a0Smrg         ctx->Driver.Clear(ctx, BUFFER_BIT_DEPTH);
612cdc920a0Smrg         ctx->Depth.Clear = clearSave;
613cdc920a0Smrg      }
614cdc920a0Smrg      /* clear depth buffer to value */
615cdc920a0Smrg      break;
616cdc920a0Smrg   case GL_COLOR:
617cdc920a0Smrg      {
618cdc920a0Smrg         const GLbitfield mask = make_color_buffer_mask(ctx, drawbuffer);
61901e04c3fSmrg         if (!no_error && mask == INVALID_MASK) {
620cdc920a0Smrg            _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferfv(drawbuffer=%d)",
621cdc920a0Smrg                        drawbuffer);
622cdc920a0Smrg            return;
623cdc920a0Smrg         }
624af69d88dSmrg         else if (mask && !ctx->RasterDiscard) {
625af69d88dSmrg            union gl_color_union clearSave;
626af69d88dSmrg
627cdc920a0Smrg            /* save color */
628af69d88dSmrg            clearSave = ctx->Color.ClearColor;
629cdc920a0Smrg            /* set color */
630af69d88dSmrg            COPY_4V(ctx->Color.ClearColor.f, value);
631cdc920a0Smrg            /* clear buffer(s) */
632cdc920a0Smrg            ctx->Driver.Clear(ctx, mask);
633cdc920a0Smrg            /* restore color */
634af69d88dSmrg            ctx->Color.ClearColor = clearSave;
635cdc920a0Smrg         }
636cdc920a0Smrg      }
637cdc920a0Smrg      break;
638cdc920a0Smrg   default:
63901e04c3fSmrg      if (!no_error) {
64001e04c3fSmrg         /* Page 498 of the PDF, section '17.4.3.1 Clearing Individual Buffers'
64101e04c3fSmrg          * of the OpenGL 4.5 spec states:
64201e04c3fSmrg          *
64301e04c3fSmrg          *    "An INVALID_ENUM error is generated by ClearBufferfv and
64401e04c3fSmrg          *     ClearNamedFramebufferfv if buffer is not COLOR or DEPTH."
64501e04c3fSmrg          */
64601e04c3fSmrg         _mesa_error(ctx, GL_INVALID_ENUM, "glClearBufferfv(buffer=%s)",
64701e04c3fSmrg                     _mesa_enum_to_string(buffer));
64801e04c3fSmrg      }
649cdc920a0Smrg      return;
650cdc920a0Smrg   }
651cdc920a0Smrg}
652cdc920a0Smrg
653cdc920a0Smrg
65401e04c3fSmrgvoid GLAPIENTRY
65501e04c3fSmrg_mesa_ClearBufferfv_no_error(GLenum buffer, GLint drawbuffer,
65601e04c3fSmrg                             const GLfloat *value)
65701e04c3fSmrg{
65801e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
65901e04c3fSmrg   clear_bufferfv(ctx, buffer, drawbuffer, value, true);
66001e04c3fSmrg}
66101e04c3fSmrg
66201e04c3fSmrg
66301e04c3fSmrgvoid GLAPIENTRY
66401e04c3fSmrg_mesa_ClearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *value)
66501e04c3fSmrg{
66601e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
66701e04c3fSmrg   clear_bufferfv(ctx, buffer, drawbuffer, value, false);
66801e04c3fSmrg}
66901e04c3fSmrg
67001e04c3fSmrg
67101e04c3fSmrg/**
67201e04c3fSmrg * The ClearBuffer framework is so complicated and so riddled with the
67301e04c3fSmrg * assumption that the framebuffer is bound that, for now, we will just fake
67401e04c3fSmrg * direct state access clearing for the user.
67501e04c3fSmrg */
67601e04c3fSmrgvoid GLAPIENTRY
67701e04c3fSmrg_mesa_ClearNamedFramebufferfv(GLuint framebuffer, GLenum buffer,
67801e04c3fSmrg                              GLint drawbuffer, const GLfloat *value)
67901e04c3fSmrg{
68001e04c3fSmrg   GLint oldfb;
68101e04c3fSmrg
68201e04c3fSmrg   _mesa_GetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, &oldfb);
68301e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, framebuffer);
68401e04c3fSmrg   _mesa_ClearBufferfv(buffer, drawbuffer, value);
68501e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, (GLuint) oldfb);
68601e04c3fSmrg}
68701e04c3fSmrg
68801e04c3fSmrg
689cdc920a0Smrg/**
690cdc920a0Smrg * New in GL 3.0
691cdc920a0Smrg * Clear depth/stencil buffer only.
692cdc920a0Smrg */
69301e04c3fSmrgstatic ALWAYS_INLINE void
69401e04c3fSmrgclear_bufferfi(struct gl_context *ctx, GLenum buffer, GLint drawbuffer,
69501e04c3fSmrg               GLfloat depth, GLint stencil, bool no_error)
696cdc920a0Smrg{
697af69d88dSmrg   GLbitfield mask = 0;
698cdc920a0Smrg
6997ec681f3Smrg   FLUSH_VERTICES(ctx, 0, 0);
700cdc920a0Smrg
70101e04c3fSmrg   if (!no_error) {
70201e04c3fSmrg      if (buffer != GL_DEPTH_STENCIL) {
70301e04c3fSmrg         _mesa_error(ctx, GL_INVALID_ENUM, "glClearBufferfi(buffer=%s)",
70401e04c3fSmrg                     _mesa_enum_to_string(buffer));
70501e04c3fSmrg         return;
70601e04c3fSmrg      }
707cdc920a0Smrg
70801e04c3fSmrg      /* Page 264 (page 280 of the PDF) of the OpenGL 3.0 spec says:
70901e04c3fSmrg       *
71001e04c3fSmrg       *     "ClearBuffer generates an INVALID VALUE error if buffer is
71101e04c3fSmrg       *     COLOR and drawbuffer is less than zero, or greater than the
71201e04c3fSmrg       *     value of MAX DRAW BUFFERS minus one; or if buffer is DEPTH,
71301e04c3fSmrg       *     STENCIL, or DEPTH STENCIL and drawbuffer is not zero."
71401e04c3fSmrg       */
71501e04c3fSmrg      if (drawbuffer != 0) {
71601e04c3fSmrg         _mesa_error(ctx, GL_INVALID_VALUE, "glClearBufferfi(drawbuffer=%d)",
71701e04c3fSmrg                     drawbuffer);
71801e04c3fSmrg         return;
71901e04c3fSmrg      }
720cdc920a0Smrg   }
721cdc920a0Smrg
722af69d88dSmrg   if (ctx->RasterDiscard)
723af69d88dSmrg      return;
724af69d88dSmrg
725cdc920a0Smrg   if (ctx->NewState) {
726cdc920a0Smrg      _mesa_update_state( ctx );
727cdc920a0Smrg   }
728cdc920a0Smrg
7297ec681f3Smrg   if (!no_error && ctx->DrawBuffer->_Status != GL_FRAMEBUFFER_COMPLETE_EXT) {
7307ec681f3Smrg      _mesa_error(ctx, GL_INVALID_FRAMEBUFFER_OPERATION_EXT,
7317ec681f3Smrg                  "glClearBufferfi(incomplete framebuffer)");
7327ec681f3Smrg      return;
7337ec681f3Smrg   }
7347ec681f3Smrg
735af69d88dSmrg   if (ctx->DrawBuffer->Attachment[BUFFER_DEPTH].Renderbuffer)
736af69d88dSmrg      mask |= BUFFER_BIT_DEPTH;
737af69d88dSmrg   if (ctx->DrawBuffer->Attachment[BUFFER_STENCIL].Renderbuffer)
738af69d88dSmrg      mask |= BUFFER_BIT_STENCIL;
739af69d88dSmrg
740af69d88dSmrg   if (mask) {
741cdc920a0Smrg      /* save current clear values */
742cdc920a0Smrg      const GLclampd clearDepthSave = ctx->Depth.Clear;
743cdc920a0Smrg      const GLuint clearStencilSave = ctx->Stencil.Clear;
744cdc920a0Smrg
7457ec681f3Smrg      /* set new clear values
7467ec681f3Smrg       *
7477ec681f3Smrg       * Page 263 (page 279 of the PDF) of the OpenGL 3.0 spec says:
7487ec681f3Smrg       *
7497ec681f3Smrg       *     "depth and stencil are the values to clear the depth and stencil
7507ec681f3Smrg       *     buffers to, respectively. Clamping and type conversion for
7517ec681f3Smrg       *     fixed-point depth buffers are performed in the same fashion as
7527ec681f3Smrg       *     for ClearDepth."
7537ec681f3Smrg       */
7547ec681f3Smrg      const struct gl_renderbuffer *rb =
7557ec681f3Smrg         ctx->DrawBuffer->Attachment[BUFFER_DEPTH].Renderbuffer;
7567ec681f3Smrg      const bool has_float_depth = rb &&
7577ec681f3Smrg         _mesa_has_depth_float_channel(rb->InternalFormat);
7587ec681f3Smrg      ctx->Depth.Clear = has_float_depth ? depth : SATURATE(depth);
759cdc920a0Smrg      ctx->Stencil.Clear = stencil;
760cdc920a0Smrg
761cdc920a0Smrg      /* clear buffers */
762af69d88dSmrg      ctx->Driver.Clear(ctx, mask);
763cdc920a0Smrg
764cdc920a0Smrg      /* restore */
765cdc920a0Smrg      ctx->Depth.Clear = clearDepthSave;
766cdc920a0Smrg      ctx->Stencil.Clear = clearStencilSave;
767cdc920a0Smrg   }
768cdc920a0Smrg}
76901e04c3fSmrg
77001e04c3fSmrg
77101e04c3fSmrgvoid GLAPIENTRY
77201e04c3fSmrg_mesa_ClearBufferfi_no_error(GLenum buffer, GLint drawbuffer,
77301e04c3fSmrg                             GLfloat depth, GLint stencil)
77401e04c3fSmrg{
77501e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
77601e04c3fSmrg   clear_bufferfi(ctx, buffer, drawbuffer, depth, stencil, true);
77701e04c3fSmrg}
77801e04c3fSmrg
77901e04c3fSmrg
78001e04c3fSmrgvoid GLAPIENTRY
78101e04c3fSmrg_mesa_ClearBufferfi(GLenum buffer, GLint drawbuffer,
78201e04c3fSmrg                    GLfloat depth, GLint stencil)
78301e04c3fSmrg{
78401e04c3fSmrg   GET_CURRENT_CONTEXT(ctx);
78501e04c3fSmrg   clear_bufferfi(ctx, buffer, drawbuffer, depth, stencil, false);
78601e04c3fSmrg}
78701e04c3fSmrg
78801e04c3fSmrg
78901e04c3fSmrg/**
79001e04c3fSmrg * The ClearBuffer framework is so complicated and so riddled with the
79101e04c3fSmrg * assumption that the framebuffer is bound that, for now, we will just fake
79201e04c3fSmrg * direct state access clearing for the user.
79301e04c3fSmrg */
79401e04c3fSmrgvoid GLAPIENTRY
79501e04c3fSmrg_mesa_ClearNamedFramebufferfi(GLuint framebuffer, GLenum buffer,
79601e04c3fSmrg                              GLint drawbuffer, GLfloat depth, GLint stencil)
79701e04c3fSmrg{
79801e04c3fSmrg   GLint oldfb;
79901e04c3fSmrg
80001e04c3fSmrg   _mesa_GetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, &oldfb);
80101e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, framebuffer);
80201e04c3fSmrg   _mesa_ClearBufferfi(buffer, drawbuffer, depth, stencil);
80301e04c3fSmrg   _mesa_BindFramebuffer(GL_DRAW_FRAMEBUFFER, (GLuint) oldfb);
80401e04c3fSmrg}
805