[gdal-dev] Fwd: How to reuse memory pointer of GDAL Memory driver

Pol Monsó Purtí lluna.nova at gmail.com
Mon Jun 6 05:53:46 PDT 2016


Let's jump to particulars, at the end, the code.

If I set the DATAPOINTER to NULL the program crashes at CreateCopy with
access violation. Same if I set it to the datapointer to &abyRaster[0] and
add the remaining two bands.

The abyRasters are initialized to white color with memset. SO this piece of
code should give me a white jpg square of widthxheight. I could set a
complete MWE if necessary.

And, the code:

        char* filename = (char*) malloc(1024);

        sprintf(filename, "MEM:::DATAPOINTER=%p,PIXELS=%d,LINES=%d,BANDS=0",

                NULL, width, height);

        poDstDS = (GDALDataset *) GDALOpen(filename,GA_Update);


        free(filename);


        for(unsigned int b = 0; b < RGBRasterBands::NUMBANDS; b++)

        {

            //assert(sizeof(long) == sizeof(void*));

            const void * address = static_cast<const void*>(&abyRasters[b]);

            std::stringstream ss;

            ss << address;

            const char * datapointer = ss.str().c_str();

            std::cout << "datapointer: " << datapointer << std::endl;

            papszOptions = CSLSetNameValue( papszOptions,
"DATAPOINTER", datapointer );

            poDstDS->AddBand(GDT_Byte, papszOptions);


        }

        char **papszOptions2 = NULL;

        papszOptions2 = CSLSetNameValue( papszOptions2, "QUALITY", "40" );


        std::cout << "Copying to " << filepath << std::endl;

        GDALDriver* jpegDriver =
GetGDALDriverManager()->GetDriverByName("JPEG");

        GDALDataset* jpeg_ds =
jpegDriver->CreateCopy(filepath.string().c_str(), poDstDS, false,
papszOptions2, GDALDummyProgress, NULL);

        if(jpeg_ds == NULL)

        {

            std::cout << "Failure when creating output orthoimage " <<
filepath << std::endl;

            return -5;

        }

The abyRasters are allocated with

        for(int b = 0; b < RGBRasterBands::NUMBANDS; b++)
        {
            abyRasters.push_back(new
GByte[rasterMemoryDimensions.width*rasterMemoryDimensions.height]());
            memset(&abyRasters[b][0],QuickDrop::NODATAVALUE,sizeof(GByte)*rasterMemoryDimensions.width*rasterMemoryDimensions.height);
        }


On Mon, Jun 6, 2016 at 12:35 PM, Pol Monsó Purtí <lluna.nova at gmail.com>
wrote:

> Just one more question,
>
> If i set the option BAND=0, what should the DATAPOINTER be? Does it become
> optional?
>
> Cheers
>
> On Mon, Jun 6, 2016 at 10:55 AM, Even Rouault <even.rouault at spatialys.com>
> wrote:
>
>> On Monday 06 June 2016 10:45:47 Pol Monsó Purtí wrote:
>> > THanks Mateusz,
>> >
>> > You're right. I'm trying it as we speak.
>> >
>> > In my case I have a std::vector<GByte*> of the 3 bands, where the GByte*
>> > are allocated in the heap with new GByte[width*height]. I guess that
>> won't
>> > work because the three bands have to be one single memory chunk, am I
>> > right? I guess the only solution is to switch to single band float and
>> > merge rgb to float. I'd prefer not having to refactor the rest of the
>> code.
>>
>>
>> > Is it possible to have a different address for each band?
>>
>> Yes, create a dataset with 0 band and then add each band with the
>> GDALDataset::AddBand() method
>>
>> See http://gdal.org/frmt_mem.html :
>> """The MEM format is one of the few that supports the AddBand() method.
>> The
>> AddBand() method supports DATAPOINTER, PIXELOFFSET and LINEOFFSET options
>> to
>> reference an existing memory array."""
>>
>> >
>> > All this is to support jpg as output. All the operations are done in my
>> > GByte array and it's only at the end that I create the dataset and
>> image.
>> > At the moment I create a Tiff and finally createcopy to jpg.
>> >
>> > On Fri, Jun 3, 2016 at 9:10 PM, Mateusz Loskot <mateusz at loskot.net>
>> wrote:
>> > > On 3 June 2016 at 20:45, Pol Monsó Purtí <lluna.nova at gmail.com>
>> wrote:
>> > > > I've seen this mysterious article http://www.gdal.org/frmt_mem.html
>> > >
>> > > which
>> > >
>> > > > references the `DATAPOINTER` option. I've seen another reference
>> > > > [here](
>> > >
>> > > https://lists.osgeo.org/pipermail/gdal-dev/2006-November/010583.html)
>> > >
>> > > > which does
>> > >
>> > >
>> sprintf(filename,"MEM:::DATAPOINTER=%d,PIXELS=%d,LINES=%d,BANDS=1,DATATYPE
>> > >
>>
>> =%d,PIXELOFFSET=0,LINEOFFSET=0,BANDOFFSET=0",datpt,pixels,lines,datatype);>
>> > > >     dataset = GDALOpen(filename,GA_Update);
>> > > >
>> > > > How would this translate to c++?
>> > >
>> > > The line above is valid C++, isn't it.
>> > > If you followed to Frank's answer [1], you'd see it slightly corrected
>> > > but the technique remains the same.
>> > >
>> > > [1]
>> https://lists.osgeo.org/pipermail/gdal-dev/2006-November/010603.html
>> > >
>> > > Best regards,
>> > > --
>> > > Mateusz Loskot, http://mateusz.loskot.net
>>
>> --
>> Spatialys - Geospatial professional services
>> http://www.spatialys.com
>>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osgeo.org/pipermail/gdal-dev/attachments/20160606/f6f3a5f9/attachment.html>


More information about the gdal-dev mailing list