1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * tools/testing/selftests/kvm/lib/io.c 4 * 5 * Copyright (C) 2018, Google LLC. 6 */ 7 8 #include "test_util.h" 9 10 /* Test Write 11 * 12 * A wrapper for write(2), that automatically handles the following 13 * special conditions: 14 * 15 * + Interrupted system call (EINTR) 16 * + Write of less than requested amount 17 * + Non-block return (EAGAIN) 18 * 19 * For each of the above, an additional write is performed to automatically 20 * continue writing the requested data. 21 * There are also many cases where write(2) can return an unexpected 22 * error (e.g. EIO). Such errors cause a TEST_ASSERT failure. 23 * 24 * Note, for function signature compatibility with write(2), this function 25 * returns the number of bytes written, but that value will always be equal 26 * to the number of requested bytes. All other conditions in this and 27 * future enhancements to this function either automatically issue another 28 * write(2) or cause a TEST_ASSERT failure. 29 * 30 * Args: 31 * fd - Opened file descriptor to file to be written. 32 * count - Number of bytes to write. 33 * 34 * Output: 35 * buf - Starting address of data to be written. 36 * 37 * Return: 38 * On success, number of bytes written. 39 * On failure, a TEST_ASSERT failure is caused. 40 */ 41 ssize_t test_write(int fd, const void *buf, size_t count) 42 { 43 ssize_t rc; 44 ssize_t num_written = 0; 45 size_t num_left = count; 46 const char *ptr = buf; 47 48 /* Note: Count of zero is allowed (see "RETURN VALUE" portion of 49 * write(2) manpage for details. 50 */ 51 TEST_ASSERT(count >= 0, "Unexpected count, count: %li", count); 52 53 do { 54 rc = write(fd, ptr, num_left); 55 56 switch (rc) { 57 case -1: 58 TEST_ASSERT(errno == EAGAIN || errno == EINTR, 59 "Unexpected write failure,\n" 60 " rc: %zi errno: %i", rc, errno); 61 continue; 62 63 case 0: 64 TEST_ASSERT(false, "Unexpected EOF,\n" 65 " rc: %zi num_written: %zi num_left: %zu", 66 rc, num_written, num_left); 67 break; 68 69 default: 70 TEST_ASSERT(rc >= 0, "Unexpected ret from write,\n" 71 " rc: %zi errno: %i", rc, errno); 72 num_written += rc; 73 num_left -= rc; 74 ptr += rc; 75 break; 76 } 77 } while (num_written < count); 78 79 return num_written; 80 } 81 82 /* Test Read 83 * 84 * A wrapper for read(2), that automatically handles the following 85 * special conditions: 86 * 87 * + Interrupted system call (EINTR) 88 * + Read of less than requested amount 89 * + Non-block return (EAGAIN) 90 * 91 * For each of the above, an additional read is performed to automatically 92 * continue reading the requested data. 93 * There are also many cases where read(2) can return an unexpected 94 * error (e.g. EIO). Such errors cause a TEST_ASSERT failure. Note, 95 * it is expected that the file opened by fd at the current file position 96 * contains at least the number of requested bytes to be read. A TEST_ASSERT 97 * failure is produced if an End-Of-File condition occurs, before all the 98 * data is read. It is the callers responsibility to assure that sufficient 99 * data exists. 100 * 101 * Note, for function signature compatibility with read(2), this function 102 * returns the number of bytes read, but that value will always be equal 103 * to the number of requested bytes. All other conditions in this and 104 * future enhancements to this function either automatically issue another 105 * read(2) or cause a TEST_ASSERT failure. 106 * 107 * Args: 108 * fd - Opened file descriptor to file to be read. 109 * count - Number of bytes to read. 110 * 111 * Output: 112 * buf - Starting address of where to write the bytes read. 113 * 114 * Return: 115 * On success, number of bytes read. 116 * On failure, a TEST_ASSERT failure is caused. 117 */ 118 ssize_t test_read(int fd, void *buf, size_t count) 119 { 120 ssize_t rc; 121 ssize_t num_read = 0; 122 size_t num_left = count; 123 char *ptr = buf; 124 125 /* Note: Count of zero is allowed (see "If count is zero" portion of 126 * read(2) manpage for details. 127 */ 128 TEST_ASSERT(count >= 0, "Unexpected count, count: %li", count); 129 130 do { 131 rc = read(fd, ptr, num_left); 132 133 switch (rc) { 134 case -1: 135 TEST_ASSERT(errno == EAGAIN || errno == EINTR, 136 "Unexpected read failure,\n" 137 " rc: %zi errno: %i", rc, errno); 138 break; 139 140 case 0: 141 TEST_ASSERT(false, "Unexpected EOF,\n" 142 " rc: %zi num_read: %zi num_left: %zu", 143 rc, num_read, num_left); 144 break; 145 146 default: 147 TEST_ASSERT(rc > 0, "Unexpected ret from read,\n" 148 " rc: %zi errno: %i", rc, errno); 149 num_read += rc; 150 num_left -= rc; 151 ptr += rc; 152 break; 153 } 154 } while (num_read < count); 155 156 return num_read; 157 } 158