mesa: don't error check the default buffer object in glBindBufferOffsetEXT()
[mesa.git] / src / mesa / main / scissor.c
index 83f39e2a0f92d790ae9248f4b601eb432bfd5025..b38db06bc863943e512f33466d9106b113e71461 100644 (file)
@@ -25,6 +25,7 @@
 
 #include "main/glheader.h"
 #include "main/context.h"
+#include "main/enums.h"
 #include "main/mtypes.h"
 #include "main/scissor.h"
 
@@ -47,29 +48,19 @@ set_scissor_no_notify(struct gl_context *ctx, unsigned idx,
        height == ctx->Scissor.ScissorArray[idx].Height)
       return;
 
-   FLUSH_VERTICES(ctx, _NEW_SCISSOR);
+   FLUSH_VERTICES(ctx, ctx->DriverFlags.NewScissorRect ? 0 : _NEW_SCISSOR);
+   ctx->NewDriverState |= ctx->DriverFlags.NewScissorRect;
+
    ctx->Scissor.ScissorArray[idx].X = x;
    ctx->Scissor.ScissorArray[idx].Y = y;
    ctx->Scissor.ScissorArray[idx].Width = width;
    ctx->Scissor.ScissorArray[idx].Height = height;
 }
 
-/**
- * Called via glScissor
- */
-void GLAPIENTRY
-_mesa_Scissor( GLint x, GLint y, GLsizei width, GLsizei height )
+static void
+scissor(struct gl_context *ctx, GLint x, GLint y, GLsizei width, GLsizei height)
 {
    unsigned i;
-   GET_CURRENT_CONTEXT(ctx);
-
-   if (MESA_VERBOSE & VERBOSE_API)
-      _mesa_debug(ctx, "glScissor %d %d %d %d\n", x, y, width, height);
-
-   if (width < 0 || height < 0) {
-      _mesa_error( ctx, GL_INVALID_VALUE, "glScissor" );
-      return;
-   }
 
    /* The GL_ARB_viewport_array spec says:
     *
@@ -90,6 +81,32 @@ _mesa_Scissor( GLint x, GLint y, GLsizei width, GLsizei height )
       ctx->Driver.Scissor(ctx);
 }
 
+/**
+ * Called via glScissor
+ */
+void GLAPIENTRY
+_mesa_Scissor_no_error(GLint x, GLint y, GLsizei width, GLsizei height)
+{
+   GET_CURRENT_CONTEXT(ctx);
+   scissor(ctx, x, y, width, height);
+}
+
+void GLAPIENTRY
+_mesa_Scissor(GLint x, GLint y, GLsizei width, GLsizei height)
+{
+   GET_CURRENT_CONTEXT(ctx);
+
+   if (MESA_VERBOSE & VERBOSE_API)
+      _mesa_debug(ctx, "glScissor %d %d %d %d\n", x, y, width, height);
+
+   if (width < 0 || height < 0) {
+      _mesa_error( ctx, GL_INVALID_VALUE, "glScissor" );
+      return;
+   }
+
+   scissor(ctx, x, y, width, height);
+}
+
 
 /**
  * Define the scissor box.
@@ -114,6 +131,19 @@ _mesa_set_scissor(struct gl_context *ctx, unsigned idx,
       ctx->Driver.Scissor(ctx);
 }
 
+static void
+scissor_array(struct gl_context *ctx, GLuint first, GLsizei count,
+              struct gl_scissor_rect *rect)
+{
+   for (GLsizei i = 0; i < count; i++) {
+      set_scissor_no_notify(ctx, i + first, rect[i].X, rect[i].Y,
+                            rect[i].Width, rect[i].Height);
+   }
+
+   if (ctx->Driver.Scissor)
+      ctx->Driver.Scissor(ctx);
+}
+
 /**
  * Define count scissor boxes starting at index.
  *
@@ -125,6 +155,15 @@ _mesa_set_scissor(struct gl_context *ctx, unsigned idx,
  *
  * Verifies the parameters and call set_scissor_no_notify to do the work.
  */
+void GLAPIENTRY
+_mesa_ScissorArrayv_no_error(GLuint first, GLsizei count, const GLint *v)
+{
+   GET_CURRENT_CONTEXT(ctx);
+
+   struct gl_scissor_rect *p = (struct gl_scissor_rect *)v;
+   scissor_array(ctx, first, count, p);
+}
+
 void GLAPIENTRY
 _mesa_ScissorArrayv(GLuint first, GLsizei count, const GLint *v)
 {
@@ -149,12 +188,7 @@ _mesa_ScissorArrayv(GLuint first, GLsizei count, const GLint *v)
       }
    }
 
-   for (i = 0; i < count; i++)
-      set_scissor_no_notify(ctx, i + first,
-                            p[i].X, p[i].Y, p[i].Width, p[i].Height);
-
-   if (ctx->Driver.Scissor)
-      ctx->Driver.Scissor(ctx);
+   scissor_array(ctx, first, count, p);
 }
 
 /**
@@ -168,11 +202,10 @@ _mesa_ScissorArrayv(GLuint first, GLsizei count, const GLint *v)
  * Verifies the parameters call set_scissor_no_notify to do the work.
  */
 static void
-ScissorIndexed(GLuint index, GLint left, GLint bottom,
-               GLsizei width, GLsizei height, const char *function)
+scissor_indexed_err(struct gl_context *ctx, GLuint index, GLint left,
+                    GLint bottom, GLsizei width, GLsizei height,
+                    const char *function)
 {
-   GET_CURRENT_CONTEXT(ctx);
-
    if (MESA_VERBOSE & VERBOSE_API)
       _mesa_debug(ctx, "%s(%d, %d, %d, %d, %d)\n",
                   function, index, left, bottom, width, height);
@@ -191,25 +224,93 @@ ScissorIndexed(GLuint index, GLint left, GLint bottom,
       return;
    }
 
-   set_scissor_no_notify(ctx, index, left, bottom, width, height);
+   _mesa_set_scissor(ctx, index, left, bottom, width, height);
+}
 
-   if (ctx->Driver.Scissor)
-      ctx->Driver.Scissor(ctx);
+void GLAPIENTRY
+_mesa_ScissorIndexed_no_error(GLuint index, GLint left, GLint bottom,
+                              GLsizei width, GLsizei height)
+{
+   GET_CURRENT_CONTEXT(ctx);
+   _mesa_set_scissor(ctx, index, left, bottom, width, height);
 }
 
 void GLAPIENTRY
 _mesa_ScissorIndexed(GLuint index, GLint left, GLint bottom,
                      GLsizei width, GLsizei height)
 {
-   ScissorIndexed(index, left, bottom, width, height, "glScissorIndexd");
+   GET_CURRENT_CONTEXT(ctx);
+   scissor_indexed_err(ctx, index, left, bottom, width, height,
+                       "glScissorIndexed");
+}
+
+void GLAPIENTRY
+_mesa_ScissorIndexedv_no_error(GLuint index, const GLint *v)
+{
+   GET_CURRENT_CONTEXT(ctx);
+   _mesa_set_scissor(ctx, index, v[0], v[1], v[2], v[3]);
 }
 
 void GLAPIENTRY
 _mesa_ScissorIndexedv(GLuint index, const GLint *v)
 {
-   ScissorIndexed(index, v[0], v[1], v[2], v[3], "glScissorIndexdv");
+   GET_CURRENT_CONTEXT(ctx);
+   scissor_indexed_err(ctx, index, v[0], v[1], v[2], v[3],
+                       "glScissorIndexedv");
+}
+
+void GLAPIENTRY
+_mesa_WindowRectanglesEXT(GLenum mode, GLsizei count, const GLint *box)
+{
+   int i;
+   struct gl_scissor_rect newval[MAX_WINDOW_RECTANGLES];
+   GET_CURRENT_CONTEXT(ctx);
+
+   if (MESA_VERBOSE & VERBOSE_API)
+      _mesa_debug(ctx, "glWindowRectanglesEXT(%s, %d, %p)\n",
+                  _mesa_enum_to_string(mode), count, box);
+
+   if (mode != GL_INCLUSIVE_EXT && mode != GL_EXCLUSIVE_EXT) {
+      _mesa_error(ctx, GL_INVALID_ENUM,
+                  "glWindowRectanglesEXT(invalid mode 0x%x)", mode);
+      return;
+   }
+
+   if (count < 0) {
+      _mesa_error(ctx, GL_INVALID_VALUE, "glWindowRectanglesEXT(count < 0)");
+      return;
+   }
+
+   if (count > ctx->Const.MaxWindowRectangles) {
+      _mesa_error(ctx, GL_INVALID_VALUE,
+                  "glWindowRectanglesEXT(count >= MaxWindowRectangles (%d)",
+                  ctx->Const.MaxWindowRectangles);
+      return;
+   }
+
+   for (i = 0; i < count; i++) {
+      if (box[2] < 0 || box[3] < 0) {
+         _mesa_error(ctx, GL_INVALID_VALUE,
+                     "glWindowRectanglesEXT(box %d: w < 0 || h < 0)", i);
+         return;
+      }
+      newval[i].X = box[0];
+      newval[i].Y = box[1];
+      newval[i].Width = box[2];
+      newval[i].Height = box[3];
+      box += 4;
+   }
+
+   FLUSH_VERTICES(ctx, 0);
+   ctx->NewDriverState |= ctx->DriverFlags.NewWindowRectangles;
+
+   memcpy(ctx->Scissor.WindowRects, newval,
+          sizeof(struct gl_scissor_rect) * count);
+   ctx->Scissor.NumWindowRects = count;
+   ctx->Scissor.WindowRectMode = mode;
 }
 
+
 /**
  * Initialize the context's scissor state.
  * \param ctx  the GL context.
@@ -221,6 +322,7 @@ _mesa_init_scissor(struct gl_context *ctx)
 
    /* Scissor group */
    ctx->Scissor.EnableFlags = 0;
+   ctx->Scissor.WindowRectMode = GL_EXCLUSIVE_EXT;
 
    /* Note: ctx->Const.MaxViewports may not have been set by the driver yet,
     * so just initialize all of them.