<div dir="ltr"><div>Bug: if in vrend_renderer.c the "use_sub_data" is set to 1 (default is 0) to use glBufferSubData() for transferring IOVs, some memory corruptions and artifacts occur. <br></div><div><br></div><div>Reason: the second parameter in glBufferSubData() is the offset, but in vrend_read_from_iovec_cb() function in iov.c, the "count" is passed to it causing to possibly write beyond the buffer boundary (or at wrong offset). The following patch fixes the problem. Also, I've made simple changes to other functions in iov.c to make the code consistent.</div><div><br></div><div><div>P.S.: our experiments on both Intel Atom and aarch64 platforms shows that
 glBufferSubData() performs faster in function 
vrend_renderer_transfer_write_iov() than using the combination of 
glMapBufferRange()+memcpy(). This improvement could be attributed to 
better cache utilization (write-combining), NEON-assisted mem-copying in
aarch64, and etc. You may set use_sub_data=1 at your discretion.<br></div></div><div><br></div><div>---<br></div><div>diff --git a/src/iov.c b/src/iov.c<br>index aae995b..273e296 100644<br>--- a/src/iov.c<br>+++ b/src/iov.c<br>@@ -64,7 +64,7 @@ size_t vrend_read_from_iovec(const struct iovec *iov, int iovlen,<br>     if (iov->iov_len > offset) {<br>       len = iov->iov_len - offset;<br>       <br>-      if (count < iov->iov_len - offset) len = count;<br>+      if (count < len) len = count;<br> <br>       memcpy(buf, (char*)iov->iov_base + offset, len);<br>       read += len;<br>@@ -93,7 +93,7 @@ size_t vrend_write_to_iovec(const struct iovec *iov, int iovlen,<br>     if (iov->iov_len > offset) {<br>       len = iov->iov_len - offset;<br> <br>-      if (count < iov->iov_len - offset) len = count;<br>+      if (count < len) len = count;<br> <br>       memcpy((char*)iov->iov_base + offset, buf, len);<br>       written += len;<br>@@ -120,11 +120,11 @@ size_t vrend_read_from_iovec_cb(const struct iovec *iov, int iovlen,<br> <br>   while (count > 0 && iovlen > 0) {<br>     if (iov->iov_len > offset) {<br>-      len = iov->iov_len;<br>-      <br>-      if (count < iov->iov_len - offset) len = count;<br>+      len = iov->iov_len - offset;<br>+<br>+      if (count < len) len = count;<br> <br>-      (*iocb)(cookie, count, (char*)iov->iov_base + offset, len);<br>+      (*iocb)(cookie, read, (char*)iov->iov_base + offset, len);<br>       read += len;<br> <br>       count -= len;<br></div></div>