1 /* This file is part of MED.
2 *
3 * COPYRIGHT (C) 1999 - 2019 EDF R&D, CEA/DEN
4 * MED is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU Lesser General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
8 *
9 * MED is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public License
15 * along with MED. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18 #include <med.h>
19 #include <med_config.h>
20 #include <med_outils.h>
21 #include <hdf5.h>
22 #include "med_utils.h"
23
_MEDdatasetWr(const med_idt id,const char * const datasetname,const med_internal_type datatype,const med_filter * const filter,const void * const value)24 med_err _MEDdatasetWr(const med_idt id,
25 const char * const datasetname,
26 const med_internal_type datatype,
27 const med_filter* const filter,
28 const void * const value) {
29
30 med_idt _dataset=0, _dataspace=0,_datadiskspace=0;
31 med_size _datasetsize[1]={0};
32 med_err _ret=-1;
33 med_idt _hdftype=0;
34 int _datasetsizeEqualTosizespace = 0;
35 med_access_mode _MED_ACCESS_MODE;
36 med_int _nvaluesperentity=0,_nconstituentpervalue=0;
37 int _i=0;
38 H5L_info_t _linkinfo;
39 hsize_t _dim=0;
40 const void *_value= value;
41
42 /* ISCRUTE((*filter).nentity ); */
43 /* ISCRUTE((*filter).nvaluesperentity ); */
44 /* ISCRUTE((*filter).nconstituentpervalue ); */
45 /* ISCRUTE((*filter).constituentselect ); */
46 /* ISCRUTE((*filter).switchmode ); */
47 /* ISCRUTE((*filter).filterarraysize ); */
48 /* ISCRUTE((*filter).profilearraysize ); */
49 /* ISCRUTE((*filter).storagemode ); */
50 /* SSCRUTE((*filter).profilename ); */
51
52
53 if ( (_MED_ACCESS_MODE = _MEDmodeAcces(id) ) == MED_ACC_UNDEF ) {
54 MED_ERR_(_ret,MED_ERR_UNRECOGNIZED,MED_ERR_ACCESSMODE,MED_ERR_FILE_MSG);
55 goto ERROR;
56 }
57
58 if ( _MED_ACCESS_MODE == MED_ACC_RDONLY) {
59 MED_ERR_(_ret,MED_ERR_INVALID,MED_ERR_ACCESSMODE,MED_ERR_FILE_MSG);
60 ISCRUTE_int(_MED_ACCESS_MODE);
61 goto ERROR;
62 }
63
64 switch(datatype)
65 {
66 case MED_INTERNAL_FLOAT64 :
67 _hdftype = H5T_NATIVE_DOUBLE;
68 break;
69
70 case MED_INTERNAL_FLOAT32 :
71 _hdftype = H5T_NATIVE_FLOAT;
72 break;
73
74 case MED_INT :
75 #if defined(HAVE_F77INT64)
76 _hdftype = H5T_NATIVE_LONG;
77 #else
78 _hdftype = H5T_NATIVE_INT;
79 #endif
80 break;
81
82 case MED_INTERNAL_INT32 :
83 _hdftype = H5T_NATIVE_INT;
84 break;
85
86 case MED_INTERNAL_INT64 :
87 /* _hdftype = H5T_NATIVE_LONG; */
88 /* _hdftype = H5T_NATIVE_LLONG; */
89 _hdftype = MED_H5T_INT64;
90 break;
91
92 case MED_INTERNAL_CHAR:
93 _hdftype = H5T_NATIVE_CHAR;
94 _dim=1;
95 break;
96
97 case MED_INTERNAL_SNAME:
98 if (!_dim) _dim= MED_SNAME_SIZE;
99 case MED_INTERNAL_NAME:
100 if (!_dim) _dim = MED_NAME_SIZE;
101 case MED_INTERNAL_LNAME:
102 if (!_dim) _dim = MED_LNAME_SIZE;
103
104 /* ISCRUTE(_dim); */
105 if( (_hdftype = H5Tarray_create1( H5T_NATIVE_CHAR, 1, &_dim, 0 )) < 0) {
106 MED_ERR_(_ret,MED_ERR_CREATE,MED_ERR_DATATYPE,"");goto ERROR;
107 }
108 break;
109
110 default :
111 MED_ERR_(_ret,MED_ERR_INVALID,MED_ERR_PARAMETER,MED_ERR_TYPEOF_MSG);
112 ISCRUTE_int(datatype);
113 goto ERROR;
114 }
115
116 /* Calculate dataset size*/
117 _nvaluesperentity = (*filter).nvaluesperentity;
118 _nconstituentpervalue = (*filter).nconstituentpervalue;
119 if ( (!_nvaluesperentity) || (!_nconstituentpervalue) ) {
120 MED_ERR_(_ret,MED_ERR_NOTNULL,MED_ERR_FILTER,"");
121 ISCRUTE((*filter).nvaluesperentity);
122 ISCRUTE((*filter).nconstituentpervalue);
123 goto ERROR;
124 }
125 _datasetsize[0] = (*filter).nvaluesperentity * (*filter).nconstituentpervalue;
126 if ( (*filter).profilearraysize == MED_UNDEF_SIZE ) {
127 /* if ( ! (*filter).nentity ) { */
128 /* MED_ERR_(_ret,MED_ERR_NOTNULL,MED_ERR_FILTER,""); */
129 /* ISCRUTE((*filter).nentity); */
130 /* goto ERROR; */
131 /* } */
132 _datasetsize[0]*= (*filter).nentity;
133 } else
134 _datasetsize[0]*= (*filter).profilearraysize;
135
136 if ( ! _datasetsize[0] || ! _value) {
137 _dataspace = H5Screate( H5S_NULL );
138 _value=NULL;
139 }
140
141 if (!_dataspace)
142 if ((_dataspace = H5Screate_simple(1,_datasetsize,NULL)) < 0) {
143 MED_ERR_(_ret,MED_ERR_CREATE,MED_ERR_DATASPACE,MED_ERR_SIZE_MSG);
144 ISCRUTE_size(_datasetsize[0]);
145 goto ERROR;
146 }
147
148 if ( H5Lget_info( id, datasetname, &_linkinfo, H5P_DEFAULT ) >= 0 ) {
149 if ( _linkinfo.type == H5L_TYPE_SOFT )
150 if ( H5Ldelete(id,datasetname,H5P_DEFAULT) < 0 ) {
151 MED_ERR_(_ret,MED_ERR_DELETE,MED_ERR_LINK,datasetname);
152 goto ERROR;
153 }
154 }
155
156 /* On s'assure de l'existence d'un dataset.
157 S'il n'existe pas, il est crée.
158 S'il existe, le mode MED_ACC_RDEXT génère une erreur.
159 Sinon, sa taille est lue et comparée à la taille du dataspace préalablement crée.
160 Si les tailles sont différente le dataset est supprimé et recrée à la bonne taille.
161 */
162
163 if ( (_dataset = H5Dopen(id,datasetname)) < 0) {
164
165 if ((_dataset = H5Dcreate(id,datasetname,_hdftype,_dataspace, H5P_DEFAULT)) < 0) {
166 MED_ERR_(_ret,MED_ERR_CREATE,MED_ERR_DATASET,datasetname);
167 goto ERROR;
168 }
169
170 } else {
171
172 if ( _MED_ACCESS_MODE == MED_ACC_RDEXT ) {
173 MED_ERR_(_ret,MED_ERR_INVALID,MED_ERR_ACCESSMODE,MED_ERR_DATASET_MSG);
174 ISCRUTE_int(_MED_ACCESS_MODE);
175 SSCRUTE(datasetname);
176 goto ERROR;
177 }
178
179 if ( (_datadiskspace = H5Dget_space(_dataset)) <0 ) {
180 MED_ERR_(_ret,MED_ERR_READ,MED_ERR_DATASPACE,MED_ERR_DATASET_MSG MED_ERR_NAME_MSG );
181 SSCRUTE(datasetname);
182 goto ERROR;
183 }
184
185 {
186 hsize_t _sizespace [H5S_MAX_RANK];
187 hsize_t _maxsizespace[H5S_MAX_RANK];
188
189 H5Sget_simple_extent_dims(_datadiskspace, _sizespace, _maxsizespace);
190 _datasetsizeEqualTosizespace = ( (_sizespace[0]) == _datasetsize[0] );
191 }
192
193 if ( !_datasetsizeEqualTosizespace ) {
194
195 if ( H5Dclose(_dataset) < 0 ) {
196 MED_ERR_(_ret,MED_ERR_CLOSE,MED_ERR_DATASET, datasetname );
197 goto ERROR;
198 }
199
200 if ( H5Ldelete(id,datasetname,H5P_DEFAULT) < 0) {
201 MED_ERR_(_ret,MED_ERR_DELETE,MED_ERR_DATASET, datasetname );
202 goto ERROR;
203 }
204 if ( (_dataset = H5Dcreate(id,datasetname,_hdftype,_dataspace,H5P_DEFAULT)) < 0){
205 MED_ERR_(_ret,MED_ERR_CREATE,MED_ERR_DATASET, datasetname );
206 goto ERROR;
207 }
208
209 }
210 } /*Fin de traitement d'un dataset existant */
211
212
213 if (_value)
214 for (_i=0; _i < (*filter).nspaces; ++_i) {
215 if ( H5Dwrite(_dataset,_hdftype,(*filter).memspace[_i],
216 (*filter).diskspace[_i],H5P_DEFAULT, _value) < 0 ) {
217 MED_ERR_(_ret,MED_ERR_WRITE,MED_ERR_DATASET, datasetname );
218 ISCRUTE_id(_dataset);
219 ISCRUTE_int(_i);
220 ISCRUTE_id((*filter).memspace[_i]);
221 ISCRUTE_id((*filter).diskspace[_i]);
222 goto ERROR;
223 }
224 }
225
226 _ret = 0;
227
228 ERROR:
229
230 if ( _dataspace > 0 ) if ( H5Sclose(_dataspace) < 0) {
231 MED_ERR_(_ret,MED_ERR_CLOSE,MED_ERR_DATASPACE, MED_ERR_ID_MSG );
232 ISCRUTE_id(_dataspace);
233 }
234
235 if ( _datadiskspace > 0 ) if ( H5Sclose(_datadiskspace) < 0) {
236 MED_ERR_(_ret,MED_ERR_CLOSE,MED_ERR_DATASPACE, MED_ERR_ID_MSG );
237 ISCRUTE_id(_datadiskspace);
238 }
239
240 if ( _dataset > 0 ) if ( H5Dclose(_dataset) < 0) {
241 MED_ERR_(_ret,MED_ERR_CLOSE,MED_ERR_DATASET, MED_ERR_ID_MSG );
242 ISCRUTE_id(_dataset);
243 }
244
245 if ( _dim > 1 ) if ( H5Tclose(_hdftype) < 0 ) {
246 MED_ERR_(_ret,MED_ERR_CLOSE,MED_ERR_DATATYPE, MED_ERR_ID_MSG );
247 ISCRUTE_id(_hdftype);
248 }
249
250 return _ret;
251 }
252