2 * Copyright (c) 2000 Silicon Graphics, Inc. All Rights Reserved.
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of version 2 of the GNU General Public License as
6 * published by the Free Software Foundation.
8 * This program is distributed in the hope that it would be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 * Further, this software is distributed without any warranty that it is
13 * free of the rightful claim of any third person regarding infringement
14 * or the like. Any license provided herein, whether implied or
15 * otherwise, applies only to this software file. Patent licenses, if
16 * any, provided herein do not apply to combinations of this program with
17 * other software, or any other product whatsoever.
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, write the Free Software Foundation, Inc., 59
21 * Temple Place - Suite 330, Boston MA 02111-1307, USA.
23 * Contact information: Silicon Graphics, Inc., 1600 Amphitheatre Pkwy,
24 * Mountain View, CA 94043, or:
28 * For further information regarding this notice, see:
30 * http://oss.sgi.com/projects/GenInfo/SGIGPLNoticeExplan/
33 #include <sys/types.h>
37 #include <lib/errtest.h>
43 /*---------------------------------------------------------------------------
45 Test program used to test the DMAPI function dm_punch_hole(). The
48 test_hole [-v] [-s sid] pathname
52 is the path to a specific copy of ls, important only for its size
54 is the path to the test filesystem
56 is the session ID whose events you you are interested in.
58 ----------------------------------------------------------------------------*/
61 extern char *sys_errlist[];
74 fprintf(stderr, "usage:\t%s [-v] [-s sid] ls_path directoryname\n",
85 dm_sessid_t sid = DM_NO_SESSION;
86 char *pathname = NULL;
90 dm_extent_t extent[20];
95 dm_token_t test_token;
104 dm_off_t blocksize = 5;
107 struct stat checkbuf;
110 if (Progname = strrchr(argv[0], '/')) {
116 /* Crack and validate the command line options. */
118 while ((opt = getopt(argc, argv, "vs:")) != EOF) {
130 if (optind + 2 != argc)
132 ls_path = argv[optind];
133 pathname = argv[optind+1];
135 if (dm_init_service(&name) == -1) {
136 fprintf(stdout, "Can't inititalize the DMAPI\n");
139 if (sid == DM_NO_SESSION)
140 find_test_session(&sid);
142 /* Get the directory handle. */
144 if (dm_path_to_handle(pathname, &hanp, &hlen)) {
146 "ERROR: can't get handle for directory %s\n", pathname);
150 printf("Hole test beginning...\n");
151 sprintf(filename, "%s/VeryLongUnlikelyFilename.HOLETEST", pathname);
152 sprintf(command, "cp %s %s \n", ls_path, filename);
155 if (dm_path_to_handle(filename, &hanp, &hlen)) {
156 fprintf(stdout, "can't get handle for %s\n; aborting test",
159 sprintf(command, "rm %s \n", filename);
161 fprintf(stdout, "\tHole test aborted.\n");
163 dm_handle_free(hanp, hlen);
167 /* ## Get the block size using a length-1 probe. ## */
168 dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, 1, 0,
172 fprintf(stdout, "Error: block size appears to be 0!\n");
174 sprintf(command, "rm %s \n", filename);
176 fprintf(stdout, "\tHole test aborted.\n");
178 dm_handle_free(hanp, hlen);
182 /* Check that dm_probe_hole returns an extent from the next
183 * highest multiple of the block size, to the end of the file
186 for (offset = 0; offset < 29604; offset++) {
187 if (dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, offset, length,
189 fprintf(stdout, "dm_probe_hole failed on pass %lld (%s)\n",
190 (long long)offset, ERR_NAME);
195 "Error: hole did not extend to end of file!\n");
197 if (blocksize*(roff/blocksize) != roff) {
199 "Error: offset not a multiple of block size!\n");
204 /* Be sure dm_punch_hole doesn't change the time stamp,
205 * and verify that dm_get_allocinfo shows a hole
206 * followed by an extent to the end of the file.
208 for(offset = 28672; offset > 0; offset-=blocksize) {
209 if (stat(filename, &buf)){
211 "Error: unable to stat the test file; %s (1st)\n",
215 if (dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, offset, length,
217 fprintf(stdout, "dm_probe_hole failed, %s\n",
221 if (roff != offset) {
223 "Error: presumed offset was not %lld.\n",
226 if (dm_punch_hole(sid, hanp, hlen, DM_NO_TOKEN,
228 fprintf(stdout, "dm_punch_hole failed, %s\n",
232 if (stat(filename, &checkbuf)){
234 "Error: unable to stat the test file. (2nd)\n");
238 /* COMPARE BUF AND CHECKBUF! */
240 if ((buf.st_atime == checkbuf.st_atime) &&
241 (buf.st_mtime == checkbuf.st_mtime) &&
242 (buf.st_ctime == checkbuf.st_ctime))
244 if ((buf.st_atim.tv_sec == checkbuf.st_atim.tv_sec) &&
245 (buf.st_atim.tv_nsec == checkbuf.st_atim.tv_nsec) &&
246 (buf.st_mtim.tv_sec == checkbuf.st_mtim.tv_sec) &&
247 (buf.st_mtim.tv_nsec == checkbuf.st_mtim.tv_nsec) &&
248 (buf.st_ctim.tv_sec == checkbuf.st_ctim.tv_sec) &&
249 (buf.st_ctim.tv_nsec == checkbuf.st_ctim.tv_nsec))
254 "\tTime stamp unchanged by hole from offset %lld.\n",
255 (long long)(offset));
260 "Error: punch_hole changed file's time stamp.\n");
263 if ((dm_get_allocinfo(sid, hanp, hlen, DM_NO_TOKEN,
264 &ex_off, 1, extent, &nelem) == 1) &&
265 (extent->ex_type == DM_EXTENT_RES) &&
266 (dm_get_allocinfo(sid, hanp, hlen, DM_NO_TOKEN,
267 &ex_off, 1, extent, &nelem) == 0) &&
268 (extent->ex_type == DM_EXTENT_HOLE)) {
269 if (extent->ex_offset == roff){
271 fprintf(stdout, "\tVerified hole at %lld\n",
272 (long long)(extent->ex_offset));
276 fprintf(stdout, "\tError: get_allocinfo found hole at %lld\n",
277 (long long)(extent->ex_offset));
281 fprintf(stdout, "\tError: get_allocinfo did not find an "
282 "extent followed by a hole!\n");
286 /*------------------------*\
287 |* ## Errno subtests ## *|
288 \*------------------------*/
289 fprintf(stdout, "\t(beginning errno subtests...)\n");
290 /*---------------------------------------------------------*/
292 "probe (from past EOF)",
293 dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, 30000, length,
295 /*---------------------------------------------------------*/
297 PROBLEM: No error is produced.
298 off+len >= filesize should produce E2BIG...
301 "probe (to past EOF)",
302 dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, 15000, 150000,
305 /*---------------------------------------------------------*/
306 SHAREDTEST("probe", hanp, hlen, test_token,
307 dm_probe_hole(sid, hanp, hlen, test_token,
309 /*---------------------------------------------------------*/
310 EXCLTEST("punch", hanp, hlen, test_token,
311 dm_punch_hole(sid, hanp, hlen, test_token, 0, 0))
312 /*---------------------------------------------------------*/
315 dm_punch_hole(sid, hanp, hlen, DM_NO_TOKEN,
317 /*---------------------------------------------------------*/
318 if ((test_vp = handle_clone(hanp, hlen)) == NULL) {
320 "Cannot create a test handle (%s); skipping EBADF test\n",
324 ((char *) test_vp)[hlen/2]++;
327 dm_probe_hole(sid, test_vp, hlen, DM_NO_TOKEN,
332 dm_punch_hole(sid, test_vp, hlen, DM_NO_TOKEN,
335 dm_handle_free(test_vp, hlen);
336 /*---------------------------------------------------------*/
338 "probe (null handle)",
339 dm_probe_hole(sid, 0, hlen, DM_NO_TOKEN, offset, length,
343 dm_probe_hole(sid, 0, hlen, DM_NO_TOKEN, offset, length,
344 &roff, (dm_size_t*)(-1000)))
347 dm_probe_hole(sid, hanp, hlen, DM_NO_TOKEN, offset, length,
348 (dm_off_t*)(-1000), &rlen))
349 /*---------------------------------------------------------*/
352 dm_punch_hole(sid, 0, hlen, DM_NO_TOKEN, offset, length))
353 /*---------------------------------------------------------*/
355 "probe (bad session)",
356 dm_probe_hole(-100, hanp, hlen, DM_NO_TOKEN, offset, length,
358 /*---------------------------------------------------------*/
361 dm_probe_hole(sid, hanp, hlen, 0, offset, length,
363 /*---------------------------------------------------------*/
365 "probe (bad token 2)",
366 dm_probe_hole(sid, hanp, hlen, 0, offset, length,
368 /*---------------------------------------------------------*/
369 fprintf(stdout, "\t(errno subtests complete)\n");
372 sprintf(command, "rm %s \n", filename);
374 printf("Hole test complete.\n");
376 dm_handle_free(hanp, hlen);