Line data Source code
1 : /******************************************************************************
2 : *
3 : * Project: GDAL Core
4 : * Purpose: Base class for objects with metadata, etc.
5 : * Author: Frank Warmerdam, warmerdam@pobox.com
6 : *
7 : ******************************************************************************
8 : * Copyright (c) 2000, Frank Warmerdam
9 : * Copyright (c) 2009-2013, Even Rouault <even dot rouault at spatialys.com>
10 : *
11 : * SPDX-License-Identifier: MIT
12 : ****************************************************************************/
13 :
14 : #include "cpl_port.h"
15 : #include "gdal_priv.h"
16 :
17 : #include <cstdarg>
18 : #include <cstddef>
19 :
20 : #include "cpl_error.h"
21 : #include "cpl_string.h"
22 : #include "gdal.h"
23 :
24 : /************************************************************************/
25 : /* GDALMajorObject() */
26 : /************************************************************************/
27 :
28 1569900 : GDALMajorObject::GDALMajorObject() : nFlags(GMO_VALID)
29 : {
30 1569760 : }
31 :
32 : /************************************************************************/
33 : /* ~GDALMajorObject() */
34 : /************************************************************************/
35 :
36 1483370 : GDALMajorObject::~GDALMajorObject()
37 :
38 : {
39 1483380 : if ((nFlags & GMO_VALID) == 0)
40 0 : CPLDebug("GDAL", "In ~GDALMajorObject on invalid object");
41 :
42 1483380 : nFlags &= ~GMO_VALID;
43 1483370 : }
44 :
45 : /************************************************************************/
46 : /* GetDescription() */
47 : /************************************************************************/
48 :
49 : /**
50 : * \brief Fetch object description.
51 : *
52 : * The semantics of the returned description are specific to the derived
53 : * type. For GDALDatasets it is the dataset name. For GDALRasterBands
54 : * it is actually a description (if supported) or "".
55 : *
56 : * This method is the same as the C function GDALGetDescription().
57 : *
58 : * @return non-null pointer to internal description string.
59 : */
60 :
61 6309510 : const char *GDALMajorObject::GetDescription() const
62 :
63 : {
64 6309510 : return sDescription.c_str();
65 : }
66 :
67 : /************************************************************************/
68 : /* GDALGetDescription() */
69 : /************************************************************************/
70 :
71 : /**
72 : * \brief Fetch object description.
73 : *
74 : * @see GDALMajorObject::GetDescription()
75 : */
76 :
77 24914 : const char *CPL_STDCALL GDALGetDescription(GDALMajorObjectH hObject)
78 :
79 : {
80 24914 : VALIDATE_POINTER1(hObject, "GDALGetDescription", nullptr);
81 :
82 24914 : return GDALMajorObject::FromHandle(hObject)->GetDescription();
83 : }
84 :
85 : /************************************************************************/
86 : /* SetDescription() */
87 : /************************************************************************/
88 :
89 : /**
90 : * \brief Set object description.
91 : *
92 : * The semantics of the description are specific to the derived
93 : * type. For GDALDatasets it is the dataset name. For GDALRasterBands
94 : * it is actually a description (if supported) or "".
95 : *
96 : * Normally application code should not set the "description" for
97 : * GDALDatasets. It is handled internally.
98 : *
99 : * This method is the same as the C function GDALSetDescription().
100 : */
101 :
102 473537 : void GDALMajorObject::SetDescription(const char *pszNewDesc)
103 :
104 : {
105 473537 : sDescription = pszNewDesc;
106 473481 : }
107 :
108 : /************************************************************************/
109 : /* GDALSetDescription() */
110 : /************************************************************************/
111 :
112 : /**
113 : * \brief Set object description.
114 : *
115 : * @see GDALMajorObject::SetDescription()
116 : */
117 :
118 64 : void CPL_STDCALL GDALSetDescription(GDALMajorObjectH hObject,
119 : const char *pszNewDesc)
120 :
121 : {
122 64 : VALIDATE_POINTER0(hObject, "GDALSetDescription");
123 :
124 64 : GDALMajorObject::FromHandle(hObject)->SetDescription(pszNewDesc);
125 : }
126 :
127 : /************************************************************************/
128 : /* GetMetadataDomainList() */
129 : /************************************************************************/
130 :
131 : /**
132 : * \brief Fetch list of metadata domains.
133 : *
134 : * The returned string list is the list of (non-empty) metadata domains.
135 : *
136 : * This method does the same thing as the C function
137 : * GDALGetMetadataDomainList().
138 : *
139 : * @return NULL or a string list. Must be freed with CSLDestroy()
140 : *
141 : * @since GDAL 1.11
142 : */
143 :
144 1038 : char **GDALMajorObject::GetMetadataDomainList()
145 : {
146 1038 : return CSLDuplicate(oMDMD.GetDomainList());
147 : }
148 :
149 : /************************************************************************/
150 : /* BuildMetadataDomainList() */
151 : /************************************************************************/
152 :
153 : /**
154 : * \brief Helper function for custom implementations of GetMetadataDomainList()
155 : *
156 : *
157 : * @param papszList initial list of domains. May be NULL. Will become invalid
158 : * after function call (use return value)
159 : * @param bCheckNonEmpty if TRUE, each candidate domain will be tested to be non
160 : * empty
161 : * @param ... NULL terminated variadic list of candidate domains.
162 : *
163 : * @return NULL or a string list. Must be freed with CSLDestroy()
164 : *
165 : * @since GDAL 1.11
166 : */
167 :
168 115 : char **GDALMajorObject::BuildMetadataDomainList(char **papszList,
169 : int bCheckNonEmpty, ...)
170 : {
171 : va_list args;
172 115 : const char *pszDomain = nullptr;
173 115 : va_start(args, bCheckNonEmpty);
174 :
175 497 : while ((pszDomain = va_arg(args, const char *)) != nullptr)
176 : {
177 701 : if (CSLFindString(papszList, pszDomain) < 0 &&
178 319 : (!bCheckNonEmpty || GetMetadata(pszDomain) != nullptr))
179 : {
180 17 : papszList = CSLAddString(papszList, pszDomain);
181 : }
182 : }
183 :
184 115 : va_end(args);
185 :
186 115 : return papszList;
187 : }
188 :
189 : /************************************************************************/
190 : /* GDALGetMetadataDomainList() */
191 : /************************************************************************/
192 :
193 : /**
194 : * \brief Fetch list of metadata domains.
195 : *
196 : * @see GDALMajorObject::GetMetadataDomainList()
197 : *
198 : * @since GDAL 1.11
199 : */
200 :
201 160 : char **CPL_STDCALL GDALGetMetadataDomainList(GDALMajorObjectH hObject)
202 :
203 : {
204 160 : VALIDATE_POINTER1(hObject, "GetMetadataDomainList", nullptr);
205 :
206 160 : return GDALMajorObject::FromHandle(hObject)->GetMetadataDomainList();
207 : }
208 :
209 : /************************************************************************/
210 : /* GetMetadata() */
211 : /************************************************************************/
212 :
213 : /**
214 : * \brief Fetch metadata.
215 : *
216 : * The returned string list is owned by the object, and may change at
217 : * any time. It is formatted as a "Name=value" list with the last pointer
218 : * value being NULL. Use the CPL StringList functions such as
219 : * CSLFetchNameValue() to manipulate it.
220 : *
221 : * Note that relatively few formats return any metadata at this time.
222 : *
223 : * This method does the same thing as the C function GDALGetMetadata().
224 : *
225 : * @param pszDomain the domain of interest. Use "" or NULL for the default
226 : * domain.
227 : *
228 : * @return NULL or a string list.
229 : */
230 :
231 125092 : char **GDALMajorObject::GetMetadata(const char *pszDomain)
232 :
233 : {
234 125092 : return oMDMD.GetMetadata(pszDomain);
235 : }
236 :
237 : /************************************************************************/
238 : /* GDALGetMetadata() */
239 : /************************************************************************/
240 :
241 : /**
242 : * \brief Fetch metadata.
243 : *
244 : * @see GDALMajorObject::GetMetadata()
245 : */
246 :
247 16827 : char **CPL_STDCALL GDALGetMetadata(GDALMajorObjectH hObject,
248 : const char *pszDomain)
249 :
250 : {
251 16827 : VALIDATE_POINTER1(hObject, "GDALGetMetadata", nullptr);
252 :
253 16827 : return GDALMajorObject::FromHandle(hObject)->GetMetadata(pszDomain);
254 : }
255 :
256 : /************************************************************************/
257 : /* SetMetadata() */
258 : /************************************************************************/
259 :
260 : /**
261 : * \brief Set metadata.
262 : *
263 : * The C function GDALSetMetadata() does the same thing as this method.
264 : *
265 : * @param papszMetadataIn the metadata in name=value string list format to
266 : * apply.
267 : * @param pszDomain the domain of interest. Use "" or NULL for the default
268 : * domain.
269 : * @return CE_None on success, CE_Failure on failure and CE_Warning if the
270 : * metadata has been accepted, but is likely not maintained persistently
271 : * by the underlying object between sessions.
272 : */
273 :
274 15520 : CPLErr GDALMajorObject::SetMetadata(char **papszMetadataIn,
275 : const char *pszDomain)
276 :
277 : {
278 15520 : nFlags |= GMO_MD_DIRTY;
279 15520 : return oMDMD.SetMetadata(papszMetadataIn, pszDomain);
280 : }
281 :
282 : /************************************************************************/
283 : /* GDALSetMetadata() */
284 : /************************************************************************/
285 :
286 : /**
287 : * \brief Set metadata.
288 : *
289 : * CAUTION: when using this function on a GDALDatasetH or GDALRasterBandH,
290 : * depending on the format, older values of the updated information might
291 : * still be found in the file in a "ghost" state, even if no longer accessible
292 : * through the GDAL API. This is for example the case of the GTiff format (this
293 : * is not a exhaustive list)
294 : *
295 : * @see GDALMajorObject::SetMetadata(), GDALDataset::SetMetadata(),
296 : * GDALRasterBand::SetMetadata()
297 : */
298 :
299 939 : CPLErr CPL_STDCALL GDALSetMetadata(GDALMajorObjectH hObject,
300 : CSLConstList papszMD, const char *pszDomain)
301 :
302 : {
303 939 : VALIDATE_POINTER1(hObject, "GDALSetMetadata", CE_Failure);
304 :
305 1878 : return GDALMajorObject::FromHandle(hObject)->SetMetadata(
306 939 : const_cast<char **>(papszMD), pszDomain);
307 : }
308 :
309 : /************************************************************************/
310 : /* GetMetadataItem() */
311 : /************************************************************************/
312 :
313 : /**
314 : * \brief Fetch single metadata item.
315 : *
316 : * The C function GDALGetMetadataItem() does the same thing as this method.
317 : *
318 : * @param pszName the key for the metadata item to fetch.
319 : * @param pszDomain the domain to fetch for, use NULL for the default domain.
320 : *
321 : * @return NULL on failure to find the key, or a pointer to an internal
322 : * copy of the value string on success.
323 : */
324 :
325 11672900 : const char *GDALMajorObject::GetMetadataItem(const char *pszName,
326 : const char *pszDomain)
327 :
328 : {
329 11672900 : return oMDMD.GetMetadataItem(pszName, pszDomain);
330 : }
331 :
332 : /************************************************************************/
333 : /* GDALGetMetadataItem() */
334 : /************************************************************************/
335 :
336 : /**
337 : * \brief Fetch single metadata item.
338 : *
339 : * @see GDALMajorObject::GetMetadataItem()
340 : */
341 :
342 1901400 : const char *CPL_STDCALL GDALGetMetadataItem(GDALMajorObjectH hObject,
343 : const char *pszName,
344 : const char *pszDomain)
345 :
346 : {
347 1901400 : VALIDATE_POINTER1(hObject, "GDALGetMetadataItem", nullptr);
348 :
349 3802800 : return GDALMajorObject::FromHandle(hObject)->GetMetadataItem(pszName,
350 1901400 : pszDomain);
351 : }
352 :
353 : /************************************************************************/
354 : /* SetMetadataItem() */
355 : /************************************************************************/
356 :
357 : /**
358 : * \brief Set single metadata item.
359 : *
360 : * The C function GDALSetMetadataItem() does the same thing as this method.
361 : *
362 : * @param pszName the key for the metadata item to fetch.
363 : * @param pszValue the value to assign to the key.
364 : * @param pszDomain the domain to set within, use NULL for the default domain.
365 : *
366 : * @return CE_None on success, or an error code on failure.
367 : */
368 :
369 3505340 : CPLErr GDALMajorObject::SetMetadataItem(const char *pszName,
370 : const char *pszValue,
371 : const char *pszDomain)
372 :
373 : {
374 3505340 : nFlags |= GMO_MD_DIRTY;
375 3505340 : return oMDMD.SetMetadataItem(pszName, pszValue, pszDomain);
376 : }
377 :
378 : /************************************************************************/
379 : /* GDALSetMetadataItem() */
380 : /************************************************************************/
381 :
382 : /**
383 : * \brief Set single metadata item.
384 : *
385 : * CAUTION: when using this function on a GDALDatasetH or GDALRasterBandH,
386 : * depending on the format, older values of the updated information might
387 : * still be found in the file in a "ghost" state, even if no longer accessible
388 : * through the GDAL API. This is for example the case of the GTiff format (this
389 : * is not a exhaustive list)
390 : *
391 : * @see GDALMajorObject::SetMetadataItem(), GDALDataset::SetMetadataItem(),
392 : * GDALRasterBand::SetMetadataItem()
393 : */
394 :
395 865 : CPLErr CPL_STDCALL GDALSetMetadataItem(GDALMajorObjectH hObject,
396 : const char *pszName,
397 : const char *pszValue,
398 : const char *pszDomain)
399 :
400 : {
401 865 : VALIDATE_POINTER1(hObject, "GDALSetMetadataItem", CE_Failure);
402 :
403 1730 : return GDALMajorObject::FromHandle(hObject)->SetMetadataItem(
404 865 : pszName, pszValue, pszDomain);
405 : }
406 :
407 : /************************************************************************/
408 : /* GetMOFlags() */
409 : /************************************************************************/
410 :
411 : /** Returns the GMO_ flags.
412 : * @return flags
413 : */
414 2104570 : int GDALMajorObject::GetMOFlags() const
415 :
416 : {
417 2104570 : return nFlags;
418 : }
419 :
420 : /************************************************************************/
421 : /* SetMOFlags() */
422 : /************************************************************************/
423 :
424 : /** Assign GMO_flags.
425 : * @param nNewFlags new flags.
426 : */
427 1135290 : void GDALMajorObject::SetMOFlags(int nNewFlags)
428 :
429 : {
430 1135290 : nFlags = nNewFlags;
431 1135290 : }
|