1 /* 2 * Copyright (c) 2015 Fujitsu Ltd. 3 * Author: Xiao Yang <yangx.jy (at) cn.fujitsu.com> 4 * 5 * This program is free software; you can redistribute it and/or modify it 6 * under the terms of version 2 of the GNU General Public License as 7 * published by the Free Software Foundation. 8 * 9 * This program is distributed in the hope that it would be useful, but 10 * WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 12 * 13 * You should have received a copy of the GNU General Public License 14 * alone with this program. 15 */ 16 17 /* 18 * Test Name: pwritev01 19 * 20 * Test Description: 21 * Testcase to check the basic functionality of the pwritev(2). 22 * pwritev(2) should succeed to write the expected content of data 23 * and after writing the file, the file offset is not changed. 24 */ 25 26 #include <string.h> 27 #include <sys/uio.h> 28 #include "tst_test.h" 29 #include "pwritev.h" 30 31 #define CHUNK 64 32 33 static char buf[CHUNK]; 34 static char initbuf[CHUNK * 2]; 35 static char preadbuf[CHUNK]; 36 static int fd; 37 38 static struct iovec wr_iovec[] = { 39 {buf, CHUNK}, 40 {NULL, 0}, 41 }; 42 43 static struct tcase { 44 int count; 45 off_t offset; 46 ssize_t size; 47 } tcases[] = { 48 {1, 0, CHUNK}, 49 {2, 0, CHUNK}, 50 {1, CHUNK/2, CHUNK}, 51 }; 52 53 static void verify_pwritev(unsigned int n) 54 { 55 int i; 56 struct tcase *tc = &tcases[n]; 57 58 SAFE_PWRITE(1, fd, initbuf, sizeof(initbuf), 0); 59 60 SAFE_LSEEK(fd, 0, SEEK_SET); 61 62 TEST(pwritev(fd, wr_iovec, tc->count, tc->offset)); 63 if (TEST_RETURN < 0) { 64 tst_res(TFAIL | TTERRNO, "pwritev() failed"); 65 return; 66 } 67 68 if (TEST_RETURN != tc->size) { 69 tst_res(TFAIL, "pwritev() wrote %li bytes, expected %li", 70 TEST_RETURN, tc->size); 71 return; 72 } 73 74 if (SAFE_LSEEK(fd, 0, SEEK_CUR) != 0) { 75 tst_res(TFAIL, "pwritev() had changed file offset"); 76 return; 77 } 78 79 SAFE_PREAD(1, fd, preadbuf, tc->size, tc->offset); 80 81 for (i = 0; i < tc->size; i++) { 82 if (preadbuf[i] != 0x61) 83 break; 84 } 85 86 if (i != tc->size) { 87 tst_res(TFAIL, "buffer wrong at %i have %02x expected 61", 88 i, preadbuf[i]); 89 return; 90 } 91 92 tst_res(TPASS, "writev() wrote %li bytes successfully " 93 "with content 'a' expectedly ", tc->size); 94 } 95 96 static void setup(void) 97 { 98 memset(&buf, 0x61, CHUNK); 99 100 fd = SAFE_OPEN("file", O_RDWR | O_CREAT, 0644); 101 } 102 103 static void cleanup(void) 104 { 105 if (fd > 0 && close(fd)) 106 tst_res(TWARN | TERRNO, "failed to close file"); 107 } 108 109 static struct tst_test test = { 110 .tid = "pwritev01", 111 .tcnt = ARRAY_SIZE(tcases), 112 .setup = setup, 113 .cleanup = cleanup, 114 .test = verify_pwritev, 115 .min_kver = "2.6.30", 116 .needs_tmpdir = 1, 117 }; 118