summaryrefslogtreecommitdiffstats
path: root/tools/h5recover/trecover_writer.c
blob: 950f4b9d31a6e273c15359fa0b3f94c646180937 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
 * Copyright by The HDF Group.                                               *
 * All rights reserved.                                                      *
 *                                                                           *
 * This file is part of HDF5.  The full HDF5 copyright notice, including     *
 * terms governing use, modification, and redistribution, is contained in    *
 * the files COPYING and Copyright.html.  COPYING can be found at the root   *
 * of the source code distribution tree; Copyright.html can be found at the  *
 * root level of an installed copy of the electronic HDF5 document set and   *
 * is linked from the top-level documents page.  It can also be found at     *
 * http://hdfgroup.org/HDF5/doc/Copyright.html.  If you do not have          *
 * access to either file, you may request a copy from help@hdfgroup.org.     *
 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

/*  
 * writer HDF5 API module of the trecover test program.
 *
 * Creator: Albert Cheng, Jan 28, 2008.
 */
 
#include "trecover.h"

int
create_files(const char *filename, const char *ctl_filename)
{
    /*
     * Create a new file and the control file using H5F_ACC_TRUNC access,
     * default file creation properties, and latest lib version file
     * access properties.
     */
    hid_t       faccpl;         /* file access property list handle */

    faccpl = H5Pcreate(H5P_FILE_ACCESS);
    if (H5Pset_libver_bounds(faccpl, H5F_LIBVER_LATEST, H5F_LIBVER_LATEST) < 0){
	fprintf(stderr, "H5Pset_libver_bounds on data file failed\n");
	H5Pclose(faccpl);
	return(-1);
    }
    /* remove any existing test files. */
    remove(filename);
    remove(ctl_filename);
    datafile = H5Fcreate(filename, H5F_ACC_TRUNC, H5P_DEFAULT, faccpl);
    ctl_file = H5Fcreate(ctl_filename, H5F_ACC_TRUNC, H5P_DEFAULT, faccpl);

    return(0);
}

int
journal_files(const char *filename, const char *ctl_filename, const char *jnl_filename, int patch)
{
    /*
     * Create a new file and the control file using H5F_ACC_TRUNC access,
     * default file creation properties, and latest lib version file
     * access properties.
     */
    hid_t       faccpl;         /* file access property list handle */
    H5AC2_jnl_config_t jnl_config;

    faccpl = H5Pcreate(H5P_FILE_ACCESS);
    /* Turn journaling on if not patch mode */
    if (!patch){

    /* set latest format */
    if ( H5Pset_libver_bounds(faccpl, H5F_LIBVER_LATEST, H5F_LIBVER_LATEST ) 
         < 0 ) {
        fprintf(stderr, "H5Pset_libver_bounds on data file failed\n");
        H5Pclose(faccpl);
        return(-1);
    }

    /* get current journaling configuration */
    jnl_config.version = H5AC2__CURR_JNL_CONFIG_VER;

    if ( H5Pget_jnl_config(faccpl, &jnl_config) < 0 ) {
        fprintf(stderr, "H5Pget_jnl_config on faccpl failed\n");
        H5Pclose(faccpl);
        return(-1);
    }

    jnl_config.enable_journaling = 1;     /* turn on journaling */
    jnl_config.journal_recovered = 0;
    jnl_config.jbrb_buf_size = 8*1024;    /* multiples of sys buffer size*/
    jnl_config.jbrb_num_bufs = 2;
    jnl_config.jbrb_use_aio = 0;          /* only sync IO is supported */
    jnl_config.jbrb_human_readable = 1;   /* only readable form is supported */
    strcpy(jnl_config.journal_file_path, jnl_filename);

    if ( H5Pset_jnl_config(faccpl, &jnl_config) < 0 ) {
        fprintf(stderr, "H5Pset_jnl_config on faccpl failed\n");
        H5Pclose(faccpl);
        return(-1);
    }

	/* remove any existing journal file. */
	remove(jnl_filename);
    }
    datafile = H5Fopen(filename, H5F_ACC_RDWR, faccpl);
    ctl_file = H5Fopen(ctl_filename, H5F_ACC_RDWR, H5P_DEFAULT);
    H5Pclose(faccpl);

    return(0);
}

int
close_file(hid_t fid)
{
    H5Fclose(fid);

    return(0);
}

void
create_dataset(hid_t f, int dstype, int rank, hsize_t *dims, hsize_t *dimschunk)
{
    hid_t       dataset;         /* dataset handle */
    hid_t       dataspace, plist;      /* handles */
    herr_t      status;                             
    hsize_t 	maxdims[RANK]; 		/* Dataset dimensions */

    /* Default to create an unlimited dimension dataset unless contigous
     * storeage is used.
     */
    if (dstype & DSContig)
	dataspace = H5Screate_simple(rank, dims, NULL); 
    else{
	maxdims[0]=H5S_UNLIMITED;
	maxdims[1]=NY;
	dataspace = H5Screate_simple(rank, dims, maxdims); 
    }
    /*
     * Describe the size of the array and create the data space for fixed
     * size dataset. 
     */

    if (dstype & DSContig) {
    /* =============================================================
     * Create a new dataset within the file using defined dataspace and
     * datatype and default dataset creation properties.
     * =============================================================
     */
    dataset = H5Dcreate2(f, DATASETNAME, H5T_STD_I32LE, dataspace,
			H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT);

    /*
     * Write the data to the dataset using default transfer properties.
     */
    status = writedata(dataset, 0, NX-1);

    /*
     * Close/release resources.
     */
    H5Dclose(dataset);
    printf("%s created.\n", DATASETNAME);
    }

    if (dstype & DSChunked) {
    /* =============================================================
     * Create a new dataset within the file using defined dataspace and
     * datatype and default dataset creation properties.
     * =============================================================
     */
    plist     = H5Pcreate(H5P_DATASET_CREATE);
                H5Pset_chunk(plist, rank, dimschunk);
    dataset = H5Dcreate2(f, CHUNKDATASETNAME, H5T_STD_I32LE,
                        dataspace, H5P_DEFAULT, plist, H5P_DEFAULT);
    /*
     * Write the data to the dataset using default transfer properties.
     */
    status = writedata(dataset, 0, NX-1);
    /*
     * Close/release resources.
     */
    H5Pclose(plist);
    H5Dclose(dataset);
    printf("%s created.\n", CHUNKDATASETNAME);
    }

    if (dstype & DSZip){
#ifdef H5_HAVE_FILTER_DEFLATE
    /* =============================================================
     * Create similar dataset but using Zlib compression.
     * Dataset creation property list is modified to use
     * GZIP compression with the compression effort set to 6.
     * Note that compression can be used only when dataset is chunked.
     * =============================================================
     */
    plist     = H5Pcreate(H5P_DATASET_CREATE);
                H5Pset_chunk(plist, rank, dimschunk);
                H5Pset_deflate( plist, 6);
    dataset = H5Dcreate2(f, ZDATASETNAME, H5T_STD_I32LE,
                        dataspace, H5P_DEFAULT, plist, H5P_DEFAULT);
    status = writedata(dataset, 0, NX-1);


    /*
     * Close/release resources.
     */
    H5Pclose(plist);
    H5Dclose(dataset);
    printf("%s created.\n", ZDATASETNAME);
#else
    printf("%s is not created because of no GZIP (deflate) support.\n",
	ZDATASETNAME);
#endif
    }

    if (dstype & DSSZip){
#ifdef H5_HAVE_FILTER_SZIP
    /* =============================================================
     * Create similar dataset but using SZLIB compression.
     * Dataset creation property list is modified to use
     * SZIP compression with 8 pixels_per_block.
     * Note that compression can be used only when dataset is chunked.
     * =============================================================
     */
    plist     = H5Pcreate(H5P_DATASET_CREATE);
                H5Pset_chunk(plist, rank, dimschunk);
		H5Pset_szip (plist, H5_SZIP_NN_OPTION_MASK, 8);
    dataset = H5Dcreate2(f, SZDATASETNAME, H5T_STD_I32LE,
                        dataspace, H5P_DEFAULT, plist, H5P_DEFAULT);
    status = writedata(dataset, 0, NX-1);


    /*
     * Close/release resources.
     */
    H5Pclose(plist);
    H5Dclose(dataset);
    printf("%s created.\n", SZDATASETNAME);
#else
    printf("%s is not created because of no SZIP encode support.\n",
	SZDATASETNAME);
#endif
    }



    /* 
     * All done, close/release resources.
     */
    H5Sclose(dataspace);

    return;
}     


/* extend the dataset size to end rows.  If it is not patch,
 * write data from begin to end rows. (begin and end are 0 based).
 */
int
extend_dataset(hid_t f, int begin, int end, int patch)
{
    hid_t       dataset;         /* dataset handle */
    hid_t       dataspace;      /* handles */
    hsize_t 	currdims[RANK]; 	/* Dataset current dimensions */

    /* argument checks */
    if ((end < begin) || (begin < 0)){
	fprintf(stderr, "writedata: bad arguments (begin=%d, end=%d)\n", begin, end);
	return(-1);
    }

    dataset=H5Dopen2(f, dsetname, H5P_DEFAULT);
    /* get dimensions */
    if ( (dataspace = H5Dget_space(dataset)) < 0 )
        return(-1);
    if ( H5Sget_simple_extent_dims(dataspace,currdims,NULL) < 0 )
        return(-1);

    /* extend the dataset if needed. */
    if (end >= currdims[0]){
	currdims[0] = end+1;
	if (H5Dset_extent(dataset, currdims)<0)
	    return(-1);
    }
    if (!patch)
	writedata(dataset, begin, end);
    H5Dclose(dataset);
    return(0);
}


/* writedata():
 * write rows of data to dataset starting from begin to end rows inclusive.
 */
int
writedata(hid_t dataset, int begin, int end)
{
    int         data[NX][NY];          /* data to write */
    int         nrows, i, j;
    hid_t	memspace, dataspace;
    hsize_t	dims[RANK], start[RANK], count[RANK];
    int		beginInc;

    /* Argument values check */
    if ((end < begin) || (begin < 0)){
	fprintf(stderr, "writedata: bad arguments (begin=%d, end=%d)\n", begin, end);
	return(-1);
    }

    dims[0]=NX;
    dims[1]=NY;
    memspace = H5Screate_simple(RANK, dims, NULL);
    dataspace = H5Dget_space(dataset);

    /* write data NX rows at a time. */
    beginInc = begin;
    nrows = NX;
    while (beginInc <= end){
	if (beginInc+nrows-1 > end)
	    nrows=end-beginInc+1;	/* last fragment of rows */
	
	start[0]=beginInc;
	start[1]=0;
	count[0]=nrows;
	count[1]=NY;
	if (H5Sselect_hyperslab(dataspace, H5S_SELECT_SET, start,
			NULL, count, NULL) <0){
	    fprintf(stderr, "H5Sselect_hyperslab failed\n");
	    return(-1);
	};

	/* Initialize data buffer */
	for(i = 0; i < nrows; i++)
	    for(j = 0; j < NY; j++)
		data[i][j] = (i+beginInc)*NY + j;

	/*
	 * Write the data to the dataset using default transfer properties.
	 */
	if (H5Dwrite(dataset, H5T_NATIVE_INT, memspace, dataspace, H5P_DEFAULT,
		    data)<0)
	    return(-1);
	beginInc += nrows;
    }
    H5Sclose(memspace);
    H5Sclose(dataspace);
    return(0);
}