if (!Py_off_t_converter(offobj, &offset))
return NULL;
+
+#if defined(__sun) && defined(__SVR4)
+ // On illumos specifically sendfile() may perform a partial write but
+ // return -1/an error (in one confirmed case the destination socket
+ // had a 5 second timeout set and errno was EAGAIN) and it's on the client
+ // code to check if the offset parameter was modified by sendfile().
+ //
+ // We need this variable to track said change.
+ off_t original_offset = offset;
+#endif
+
do {
Py_BEGIN_ALLOW_THREADS
ret = sendfile(out, in, &offset, count);
+#if defined(__sun) && defined(__SVR4)
+ // This handles illumos-specific sendfile() partial write behavior,
+ // see a comment above for more details.
+ if (ret < 0 && offset != original_offset) {
+ ret = offset - original_offset;
+ }
+#endif
Py_END_ALLOW_THREADS
} while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
if (ret < 0)