From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on inbox.vuxu.org X-Spam-Level: X-Spam-Status: No, score=-1.5 required=5.0 tests=DKIM_INVALID,DKIM_SIGNED, MAILING_LIST_MULTI,RCVD_IN_DNSWL_LOW autolearn=ham autolearn_force=no version=3.4.4 Received: (qmail 10690 invoked from network); 10 Sep 2021 14:19:11 -0000 Received: from lists.zx2c4.com (165.227.139.114) by inbox.vuxu.org with ESMTPUTF8; 10 Sep 2021 14:19:11 -0000 Received: by lists.zx2c4.com (ZX2C4 Mail Server) with ESMTP id 7b439dcc; Fri, 10 Sep 2021 14:18:58 +0000 (UTC) Return-Path: Received: from a1-bg02.venev.name (a1-bg02.venev.name [213.240.239.49]) by lists.zx2c4.com (ZX2C4 Mail Server) with ESMTPS id 0359ab9c (TLSv1.3:AEAD-AES256-GCM-SHA384:256:NO) for ; Fri, 10 Sep 2021 14:18:55 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=venev.name; s=default; h=Content-Transfer-Encoding:MIME-Version:Message-Id:Date:Subject: Cc:To:From:Sender:Reply-To:Content-Type:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: In-Reply-To:References:List-Id:List-Help:List-Unsubscribe:List-Subscribe: List-Post:List-Owner:List-Archive; bh=sr7IjAkDKjD5djFhJoaoNNOcZa5G5UlvWG3BcWM2ufo=; b=cNY/tOD675KiU8B0AOKo7AexF3 g/zS0jT3b0gv3IBSSJpI2EeHI6YsH2VQ39e5Udob1DUHF3BXR1suwpoiF7+HXH2FkeqNqzqh5ywSH FszSHJd3kYOWVLvI+Es7Bc0ujqmCr15rjHcwGvwtCasb0OaOzxamPAjatsYS7/PnbYRgkcLuV7nkB DHtxQQdBjstOVfAm55sTbi/1j2gOq60Lsd93LQDOHaWO/WWnngfFcEQ9NM2iHJUmDb5ddK4hHdICc whJnZnR52DRQI0GLd8W6kHKfZ7RQ11SjHNK3+nlobUd83aVRRy8shCzVAiQFSZsakYYLGL8j2iU8e rn5yavQNmmm8mi4K5JoXIcLe6TJ3lmPfQ9egdCLDvbkp4kFzrijo1jiMWZMWbQmfgKTEtKZVH2+FE 4rLzEkbcFzcekx/pQbgwdbmFHyDnnDbki1gnqhqVcuJ8k91MOktbTqKvNFS2TjCjoefxHbXdrbGdj dx3ReNeRsO81F4sX3jS2NOyr//YQa7zs/GLyjzkY0/WxzZDBGBBZhkEfluWcbAp7Oz3AgRw3XDm/e vbnCevwsQbsRkDYDaeTS+/Vlop3e0URQUYDrUf1gh3imNfbVvdjaw2Cs/G9hGkrvDNHf6+w+3o+Sj fffLitHFBVdfssv+tTf9EYYxVx8lTsqFWlv8Ya1bU=; X-Check-Malware: ok Received: from a1-bg02.venev.name ([213.240.239.49] helo=pmx1.venev.name) by a1-bg02.venev.name with esmtps id 1mOhMk-008mOL-83 (TLS1.3:TLS_AES_256_GCM_SHA384:256) (envelope-from ); Fri, 10 Sep 2021 14:18:54 +0000 Received: from venev.name ([213.240.239.49]) by pmx1.venev.name with ESMTPSA id bjGRDk5pO2Fh7h8AdB6GMg (envelope-from ); Fri, 10 Sep 2021 14:18:54 +0000 From: Hristo Venev To: cgit@lists.zx2c4.com Cc: Hristo Venev Subject: [PATCH] cache: Tolerate short writes in print_slot Date: Fri, 10 Sep 2021 17:18:41 +0300 Message-Id: <20210910141841.2092532-1-hristo@venev.name> X-Mailer: git-send-email 2.31.1 MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-BeenThere: cgit@lists.zx2c4.com X-Mailman-Version: 2.1.30rc1 Precedence: list List-Id: List for cgit developers and users List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: cgit-bounces@lists.zx2c4.com Sender: "CGit" sendfile() can return after a short read/write, so we may need to call it more than once. Furthermore, not all files support sendfile(), so we may need to fall back to read/write. On the read/write path, use write_in_full which deals with short writes. Signed-off-by: Hristo Venev --- cache.c | 46 ++++++++++++++++++++++++---------------------- 1 file changed, 24 insertions(+), 22 deletions(-) diff --git a/cache.c b/cache.c index 55199e8..85cfbd9 100644 --- a/cache.c +++ b/cache.c @@ -85,40 +85,42 @@ static int close_slot(struct cache_slot *slot) /* Print the content of the active cache slot (but skip the key). */ static int print_slot(struct cache_slot *slot) { -#ifdef HAVE_LINUX_SENDFILE - off_t start_off; - int ret; + off_t off; + ssize_t i; + + off = slot->keylen + 1; - start_off = slot->keylen + 1; +#ifdef HAVE_LINUX_SENDFILE + off_t size; + size = slot->cache_st.st_size; do { - ret = sendfile(STDOUT_FILENO, slot->cache_fd, &start_off, - slot->cache_st.st_size - start_off); - if (ret < 0) { + i = sendfile(STDOUT_FILENO, slot->cache_fd, &off, size - off); + if (i < 0) { if (errno == EAGAIN || errno == EINTR) continue; + /* Fall back to read/write on EINVAL */ + if (errno == EINVAL) + break; return errno; } - return 0; + if (off == size) + return 0; } while (1); -#else - ssize_t i, j; +#endif - i = lseek(slot->cache_fd, slot->keylen + 1, SEEK_SET); - if (i != slot->keylen + 1) + if (lseek(slot->cache_fd, off, SEEK_SET) != off) return errno; do { - i = j = xread(slot->cache_fd, slot->buf, sizeof(slot->buf)); - if (i > 0) - j = xwrite(STDOUT_FILENO, slot->buf, i); - } while (i > 0 && j == i); - - if (i < 0 || j != i) - return errno; - else - return 0; -#endif + i = xread(slot->cache_fd, slot->buf, sizeof(slot->buf)); + if (i < 0) + return errno; + if (i == 0) + return 0; + if (write_in_full(STDOUT_FILENO, slot->buf, i) < 0) + return errno; + } while (1); } /* Check if the slot has expired */ -- 2.31.1