wiki:rfc24_progressive_data_support

Version 76 (modified by warmerdam, 14 years ago) ( diff )

Restructure to focus on interface changes.

RFC 24: GDAL Progressive Data Support

Author: Norman Barker, Frank Warmerdam
Contact: nbarker@…, warmerdam@…
Status: Development

Summary

Provide an interface for asynchronous/streaming data access in GDAL. The initial implementation is for JPIP, but should be generic enough to apply to other streaming / progressive approaches. Background on the JPIP (Kakadu) implementation can be found in rfc24_jpipkak.

Interfaces

GDALAsyncRasterIO

This new class is intended to represent an active asynchronous raster imagery request. The request includes information on a source window on the dataset, a target buffer size (implies level of decimation or replication), the buffer type, buffer interleaving, data buffer and bands being requested. Essentially the same sort of information that is passed in a GDALDataset::!RasterIO() request.

The GetNextUpdatedRegion() method can be used to wait for an update to the imagery buffer, and to find out what area was updated. The LockBuffer() and UnlockBuffer() methods can be used to temporarily disable updates to the buffer while application code accesses the buffer.

While an implementation of the simple accessors is provided as part of the class, it is intended that the class be subclassed as part of implementation of a particular driver, and custom implementations of GetNextUpdatedRegion(), LockBuffer() and UnlockBuffer() provided.

class CPL_DLL GDALAsyncRasterIO
{
  protected:
    GDALDataset* poDS;
	int xOff;
	int yOff;
	int xSize;
	int ySize;
	void * pBuf;
	int bufXSize;
	int bufYSize;
	GDALDataType bufType;
	int nBandCount;
	int* pBandMap;
	int nPixelSpace;
	int nLineSpace;
	int nBandSpace;
	long nDataRead;
  public:
	GDALAsyncRasterIO(GDALDataset* poDS = NULL);
	virtual ~GDALAsyncRasterIO();

	GDALDataset* GetGDALDataset(){return poDS;}
	int GetXOffset(){return xOff;}
	int GetYOffset(){return yOff;}
	int GetXSize(){return xSize;}
	int GetYSize(){return ySize;}
	void * GetBuffer(){return pBuf;}
	int GetBufferXSize(){return bufXSize;}
	int GetBufferYSize(){return bufYSize;}
	GDALDataType GetBufferType(){return bufType;}
	int GetBandCount(){return nBandCount;}
	int* GetBandMap(){return pBandMap;}
	int GetPixelSpace(){return nPixelSpace;}
	int GetLineSpace(){return nLineSpace;}
	int GetBandSpace(){return nBandSpace;}
	int GetNDataRead(){return nDataRead;}
	
	/* Returns GARIO_UPDATE, GARIO_NO_MESSAGE (if pending==false and nothing in the queue or if pending==true && timeout != 0 and nothing in the queue at the end of the timeout), GARIO_COMPLETE, GARIO_ERROR */
	virtual GDALAsyncStatusType GetNextUpdatedRegion(bool wait, int timeout,
                                                   int* pnxbufoff,
                                                   int* pnybufoff,
                                                   int* pnxbufsize,
                                                   int* pnybufsize) = 0;
	/* if pending = true, we wait forever if timeout=0, for the timeout time otherwise */
	/* if pending = false, we return immediately */
	/* the int* are output values */

	// lock a whole buffer.
	virtual void LockBuffer() = 0;

	// lock only a block
        // the caller must relax a previous lock before asking for a new one
        virtual void LockBuffer(int xbufoff, int ybufoff, int xbufsize, int ybufsize) = 0;
        virtual void UnlockBuffer() = 0; 
	
	friend class GDALDataset;
};

The async status list is as follows, and will be declared in gdal.h.

typedef enum 
{	
	GARIO_PENDING = 0,
	GARIO_UPDATE = 1,
	GARIO_ERROR = 2,
	GARIO_COMPLETE = 3,
	GARIO_TypeCount = 4
} GDALAsyncStatusType;

GDALDataset

The GDALDataset class is extended with methods to create an asynchronous reader, and to cleanup the asynchronous reader. It is intended that these methods would be subclassed by drivers implementing asynchronous data access.

        virtual GDALAsyncRasterIO* 
            BeginAsyncRasterIO(int xOff, int yOff,
                               int xSize, int ySize, 
                               void *pBuf,
                               int bufXSize, int bufYSize,
                               GDALDataType bufType,
                               int nBandCount, int* bandMap,
                               int nPixelSpace, int nLineSpace,
                               int nBandSpace,
                               char **papszOptions);
        virtual void EndAsyncRasterIO(GDALAsyncRasterIO *);

It is expected that as part of gdal/gcore a default !GDALAsyncRasterIO implementation will be provided that just uses GDALDataset::!RasterIO() to perform the request as a single blocking request. However, this default implementation will ensure that applications can use the asynchronous interface without worrying whether a particular format will actually operate asynchronously.

GDALDriver

In order to provide a hint to applications whether particular formats support asynchronous IO, we will add a new metadata item on the GDALDriver of implementing formats. The metadata item will be "DCAP_ASYNCIO" (macro GDAL_DCAP_ASYNCIO) and will have the value "YES" if asynchronous IO is available.

Implementing drivers will do something like this in their driver setup code:

   poDriver->SetMetadataItem( GDAL_DCAP_ASYNCIO, "YES" );

GDALRasterBand

There are no changes to the GDALRasterBand interface for asynchronous raster IO. Asynchronous IO requests can only be made at the dataset level, not the band.

CPLHTTPFetch()

The initial JPIPKAK implementation of asynchronous IO requests will use !CPLHTTPFetch() for the JPIP network transport of requests. This will require two improvements to the implementation without changing the call sequence.

  1. A new boolean option can be passed in the options list called "PERSISTENT". When it is true (ie. value "YES") persistent connection handle will be used.
  2. A new option named "HEADERS" can be used to send an additional header in the HTTP request. The JPIPKAK driver will pass accept headers this way.

Attachments (7)

Download all attachments as: .zip

Note: See TracWiki for help on using the wiki.