Coverage Report

Created: 2026-05-16 08:20

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/gdal/frmts/mem/memdataset.h
Line
Count
Source
1
/******************************************************************************
2
 *
3
 * Project:  Memory Array Translator
4
 * Purpose:  Declaration of MEMDataset, and MEMRasterBand.
5
 * Author:   Frank Warmerdam, warmerdam@pobox.com
6
 *
7
 ******************************************************************************
8
 * Copyright (c) 2000, Frank Warmerdam
9
 *
10
 * SPDX-License-Identifier: MIT
11
 ****************************************************************************/
12
13
#ifndef MEMDATASET_H_INCLUDED
14
#define MEMDATASET_H_INCLUDED
15
16
#include "gdal_pam.h"
17
#include "gdal_priv.h"
18
#include "gdal_rat.h"
19
#include "ogr_feature.h"
20
#include "ogrsf_frmts.h"
21
22
#include <map>
23
#include <memory>
24
25
CPL_C_START
26
27
void CPL_DLL GDALRegister_MEM();
28
29
/* Caution: if changing this prototype, also change in
30
   swig/include/gdal_python.i where it is redefined */
31
GDALRasterBandH CPL_DLL MEMCreateRasterBand(GDALDataset *, int, GByte *,
32
                                            GDALDataType, int, int, int);
33
GDALRasterBandH CPL_DLL MEMCreateRasterBandEx(GDALDataset *, int, GByte *,
34
                                              GDALDataType, GSpacing, GSpacing,
35
                                              int);
36
CPL_C_END
37
38
/************************************************************************/
39
/*                              MEMDataset                              */
40
/************************************************************************/
41
42
class MEMRasterBand;
43
class OGRMemLayer;
44
45
class CPL_DLL MEMDataset CPL_NON_FINAL : public GDALDataset
46
{
47
    CPL_DISALLOW_COPY_ASSIGN(MEMDataset)
48
49
    friend class MEMRasterBand;
50
51
    int bGeoTransformSet;
52
    GDALGeoTransform m_gt{};
53
54
    OGRSpatialReference m_oSRS{};
55
56
    std::vector<gdal::GCP> m_aoGCPs{};
57
    OGRSpatialReference m_oGCPSRS{};
58
59
    using GDALDatasetRefCountedPtr =
60
        std::unique_ptr<GDALDataset, GDALDatasetUniquePtrReleaser>;
61
62
    std::vector<GDALDatasetRefCountedPtr> m_apoOverviewDS{};
63
64
    struct Private;
65
    std::unique_ptr<Private> m_poPrivate;
66
67
    std::vector<std::unique_ptr<OGRMemLayer>> m_apoLayers{};
68
69
#if 0
70
  protected:
71
    virtual int                 EnterReadWrite(GDALRWFlag eRWFlag);
72
    virtual void                LeaveReadWrite();
73
#endif
74
75
    friend void GDALRegister_MEM();
76
77
    // cppcheck-suppress unusedPrivateFunction
78
    static GDALDataset *CreateBase(const char *pszFilename, int nXSize,
79
                                   int nYSize, int nBands, GDALDataType eType,
80
                                   CSLConstList papszParamList);
81
82
  protected:
83
    bool CanBeCloned(int nScopeFlags, bool bCanShareState) const override;
84
85
    std::unique_ptr<GDALDataset> Clone(int nScopeFlags,
86
                                       bool bCanShareState) const override;
87
88
  public:
89
    MEMDataset();
90
    ~MEMDataset() override;
91
92
    CPLErr Close(GDALProgressFunc = nullptr, void * = nullptr) override;
93
94
    const OGRSpatialReference *GetSpatialRef() const override;
95
    const OGRSpatialReference *GetSpatialRefRasterOnly() const override;
96
    CPLErr SetSpatialRef(const OGRSpatialReference *poSRS) override;
97
98
    CPLErr GetGeoTransform(GDALGeoTransform &gt) const override;
99
    CPLErr SetGeoTransform(const GDALGeoTransform &gt) override;
100
101
    void *GetInternalHandle(const char *) override;
102
103
    int GetGCPCount() override;
104
    const OGRSpatialReference *GetGCPSpatialRef() const override;
105
    const GDAL_GCP *GetGCPs() override;
106
    CPLErr SetGCPs(int nGCPCount, const GDAL_GCP *pasGCPList,
107
                   const OGRSpatialReference *poSRS) override;
108
    virtual CPLErr AddBand(GDALDataType eType,
109
                           CSLConstList papszOptions = nullptr) override;
110
    CPLErr IRasterIO(GDALRWFlag eRWFlag, int nXOff, int nYOff, int nXSize,
111
                     int nYSize, void *pData, int nBufXSize, int nBufYSize,
112
                     GDALDataType eBufType, int nBandCount,
113
                     BANDMAP_TYPE panBandMap, GSpacing nPixelSpaceBuf,
114
                     GSpacing nLineSpaceBuf, GSpacing nBandSpaceBuf,
115
                     GDALRasterIOExtraArg *psExtraArg) override;
116
    CPLErr IBuildOverviews(const char *pszResampling, int nOverviews,
117
                           const int *panOverviewList, int nListBands,
118
                           const int *panBandList, GDALProgressFunc pfnProgress,
119
                           void *pProgressData,
120
                           CSLConstList papszOptions) override;
121
122
    CPLErr CreateMaskBand(int nFlagsIn) override;
123
124
    std::shared_ptr<GDALGroup> GetRootGroup() const override;
125
126
    void AddMEMBand(GDALRasterBandH hMEMBand);
127
128
    static GDALDataset *Open(GDALOpenInfo *);
129
    static MEMDataset *Create(const char *pszFilename, int nXSize, int nYSize,
130
                              int nBands, GDALDataType eType,
131
                              CSLConstList papszParamList);
132
    static GDALDataset *
133
    CreateMultiDimensional(const char *pszFilename,
134
                           CSLConstList papszRootGroupOptions,
135
                           CSLConstList papszOptions);
136
137
    // Vector capabilities
138
139
    int GetLayerCount() const override
140
251k
    {
141
251k
        return static_cast<int>(m_apoLayers.size());
142
251k
    }
143
144
    const OGRLayer *GetLayer(int) const override;
145
146
    using GDALDataset::CreateLayer;
147
148
    OGRMemLayer *CreateLayer(const OGRFeatureDefn &oDefn,
149
                             CSLConstList papszOptions);
150
151
    OGRLayer *ICreateLayer(const char *pszName,
152
                           const OGRGeomFieldDefn *poGeomFieldDefn,
153
                           CSLConstList papszOptions) override;
154
    OGRErr DeleteLayer(int iLayer) override;
155
156
    int TestCapability(const char *) const override;
157
158
    OGRLayer *ExecuteSQL(const char *pszStatement, OGRGeometry *poSpatialFilter,
159
                         const char *pszDialect) override;
160
161
    bool AddFieldDomain(std::unique_ptr<OGRFieldDomain> &&domain,
162
                        std::string &failureReason) override;
163
164
    bool DeleteFieldDomain(const std::string &name,
165
                           std::string &failureReason) override;
166
167
    bool UpdateFieldDomain(std::unique_ptr<OGRFieldDomain> &&domain,
168
                           std::string &failureReason) override;
169
170
    std::vector<std::string>
171
    GetRelationshipNames(CSLConstList papszOptions = nullptr) const override;
172
173
    const GDALRelationship *
174
    GetRelationship(const std::string &name) const override;
175
176
    bool AddRelationship(std::unique_ptr<GDALRelationship> &&relationship,
177
                         std::string &failureReason) override;
178
179
    bool DeleteRelationship(const std::string &name,
180
                            std::string &failureReason) override;
181
182
    bool UpdateRelationship(std::unique_ptr<GDALRelationship> &&relationship,
183
                            std::string &failureReason) override;
184
};
185
186
/************************************************************************/
187
/*                            MEMRasterBand                             */
188
/************************************************************************/
189
190
class CPL_DLL MEMRasterBand CPL_NON_FINAL : public GDALPamRasterBand
191
{
192
  private:
193
    CPL_DISALLOW_COPY_ASSIGN(MEMRasterBand)
194
195
  protected:
196
    friend class MEMDataset;
197
198
    GByte *pabyData;
199
    GSpacing nPixelOffset;
200
    GSpacing nLineOffset;
201
    int bOwnData;
202
203
    bool m_bIsMask = false;
204
205
    MEMRasterBand(GByte *pabyDataIn, GDALDataType eTypeIn, int nXSizeIn,
206
                  int nYSizeIn, bool bOwnDataIn);
207
208
  public:
209
    MEMRasterBand(GDALDataset *poDS, int nBand, GByte *pabyData,
210
                  GDALDataType eType, GSpacing nPixelOffset,
211
                  GSpacing nLineOffset, int bAssumeOwnership,
212
                  const char *pszPixelType = nullptr);
213
    ~MEMRasterBand() override;
214
215
    CPLErr IReadBlock(int, int, void *) override;
216
    CPLErr IWriteBlock(int, int, void *) override;
217
    CPLErr IRasterIO(GDALRWFlag eRWFlag, int nXOff, int nYOff, int nXSize,
218
                     int nYSize, void *pData, int nBufXSize, int nBufYSize,
219
                     GDALDataType eBufType, GSpacing nPixelSpaceBuf,
220
                     GSpacing nLineSpaceBuf,
221
                     GDALRasterIOExtraArg *psExtraArg) override;
222
223
    int GetOverviewCount() override;
224
    GDALRasterBand *GetOverview(int) override;
225
226
    CPLErr CreateMaskBand(int nFlagsIn) override;
227
    bool IsMaskBand() const override;
228
229
    // Allow access to MEM driver's private internal memory buffer.
230
    GByte *GetData() const
231
0
    {
232
0
        return (pabyData);
233
0
    }
234
};
235
236
/************************************************************************/
237
/*                             OGRMemLayer                              */
238
/************************************************************************/
239
240
class IOGRMemLayerFeatureIterator;
241
242
class CPL_DLL OGRMemLayer CPL_NON_FINAL : public OGRLayer
243
{
244
    CPL_DISALLOW_COPY_ASSIGN(OGRMemLayer)
245
246
    typedef std::map<GIntBig, std::unique_ptr<OGRFeature>> FeatureMap;
247
    typedef FeatureMap::iterator FeatureIterator;
248
249
    OGRFeatureDefnRefCountedPtr m_poFeatureDefn{};
250
251
    GIntBig m_nFeatureCount = 0;
252
253
    GIntBig m_iNextReadFID = 0;
254
    GIntBig m_nMaxFeatureCount = 0;  // Max size of papoFeatures.
255
    OGRFeature **m_papoFeatures = nullptr;
256
    bool m_bHasHoles = false;
257
258
    FeatureMap m_oMapFeatures{};
259
    FeatureIterator m_oMapFeaturesIter{};
260
261
    GIntBig m_iNextCreateFID = 0;
262
263
    bool m_bUpdatable = true;
264
    bool m_bAdvertizeUTF8 = false;
265
266
    bool m_bUpdated = false;
267
268
    std::string m_osFIDColumn{};
269
270
    GDALDataset *m_poDS{};
271
272
    // Only use it in the lifetime of a function where the list of features
273
    // doesn't change.
274
    IOGRMemLayerFeatureIterator *GetIterator();
275
    void PrepareCreateFeature(OGRFeature *poFeature);
276
    OGRErr SetFeatureInternal(std::unique_ptr<OGRFeature> poFeature,
277
                              GIntBig *pnFID = nullptr);
278
279
  protected:
280
    OGRFeature *GetFeatureRef(GIntBig nFeatureId);
281
282
  public:
283
    // Clone poSRS if not nullptr
284
    OGRMemLayer(const char *pszName, const OGRSpatialReference *poSRS,
285
                OGRwkbGeometryType eGeomType);
286
    explicit OGRMemLayer(const OGRFeatureDefn &oFeatureDefn);
287
    ~OGRMemLayer() override;
288
289
    void ResetReading() override;
290
    OGRFeature *GetNextFeature() override;
291
    OGRErr SetNextByIndex(GIntBig nIndex) override;
292
293
    OGRFeature *GetFeature(GIntBig nFeatureId) override;
294
295
    OGRErr ISetFeatureUniqPtr(std::unique_ptr<OGRFeature> poFeature) override;
296
    OGRErr ISetFeature(OGRFeature *poFeature) override;
297
298
    OGRErr ICreateFeatureUniqPtr(std::unique_ptr<OGRFeature> poFeature,
299
                                 GIntBig *pnFID = nullptr) override;
300
    OGRErr ICreateFeature(OGRFeature *poFeature) override;
301
302
    OGRErr IUpsertFeature(OGRFeature *poFeature) override;
303
    OGRErr IUpdateFeature(OGRFeature *poFeature, int nUpdatedFieldsCount,
304
                          const int *panUpdatedFieldsIdx,
305
                          int nUpdatedGeomFieldsCount,
306
                          const int *panUpdatedGeomFieldsIdx,
307
                          bool bUpdateStyleString) override;
308
    OGRErr DeleteFeature(GIntBig nFID) override;
309
310
    using OGRLayer::GetLayerDefn;
311
312
    const OGRFeatureDefn *GetLayerDefn() const override
313
138M
    {
314
138M
        return m_poFeatureDefn.get();
315
138M
    }
316
317
    GIntBig GetFeatureCount(int = true) override;
318
319
    virtual OGRErr CreateField(const OGRFieldDefn *poField,
320
                               int bApproxOK = TRUE) override;
321
    OGRErr DeleteField(int iField) override;
322
    OGRErr ReorderFields(int *panMap) override;
323
    virtual OGRErr AlterFieldDefn(int iField, OGRFieldDefn *poNewFieldDefn,
324
                                  int nFlags) override;
325
    virtual OGRErr
326
    AlterGeomFieldDefn(int iGeomField,
327
                       const OGRGeomFieldDefn *poNewGeomFieldDefn,
328
                       int nFlagsIn) override;
329
    virtual OGRErr CreateGeomField(const OGRGeomFieldDefn *poGeomField,
330
                                   int bApproxOK = TRUE) override;
331
332
    int TestCapability(const char *) const override;
333
334
    const char *GetFIDColumn() const override
335
39.8k
    {
336
39.8k
        return m_osFIDColumn.c_str();
337
39.8k
    }
338
339
    bool IsUpdatable() const
340
4.59k
    {
341
4.59k
        return m_bUpdatable;
342
4.59k
    }
343
344
    void SetUpdatable(bool bUpdatableIn)
345
189k
    {
346
189k
        m_bUpdatable = bUpdatableIn;
347
189k
    }
348
349
    void SetAdvertizeUTF8(bool bAdvertizeUTF8In)
350
89.2k
    {
351
89.2k
        m_bAdvertizeUTF8 = bAdvertizeUTF8In;
352
89.2k
    }
353
354
    void SetFIDColumn(const char *pszFIDColumn)
355
165k
    {
356
165k
        m_osFIDColumn = pszFIDColumn;
357
165k
    }
358
359
    bool HasBeenUpdated() const
360
1.30k
    {
361
1.30k
        return m_bUpdated;
362
1.30k
    }
363
364
    void SetUpdated(bool bUpdated)
365
4.59k
    {
366
4.59k
        m_bUpdated = bUpdated;
367
4.59k
    }
368
369
    GIntBig GetNextReadFID()
370
429k
    {
371
429k
        return m_iNextReadFID;
372
429k
    }
373
374
    void SetDataset(GDALDataset *poDS)
375
165k
    {
376
165k
        m_poDS = poDS;
377
165k
    }
378
379
    GDALDataset *GetDataset() override
380
0
    {
381
0
        return m_poDS;
382
0
    }
383
};
384
385
#endif /* ndef MEMDATASET_H_INCLUDED */