bes  Updated for version 3.20.6
HDFCFStr.cc
Go to the documentation of this file.
1 // This file is part of the hdf4_handler implementing for the CF-compliant
2 // Copyright (c) 2011-2013 The HDF Group, Inc. and OPeNDAP, Inc.
3 //
4 // This is free software; you can redistribute it and/or modify it under the
5 // terms of the GNU Lesser General Public License as published by the Free
6 // Software Foundation; either version 2.1 of the License, or (at your
7 // option) any later version.
8 //
9 // This software is distributed in the hope that it will be useful, but
10 // WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
11 // or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
12 // License for more details.
13 //
14 // You should have received a copy of the GNU Lesser General Public
15 // License along with this library; if not, write to the Free Software
16 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 //
18 // You can contact OPeNDAP, Inc. at PO Box 112, Saunderstown, RI. 02874-0112.
19 // You can contact The HDF Group, Inc. at 1800 South Oak Street,
20 // Suite 203, Champaign, IL 61820
21 
30 
31 
32 
33 #include <iostream>
34 #include <sstream>
35 
36 #include "InternalErr.h"
37 #include "HDFCFStr.h"
38 #include <BESDebug.h>
39 #include "HDFCFUtil.h"
40 #include "HDF4RequestHandler.h"
41 
42 using namespace std;
43 using namespace libdap;
44 HDFCFStr::HDFCFStr(const int this_h4fd, int32 sds_field_ref,const string &h4_filename,const string &sds_varname,const string &sds_varnewname, bool is_h4_vdata)
45  : Str(sds_varnewname, h4_filename),
46  filename(h4_filename),
47  varname(sds_varname),
48  h4fd(this_h4fd),
49  field_ref(sds_field_ref),
50  is_vdata(is_h4_vdata)
51 {
52 }
53 
54 HDFCFStr::~HDFCFStr()
55 {
56 }
57 BaseType *HDFCFStr::ptr_duplicate()
58 {
59  return new HDFCFStr(*this);
60 }
61 
62 bool HDFCFStr::read()
63 {
64 
65  BESDEBUG("h4","Coming to HDFCFStr read "<<endl);
66 #if 0
67  string check_pass_fileid_key_str="H4.EnablePassFileID";
68  bool check_pass_fileid_key = false;
69  check_pass_fileid_key = HDFCFUtil::check_beskeys(check_pass_fileid_key_str);
70 #endif
71  bool check_pass_fileid_key = HDF4RequestHandler::get_pass_fileid();
72 
73  // SDS
74  if(false == is_vdata) {
75 
76  int32 sdid = -1;
77  if(false == check_pass_fileid_key) {
78  sdid = SDstart (const_cast < char *>(filename.c_str ()), DFACC_READ);
79  if (sdid < 0) {
80  ostringstream eherr;
81  eherr << "File " << filename.c_str () << " cannot be open.";
82  throw InternalErr (__FILE__, __LINE__, eherr.str ());
83  }
84  }
85  else
86  sdid = h4fd;
87 
88  int32 sdsid = 0;
89 
90  int32 sdsindex = SDreftoindex (sdid, field_ref);
91  if (sdsindex == -1) {
92  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
93  ostringstream eherr;
94  eherr << "SDS index " << sdsindex << " is not right.";
95  throw InternalErr (__FILE__, __LINE__, eherr.str ());
96  }
97 
98  // Obtain this SDS ID.
99  sdsid = SDselect (sdid, sdsindex);
100  if (sdsid < 0) {
101  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
102  ostringstream eherr;
103  eherr << "SDselect failed.";
104  throw InternalErr (__FILE__, __LINE__, eherr.str ());
105  }
106 
107  int32 dim_sizes[H4_MAX_VAR_DIMS];
108  int32 sds_rank, data_type, n_attrs;
109  char name[H4_MAX_NC_NAME];
110 
111  int32 r = 0;
112  r = SDgetinfo (sdsid, name, &sds_rank, dim_sizes,
113  &data_type, &n_attrs);
114  if(r == FAIL) {
115  SDendaccess(sdsid);
116  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
117  ostringstream eherr;
118  eherr << "SDgetinfo failed.";
119  throw InternalErr (__FILE__, __LINE__, eherr.str ());
120  }
121 
122  if(sds_rank != 1) {
123  SDendaccess(sdsid);
124  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
125  ostringstream eherr;
126  eherr << "The rank of string doesn't match with the rank of character array";
127  throw InternalErr (__FILE__, __LINE__, eherr.str ());
128 
129  }
130 
131  vector<int32>offset32;
132  offset32.resize(1);
133  vector<int32>count32;
134  count32.resize(1);
135  vector<int32>step32;
136  step32.resize(1);
137  offset32[0] = 0;
138  count32[0] = dim_sizes[0];
139  step32[0] = 1;
140 
141  vector<char>val;
142  val.resize(count32[0]);
143 
144  r = SDreaddata (sdsid, &offset32[0], &step32[0], &count32[0], &val[0]);
145  if (r != 0) {
146  SDendaccess (sdsid);
147  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
148  ostringstream eherr;
149  eherr << "SDreaddata failed.";
150  throw InternalErr (__FILE__, __LINE__, eherr.str ());
151  }
152 
153  string final_str(val.begin(),val.end());
154  set_value(final_str);
155  SDendaccess(sdsid);
156  HDFCFUtil::close_fileid(sdid,-1,-1,-1,check_pass_fileid_key);
157  }
158  else {
159 
160  int32 file_id = -1;
161 
162  if(true == check_pass_fileid_key)
163  file_id = h4fd;
164  else {
165  // Open the file
166  file_id = Hopen (filename.c_str (), DFACC_READ, 0);
167  if (file_id < 0) {
168  ostringstream eherr;
169  eherr << "File " << filename.c_str () << " cannot be open.";
170  throw InternalErr (__FILE__, __LINE__, eherr.str ());
171  }
172  }
173 
174 
175  // Start the Vdata interface
176  if (Vstart (file_id) < 0) {
177  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
178  ostringstream eherr;
179  eherr << "This file cannot be open.";
180  throw InternalErr (__FILE__, __LINE__, eherr.str ());
181  }
182 
183  // Attach the vdata
184  int32 vdref = field_ref;
185  int32 vdata_id = VSattach (file_id, vdref, "r");
186  if (vdata_id == -1) {
187  Vend (file_id);
188  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
189  ostringstream eherr;
190  eherr << "Vdata cannot be attached.";
191  throw InternalErr (__FILE__, __LINE__, eherr.str ());
192  }
193 
194  int32 num_rec = VSelts(vdata_id);
195  if (num_rec == -1) {
196  VSdetach (vdata_id);
197  Vend (file_id);
198 
199  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
200  ostringstream eherr;
201  eherr << "The number of elements from this vdata cannot be obtained.";
202  throw InternalErr (__FILE__, __LINE__, eherr.str ());
203  }
204 
205 
206  int32 r = -1;
207 
208  // Seek the position of the starting point
209  if (VSseek (vdata_id, 0) == -1) {
210  VSdetach (vdata_id);
211  Vend (file_id);
212  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
213  ostringstream eherr;
214  eherr << "VSseek failed at " << 0;
215  throw InternalErr (__FILE__, __LINE__, eherr.str ());
216  }
217 
218  // Prepare the vdata field
219  if (VSsetfields (vdata_id, varname.c_str ()) == -1) {
220  VSdetach (vdata_id);
221  Vend (file_id);
222  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
223  ostringstream eherr;
224  eherr << "VSsetfields failed with the name " << varname;
225  throw InternalErr (__FILE__, __LINE__, eherr.str ());
226  }
227  vector <char> val;
228  val.resize(num_rec);
229 
230  // Read the data
231  if(VSread (vdata_id, (uint8 *) &val[0], num_rec,
232  FULL_INTERLACE) == -1) {
233  VSdetach (vdata_id);
234  Vend (file_id);
235  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
236  ostringstream eherr;
237  eherr << "VSread failed.";
238  throw InternalErr (__FILE__, __LINE__, eherr.str ());
239  }
240 
241  string final_str(val.begin(),val.end());
242  set_value(final_str);
243  if (VSdetach (vdata_id) == -1) {
244  Vend (file_id);
245  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
246  ostringstream eherr;
247  eherr << "VSdetach failed.";
248  throw InternalErr (__FILE__, __LINE__, eherr.str ());
249  }
250 
251  if (Vend (file_id) == -1) {
252  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
253  ostringstream eherr;
254  eherr << "VSdetach failed.";
255  throw InternalErr (__FILE__, __LINE__, eherr.str ());
256  }
257 
258  HDFCFUtil::close_fileid(-1,file_id,-1,-1,check_pass_fileid_key);
259 //#endif
260  }
261  return true;
262 }
HDFCFStr
Definition: HDFCFStr.h:44
HDFCFStr.h
This class provides a way to map HDF4 1-D character array to DAP Str for the CF option.
libdap
Definition: BESDapFunctionResponseCache.h:35
HDFCFUtil::close_fileid
static void close_fileid(int32 sdfd, int32 file_id, int32 gridfd, int32 swathfd, bool pass_fileid_key)
Definition: HDFCFUtil.cc:3685