summaryrefslogtreecommitdiffstats
path: root/src/mesa/swrast/s_span.c
diff options
context:
space:
mode:
authorBrian Paul <[email protected]>2005-09-16 21:15:27 +0000
committerBrian Paul <[email protected]>2005-09-16 21:15:27 +0000
commit67074332728acba86da7630353673b458713bb8a (patch)
treeee17b8b91b16ef04df684157d2b25983373268e7 /src/mesa/swrast/s_span.c
parent82e314252f0b706c3ae1c748e9d64d8fa58812db (diff)
Fix potential segfault when trying to read pixels outside renderbuffer bounds.
Use _swrast_get_values() which does clipping.
Diffstat (limited to 'src/mesa/swrast/s_span.c')
-rw-r--r--src/mesa/swrast/s_span.c38
1 files changed, 38 insertions, 0 deletions
diff --git a/src/mesa/swrast/s_span.c b/src/mesa/swrast/s_span.c
index 780f1b63990..a9f6684a72b 100644
--- a/src/mesa/swrast/s_span.c
+++ b/src/mesa/swrast/s_span.c
@@ -1436,3 +1436,41 @@ _swrast_read_index_span( GLcontext *ctx, struct gl_renderbuffer *rb,
}
}
}
+
+
+/**
+ * Wrapper for gl_renderbuffer::GetValues() which does clipping to avoid
+ * reading values outside the buffer bounds.
+ * We can use this for reading any format/type of renderbuffer.
+ * \param valueSize is the size in bytes of each value put into the
+ * values array.
+ */
+void
+_swrast_get_values(GLcontext *ctx, struct gl_renderbuffer *rb,
+ GLuint count, const GLint x[], const GLint y[],
+ void *values, GLuint valueSize)
+{
+ GLuint i, inCount = 0, inStart = 0;
+
+ for (i = 0; i < count; i++) {
+ if (x[i] >= 0 && y[i] >= 0 && x[i] < rb->Width && y[i] < rb->Height) {
+ /* inside */
+ if (inCount == 0)
+ inStart = i;
+ inCount++;
+ }
+ else {
+ if (inCount > 0) {
+ /* read [inStart, inStart + inCount) */
+ rb->GetValues(ctx, rb, inCount, x + inStart, y + inStart,
+ (GLubyte *) values + inStart * valueSize);
+ inCount = 0;
+ }
+ }
+ }
+ if (inCount > 0) {
+ /* read last values */
+ rb->GetValues(ctx, rb, inCount, x + inStart, y + inStart,
+ (GLubyte *) values + inStart * valueSize);
+ }
+}