test_write_format_tar_sparse.c revision 358088
1/*- 2 * Copyright (c) 2003-2010 Tim Kientzle 3 * Copyright (c) 2012 Michihiro NAKAJIMA 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR 16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 17 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 18 * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT, 19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 20 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 24 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26#include "test.h" 27__FBSDID("$FreeBSD$"); 28 29static char buff[1000000]; 30 31static void 32test_1(void) 33{ 34 struct archive_entry *ae; 35 struct archive *a; 36 size_t used; 37 size_t blocksize; 38 int64_t offset, length; 39 char *buff2; 40 size_t buff2_size = 0x13000; 41 char buff3[1024]; 42 long i; 43 44 assert((buff2 = malloc(buff2_size)) != NULL); 45 /* Repeat the following for a variety of odd blocksizes. */ 46 for (blocksize = 1; blocksize < 100000; blocksize += blocksize + 3) { 47 /* Create a new archive in memory. */ 48 assert((a = archive_write_new()) != NULL); 49 assertEqualIntA(a, ARCHIVE_OK, 50 archive_write_set_format_pax(a)); 51 assertEqualIntA(a, ARCHIVE_OK, 52 archive_write_add_filter_none(a)); 53 assertEqualIntA(a, ARCHIVE_OK, 54 archive_write_set_bytes_per_block(a, (int)blocksize)); 55 assertEqualIntA(a, ARCHIVE_OK, 56 archive_write_set_bytes_in_last_block(a, (int)blocksize)); 57 assertEqualInt(blocksize, 58 archive_write_get_bytes_in_last_block(a)); 59 assertEqualIntA(a, ARCHIVE_OK, 60 archive_write_open_memory(a, buff, sizeof(buff), &used)); 61 assertEqualInt(blocksize, 62 archive_write_get_bytes_in_last_block(a)); 63 64 /* 65 * Write a file to it. 66 */ 67 assert((ae = archive_entry_new()) != NULL); 68 archive_entry_set_mtime(ae, 1, 10); 69 assertEqualInt(1, archive_entry_mtime(ae)); 70 assertEqualInt(10, archive_entry_mtime_nsec(ae)); 71 archive_entry_copy_pathname(ae, "file"); 72 assertEqualString("file", archive_entry_pathname(ae)); 73 archive_entry_set_mode(ae, S_IFREG | 0755); 74 assertEqualInt(S_IFREG | 0755, archive_entry_mode(ae)); 75 archive_entry_set_size(ae, 0x81000); 76 archive_entry_sparse_add_entry(ae, 0x10000, 0x1000); 77 archive_entry_sparse_add_entry(ae, 0x80000, 0x1000); 78 79 assertEqualIntA(a, ARCHIVE_OK, archive_write_header(a, ae)); 80 archive_entry_free(ae); 81 memset(buff2, 'a', buff2_size); 82 for (i = 0; i < 0x81000;) { 83 size_t ws = buff2_size; 84 if (i + ws > 0x81000) 85 ws = 0x81000 - i; 86 assertEqualInt(ws, 87 archive_write_data(a, buff2, ws)); 88 i += (long)ws; 89 } 90 91 /* Close out the archive. */ 92 assertEqualIntA(a, ARCHIVE_OK, archive_write_close(a)); 93 assertEqualInt(ARCHIVE_OK, archive_write_free(a)); 94 95 /* This calculation gives "the smallest multiple of 96 * the block size that is at least 11264 bytes". */ 97 failure("blocksize=%zu", blocksize); 98 assertEqualInt(((11264 - 1)/blocksize+1)*blocksize, used); 99 100 /* 101 * Now, read the data back. 102 */ 103 assert((a = archive_read_new()) != NULL); 104 assertEqualIntA(a, ARCHIVE_OK, 105 archive_read_support_format_all(a)); 106 assertEqualIntA(a, ARCHIVE_OK, 107 archive_read_support_filter_all(a)); 108 assertEqualIntA(a, ARCHIVE_OK, 109 archive_read_open_memory(a, buff, used)); 110 111 assertEqualIntA(a, ARCHIVE_OK, 112 archive_read_next_header(a, &ae)); 113 114 assertEqualInt(1, archive_entry_mtime(ae)); 115 assertEqualInt(10, archive_entry_mtime_nsec(ae)); 116 assertEqualInt(0, archive_entry_atime(ae)); 117 assertEqualInt(0, archive_entry_ctime(ae)); 118 assertEqualString("file", archive_entry_pathname(ae)); 119 assertEqualInt(AE_IFREG, archive_entry_filetype(ae)); 120 assertEqualInt(AE_IFREG | 0755, archive_entry_mode(ae)); 121 assertEqualInt(0x81000, archive_entry_size(ae)); 122 /* Verify sparse information. */ 123 assertEqualInt(2, archive_entry_sparse_reset(ae)); 124 assertEqualInt(0, 125 archive_entry_sparse_next(ae, &offset, &length)); 126 assertEqualInt(0x10000, offset); 127 assertEqualInt(0x1000, length); 128 assertEqualInt(0, 129 archive_entry_sparse_next(ae, &offset, &length)); 130 assertEqualInt(0x80000, offset); 131 assertEqualInt(0x1000, length); 132 /* Verify file contents. */ 133 memset(buff3, 0, sizeof(buff3)); 134 for (i = 0; i < 0x10000; i += 1024) { 135 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 136 failure("Read data(0x%lx - 0x%lx) should be all zero", 137 i, i + 1024); 138 assertEqualMem(buff2, buff3, 1024); 139 } 140 memset(buff3, 'a', sizeof(buff3)); 141 for (i = 0x10000; i < 0x11000; i += 1024) { 142 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 143 failure("Read data(0x%lx - 0x%lx) should be all 'a'", 144 i, i + 1024); 145 assertEqualMem(buff2, buff3, 1024); 146 } 147 memset(buff3, 0, sizeof(buff3)); 148 for (i = 0x11000; i < 0x80000; i += 1024) { 149 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 150 failure("Read data(0x%lx - 0x%lx) should be all zero", 151 i, i + 1024); 152 assertEqualMem(buff2, buff3, 1024); 153 } 154 memset(buff3, 'a', sizeof(buff3)); 155 for (i = 0x80000; i < 0x81000; i += 1024) { 156 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 157 failure("Read data(0x%lx - 0x%lx) should be all 'a'", 158 i, i + 1024); 159 assertEqualMem(buff2, buff3, 1024); 160 } 161 162 /* Verify the end of the archive. */ 163 assertEqualIntA(a, ARCHIVE_EOF, 164 archive_read_next_header(a, &ae)); 165 assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a)); 166 assertEqualInt(ARCHIVE_OK, archive_read_free(a)); 167 } 168 free(buff2); 169} 170 171/* 172 * Test for the case the full bytes of sparse file data is not written. 173 */ 174static void 175test_2(void) 176{ 177 struct archive_entry *ae; 178 struct archive *a; 179 size_t used; 180 size_t blocksize = 20 * 512; 181 int64_t offset, length; 182 char *buff2; 183 size_t buff2_size = 0x11000; 184 char buff3[1024]; 185 long i; 186 187 assert((buff2 = malloc(buff2_size)) != NULL); 188 /* Create a new archive in memory. */ 189 assert((a = archive_write_new()) != NULL); 190 assertEqualIntA(a, ARCHIVE_OK, 191 archive_write_set_format_pax(a)); 192 assertEqualIntA(a, ARCHIVE_OK, 193 archive_write_add_filter_none(a)); 194 assertEqualIntA(a, ARCHIVE_OK, 195 archive_write_set_bytes_per_block(a, (int)blocksize)); 196 assertEqualIntA(a, ARCHIVE_OK, 197 archive_write_set_bytes_in_last_block(a, (int)blocksize)); 198 assertEqualInt(blocksize, 199 archive_write_get_bytes_in_last_block(a)); 200 assertEqualIntA(a, ARCHIVE_OK, 201 archive_write_open_memory(a, buff, sizeof(buff), &used)); 202 assertEqualInt(blocksize, 203 archive_write_get_bytes_in_last_block(a)); 204 205 /* 206 * Write a file to it. 207 */ 208 assert((ae = archive_entry_new()) != NULL); 209 archive_entry_set_mtime(ae, 1, 10); 210 assertEqualInt(1, archive_entry_mtime(ae)); 211 assertEqualInt(10, archive_entry_mtime_nsec(ae)); 212 archive_entry_copy_pathname(ae, "file"); 213 assertEqualString("file", archive_entry_pathname(ae)); 214 archive_entry_set_mode(ae, S_IFREG | 0755); 215 assertEqualInt(S_IFREG | 0755, archive_entry_mode(ae)); 216 archive_entry_set_size(ae, 0x81000); 217 archive_entry_sparse_add_entry(ae, 0x10000, 0x1000); 218 archive_entry_sparse_add_entry(ae, 0x80000, 0x1000); 219 220 assertEqualIntA(a, ARCHIVE_OK, archive_write_header(a, ae)); 221 archive_entry_free(ae); 222 memset(buff2, 'a', buff2_size); 223 /* Write bytes less than it should be. */ 224 assertEqualInt(buff2_size, archive_write_data(a, buff2, buff2_size)); 225 226 /* Close out the archive. */ 227 assertEqualIntA(a, ARCHIVE_OK, archive_write_close(a)); 228 assertEqualInt(ARCHIVE_OK, archive_write_free(a)); 229 230 /* This calculation gives "the smallest multiple of 231 * the block size that is at least 11264 bytes". */ 232 failure("blocksize=%zu", blocksize); 233 assertEqualInt(((11264 - 1)/blocksize+1)*blocksize, used); 234 235 /* 236 * Now, read the data back. 237 */ 238 assert((a = archive_read_new()) != NULL); 239 assertEqualIntA(a, ARCHIVE_OK, archive_read_support_format_all(a)); 240 assertEqualIntA(a, ARCHIVE_OK, archive_read_support_filter_all(a)); 241 assertEqualIntA(a, ARCHIVE_OK, archive_read_open_memory(a, buff, used)); 242 243 assertEqualIntA(a, ARCHIVE_OK, archive_read_next_header(a, &ae)); 244 245 assertEqualInt(1, archive_entry_mtime(ae)); 246 assertEqualInt(10, archive_entry_mtime_nsec(ae)); 247 assertEqualInt(0, archive_entry_atime(ae)); 248 assertEqualInt(0, archive_entry_ctime(ae)); 249 assertEqualString("file", archive_entry_pathname(ae)); 250 assertEqualInt(AE_IFREG, archive_entry_filetype(ae)); 251 assertEqualInt(AE_IFREG | 0755, archive_entry_mode(ae)); 252 assertEqualInt(0x81000, archive_entry_size(ae)); 253 /* Verify sparse information. */ 254 assertEqualInt(2, archive_entry_sparse_reset(ae)); 255 assertEqualInt(0, archive_entry_sparse_next(ae, &offset, &length)); 256 assertEqualInt(0x10000, offset); 257 assertEqualInt(0x1000, length); 258 assertEqualInt(0, archive_entry_sparse_next(ae, &offset, &length)); 259 assertEqualInt(0x80000, offset); 260 assertEqualInt(0x1000, length); 261 /* Verify file contents. */ 262 memset(buff3, 0, sizeof(buff3)); 263 for (i = 0; i < 0x10000; i += 1024) { 264 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 265 failure("Read data(0x%lx - 0x%lx) should be all zero", 266 i, i + 1024); 267 assertEqualMem(buff2, buff3, 1024); 268 } 269 memset(buff3, 'a', sizeof(buff3)); 270 for (i = 0x10000; i < 0x11000; i += 1024) { 271 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 272 failure("Read data(0x%lx - 0x%lx) should be all 'a'", 273 i, i + 1024); 274 assertEqualMem(buff2, buff3, 1024); 275 } 276 memset(buff3, 0, sizeof(buff3)); 277 for (i = 0x11000; i < 0x80000; i += 1024) { 278 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 279 failure("Read data(0x%lx - 0x%lx) should be all zero", 280 i, i + 1024); 281 assertEqualMem(buff2, buff3, 1024); 282 } 283 memset(buff3, 0, sizeof(buff3)); 284 for (i = 0x80000; i < 0x81000; i += 1024) { 285 assertEqualInt(1024, archive_read_data(a, buff2, 1024)); 286 failure("Read data(0x%lx - 0x%lx) should be all 'a'", 287 i, i + 1024); 288 assertEqualMem(buff2, buff3, 1024); 289 } 290 291 /* Verify the end of the archive. */ 292 assertEqualIntA(a, ARCHIVE_EOF, 293 archive_read_next_header(a, &ae)); 294 assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a)); 295 assertEqualInt(ARCHIVE_OK, archive_read_free(a)); 296 free(buff2); 297} 298 299DEFINE_TEST(test_write_format_tar_sparse) 300{ 301 /* Test1: archiving sparse files. */ 302 test_1(); 303 /* Test2: incompletely archiving sparse files. */ 304 test_2(); 305} 306