00001 /* 00002 * Name: filter.m4 00003 * 00004 * Description: 00005 * DOXYGEN Input file filter for DRAMA source files. 00006 * 00007 * This file must be complatible with both Solaris and GNU m4. All 00008 * unused macros are deleted and this comment must end up as a C/C++ 00009 * compatible comment which is not picked up by DOXYGEN. 00010 * 00011 * Synopsis: 00012 * DCF(func) => Produces a link to a DRAMA C source file func.html 00013 * in ../routines. 00014 * DDL(link,text) => Produce a link to ../link.html, specified link text. 00015 * 00016 * Language: m4 macro. 00017 * 00018 * Author: Tony Farrell, AAO. 00019 * 00020 * "@(#) $Id: ACMM:DramaHtml/filter.m4,v 3.24 03-Nov-2009 09:07:29+11 tjf $" 00021 * 00022 * History: 00023 * 10-Nov-2004 - TJF - Original Version. 00024 */ 00025 00026 00027 00028 /* SDS Include file */ 00029 /* */ 00030 /* Jeremy Bailey 1998 Jul 13 */ 00031 /* */ 00032 /* @(#) $Id: ACMM:sds/sds.h,v 3.48 02-Nov-2009 14:50:59+11 tjf $ */ 00033 /* */ 00034 /* */ 00035 /* */ 00036 00037 /* 00038 * This file now uses DOXYGEN comments to generate the C++ web pages. 00039 * m4 macros of the form @htmlonly <a href="../routines/function.html">function()</a>@endhtmlonly are used in the comments 00040 * to refer to DRAMA C function documention (see DramaHtml/Makefile, 00041 * DramaHtml/doxygen.config and DramaHtml/filter.m4 for detials) 00042 */ 00043 #ifndef _SDS_INCLUDE_ 00044 #define _SDS_INCLUDE_ 1 00045 00046 #include "sdsport.h" 00047 #include "status.h" 00048 00049 #ifdef __cplusplus 00050 extern "C" { 00051 #endif 00052 00058 #define SDS_VERSION 100 00059 00060 /* Status codes */ 00061 00062 #include "sds_err.h" 00063 00064 /* Type codes */ 00065 00066 #define SDS_STRUCT 0 /* Structure */ 00067 #define SDS_CHAR 1 /* Character */ 00068 #define SDS_UBYTE 2 /* Unsigned byte */ 00069 #define SDS_BYTE 3 /* byte */ 00070 #define SDS_USHORT 4 /* Unsigned short */ 00071 #define SDS_SHORT 5 /* short */ 00072 #define SDS_UINT 6 /* Unsigned int */ 00073 #define SDS_INT 7 /* int */ 00074 #define SDS_FLOAT 8 /* float */ 00075 #define SDS_DOUBLE 9 /* double */ 00076 #define SDS_I64 11 /* Int 64 */ 00077 #define SDS_UI64 12 /* Unsigned Int 64 */ 00078 #define SDS_C_MAXCODE SDS_UI64 /* The maximum code value */ 00079 00080 /* Name length */ 00081 00082 #define SDS_C_NAMELEN 16 00083 00084 #define SDS_C_MAXARRAYDIMS 7 00085 00086 #define SDS_WATCH_EVENT_FREE 0 00087 #define SDS_WATCH_EVENT_DELETE 1 00088 #define SDS_WATCH_EVENT_READFREE 2 00089 #define SDS_WATCH_EVENT_NEW 3 00090 #define SDS_WATCH_EVENT_COPY 4 00091 #define SDS_WATCH_EVENT_INSERT 5 00092 #define SDS_WATCH_EVENT_INSERT_CELL 6 00093 #define SDS_WATCH_EVENT_EXTRACT 7 00094 #define SDS_WATCH_EVENT_RESIZE 8 00095 #define SDS_WATCH_EVENT_NEWID 9 00096 00097 typedef long SdsIdType; 00098 00099 typedef long SdsCodeType; 00100 00101 typedef void (*SdsWatchRoutineType)(SdsIdType, void *, int reserved); 00102 00103 SDSEXTERN void SdsSetWatch(SdsIdType id, 00104 SdsWatchRoutineType watchRoutine, 00105 void * clientData, 00106 SdsIdType *oldId, 00107 SdsWatchRoutineType *oldWatchRoutine, 00108 void ** oldClientData, 00109 StatusType * SDSCONST status); 00110 00111 SDSEXTERN void SdsCreate(SDSCONST char *name, long nextra, SDSCONST char *extra, 00112 SdsIdType *id, StatusType * SDSCONST status); 00113 00114 SDSEXTERN void SdsInfo(SdsIdType id,char *name, SdsCodeType *code, long *ndims, 00115 unsigned long* dims, StatusType * SDSCONST status); 00116 00117 SDSEXTERN void SdsNew(SdsIdType parent_id, SDSCONST char *name, long nextra, 00118 SDSCONST char *extra, SdsCodeType code, long ndims, 00119 SDSCONST unsigned long *dims, 00120 SdsIdType *id, StatusType * SDSCONST status); 00121 00122 SDSEXTERN int SdsIsDefined(SdsIdType parent_id, StatusType * SDSCONST status); 00123 00124 SDSEXTERN void SdsIndex(SdsIdType parent_id, long index, SdsIdType *id, StatusType * SDSCONST status); 00125 00126 SDSEXTERN void SdsFind(SdsIdType parent_id, SDSCONST char *name, SdsIdType *id, StatusType * SDSCONST status); 00127 00128 SDSEXTERN void SdsFindByPath(SdsIdType parent_id, SDSCONST char *name, SdsIdType *id, StatusType * SDSCONST status); 00129 00130 SDSEXTERN void SdsPointer(SdsIdType id, void **data, unsigned long *length, StatusType * SDSCONST status); 00131 00132 SDSEXTERN void SdsGet(SdsIdType id, unsigned long length, unsigned long offset, 00133 void *data, unsigned long *actlen, StatusType * SDSCONST status); 00134 00135 SDSEXTERN void SdsPut(SdsIdType id, unsigned long length, unsigned long offset, 00136 SDSCONST void *data, StatusType * SDSCONST status); 00137 00138 00139 SDSEXTERN void SdsCell(SdsIdType array_id, long nindices, 00140 SDSCONST unsigned long *indices, 00141 SdsIdType *id, StatusType * SDSCONST status); 00142 00143 00144 SDSEXTERN void SdsInsertCell(SdsIdType array_id, long nindices, 00145 SDSCONST unsigned long *indices, 00146 SdsIdType id, StatusType * SDSCONST status); 00147 00148 SDSEXTERN void SdsDelete(SdsIdType id, StatusType * SDSCONST status); 00149 00150 SDSEXTERN void SdsSize(SdsIdType id, unsigned long *bytes, StatusType * SDSCONST status); 00151 SDSEXTERN void SdsExport(SdsIdType id, unsigned long length, void *data, StatusType * SDSCONST status); 00152 00153 SDSEXTERN void SdsImport(SDSCONST void *data, SdsIdType *id, 00154 StatusType * SDSCONST status); 00155 00156 SDSEXTERN void SdsAccess(void *data, SdsIdType *id, StatusType * SDSCONST status); 00157 00158 SDSEXTERN void SdsExtract(SdsIdType id, StatusType * SDSCONST status); 00159 00160 SDSEXTERN void SdsInsert(SdsIdType parent_id, SdsIdType id, StatusType * SDSCONST status); 00161 00162 SDSEXTERN void SdsCopy(SdsIdType id, SdsIdType *copy_id, StatusType * SDSCONST status); 00163 00164 SDSEXTERN void SdsResize(SdsIdType id, long ndims, SDSCONST unsigned long *dims, 00165 StatusType * SDSCONST status); 00166 00167 SDSEXTERN void SdsRename(SdsIdType id, SDSCONST char* name, StatusType * SDSCONST status); 00168 00169 SDSEXTERN void SdsGetExtra(SdsIdType id, long length, char* extra, unsigned long *actlen, 00170 StatusType * SDSCONST status); 00171 00172 SDSEXTERN void SdsPutExtra(SdsIdType id, long length, SDSCONST char *extra, 00173 StatusType * SDSCONST status); 00174 00175 SDSEXTERN void SdsExportDefined(SdsIdType id, unsigned long length, void *data, StatusType * SDSCONST status); 00176 00177 SDSEXTERN void SdsSizeDefined(SdsIdType id, unsigned long *bytes, StatusType * SDSCONST status); 00178 00179 SDSEXTERN void SdsIsExternal(SdsIdType id, int *external, StatusType * SDSCONST status); 00180 00181 SDSEXTERN void SdsGetExternInfo(SdsIdType id, void **data, StatusType * SDSCONST status); 00182 00183 SDSEXTERN void SdsList(SdsIdType id, StatusType * SDSCONST status); 00184 00185 SDSEXTERN void SdsWrite(SdsIdType id, SDSCONST char *filename, StatusType * SDSCONST status); 00186 00187 SDSEXTERN void SdsFreeId(SdsIdType id, StatusType * SDSCONST status); 00188 00189 SDSEXTERN void SdsFlush(SdsIdType id, StatusType * SDSCONST status); 00190 00191 SDSEXTERN void SdsRead(SDSCONST char *filename, SdsIdType *id, StatusType * SDSCONST status); 00192 00193 SDSEXTERN void SdsFillArray(SdsIdType array_id, SdsIdType elem_id, 00194 StatusType * SDSCONST status); 00195 00196 00197 SDSEXTERN void SdsReadFree(SdsIdType id, StatusType * SDSCONST status); 00198 SDSEXTERN SDSCONST char *SdsTypeToStr(SdsCodeType code, int mode); 00199 SDSEXTERN void SdsFindByName( SdsIdType parent_id, 00200 SDSCONST char * name, 00201 unsigned int * skip, 00202 SdsIdType * id, 00203 StatusType * SDSCONST status ); 00204 00205 00206 00207 SDSEXTERN void Sds__MarkFree(SdsIdType id); 00208 00209 SDSEXTERN void Sds__Free(SdsIdType id, StatusType * SDSCONST status); 00210 00211 SDSEXTERN void Sds___WatchEvent(SdsIdType id, int eventFlag, const char * sourceFunc); 00212 00213 00214 #define SDS_COMP_MESS_ERROR 1 00215 #define SDS_COMP_MESS_WARN 2 00216 00217 SDSEXTERN void SdsCompiler(SDSCONST char *string, int messages, int intaslong, SdsIdType *id, StatusType *status); 00218 00219 00220 /* 00221 * Note - if you get a syntax error at this point, it is likely 00222 * that INT64 has not been defined. See the relevant part of 00223 * sdsport.h. 00224 */ 00225 SDSEXTERN INT64 SdsSetI64(long high, unsigned long low); 00226 00227 SDSEXTERN UINT64 SdsSetUI64(unsigned long high, unsigned long low); 00228 00229 SDSEXTERN void SdsGetI64(INT64 i64, long *high, unsigned long *low); 00230 00231 SDSEXTERN void SdsGetUI64(UINT64 i64, unsigned long *high, unsigned long *low); 00232 00233 00234 SDSEXTERN void SdsGetIdInfo( INT32 * pnum, INT32 * pasize, INT32 * puids ); 00235 00236 struct SdsCheckStruct { 00237 INT32 _init_last_id; 00238 INT32 _init_current_array_size; 00239 INT32 _init_unused_ids; 00240 INT32 leakCount; 00241 INT32 _spare2; 00242 INT32 _spare3; 00243 INT32 _spare4; 00244 }; 00245 typedef struct SdsCheckStruct SdsCheckType; 00246 00247 SDSEXTERN void SdsCheckInit(SdsCheckType *chkData, StatusType *status); 00248 SDSEXTERN void SdsCheck(const char *mes, SdsCheckType *chkData, 00249 StatusType *status); 00250 00251 SDSEXTERN void SdsFreeIdAndCheck(const char *mes, SdsIdType id, StatusType *status); 00252 SDSEXTERN SDSCONST char * SdsErrorCodeString(StatusType error); 00253 SDSEXTERN void SdsListInUse(); 00254 00255 #if defined(SDS_CHECK_FREE)||defined(SDS_CHECK_FREE_W) 00256 #include <stdio.h> 00257 #ifndef SdsFreeId 00258 #ifdef SDS_CHECK_FREE_W 00259 #warning "Checking SdsFree operations" 00260 #endif 00261 /* 00262 * Note - the C++ version does its own thing below - see cleanup(). 00263 */ 00264 #define SdsFreeId(_id_, _status) \ 00265 { \ 00266 if (*(_status) == STATUS__OK) \ 00267 { \ 00268 SdsFreeIdAndCheck("", (_id_), (_status)); \ 00269 if (*(_status) == SDS__CHK_FREE) \ 00270 { \ 00271 fprintf(stderr, " At file %s, line %d\n", __FILE__, __LINE__); \ 00272 fprintf(stderr, " This warning was enabled by SDS_CHECK_FREE or SDS_CHECK_FREE_W macro\n"); \ 00273 *(_status) = STATUS__OK; \ 00274 } \ 00275 } \ 00276 } 00277 #endif 00278 #endif 00279 00280 #ifdef __cplusplus 00281 00282 } /* extern "C" */ 00283 00284 /* 00285 * C++ only section. 00286 * 00287 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00288 * Here is the a C++ interface to SDS. No object code is required since 00289 * all code is inline. 00290 * 00291 */ 00324 #ifdef DRAMA_ALLOW_CPP_STDLIB 00325 #include <string> 00326 template <typename T> class SdsArrayAccessHelper { 00327 public: 00328 friend class SdsId; 00329 /* Some exceptions thrown from the subscript operator */ 00334 class NoDataException { 00335 std::string detail; 00336 public: 00341 NoDataException(const char *why) :detail(why) { } 00345 std::string const & GetDetails() const { return detail; }; 00346 00347 }; 00352 class InvalidIndexException { 00353 std::string detail; 00354 public: 00359 InvalidIndexException(const char *why) :detail(why) { } 00363 std::string const & GetDetails() const { return detail; }; 00364 }; 00365 00366 private: 00367 SdsCodeType code; /* The SDS code of the item */ 00368 unsigned long elements; /* Number of element in the array */ 00369 T* data; /* The array pointer is written here */ 00370 00371 /* 00372 * Help function used to check an index is valid. Also checks 00373 * that we have some data. Throws expections on problems. 00374 */ 00375 void CheckIndexAndData(unsigned long index) const { 00376 if (!data) 00377 { 00378 throw new NoDataException("Index %d, Code %d, elements %d - data is invalid"); 00379 } 00380 if (index >= elements) 00381 { 00382 throw new InvalidIndexException("Index %d, Code %d, elements %d - index is invalid"); 00383 } 00384 } 00385 00386 00387 /* 00388 * The remaining private items are accessed by SdsId as a friend class. 00389 */ 00390 /* 00391 * Return the address of the address of the data being accessed 00392 * 00393 * This is used by SdsId.AccessArray() to put the address of the 00394 * data item. 00395 */ 00396 void ** Data() { return (void **)&data; } 00397 00398 /* 00399 * Set the number of elements in the array. 00400 * 00401 * This is used by SdsId.AccessArray() set the number of elements in 00402 * the array. 00403 */ 00404 void SetElements(unsigned long nelem) { 00405 elements = nelem; 00406 } 00407 00408 00409 protected: 00417 SdsArrayAccessHelper(SdsCodeType c) : code(c), elements(0), data(0) { 00418 } 00419 public: 00420 00423 SdsCodeType Code() const { return code; } 00426 unsigned long Size() const { return elements; } 00440 T const & operator[](const unsigned long index) const { 00441 CheckIndexAndData(index); 00442 return data[index]; 00443 } 00457 T & operator[](const unsigned long index) { 00458 CheckIndexAndData(index); 00459 return data[index]; 00460 } 00467 T * DataAddressRW() { 00468 return data; 00469 } 00476 const T * DataAddressRO() const { 00477 return data; 00478 } 00479 }; /* SdsArrayAccessHelper */ 00480 00481 /* 00482 * Classes for each SDS data type. 00483 */ 00490 class SdsArrayChar : public SdsArrayAccessHelper<char> { 00491 public: 00492 SdsArrayChar() : SdsArrayAccessHelper<char>(SDS_CHAR) { 00493 } 00494 00495 }; 00502 class SdsArrayUbyte : public SdsArrayAccessHelper<unsigned char> { 00503 public: 00504 SdsArrayUbyte() : SdsArrayAccessHelper<unsigned char>(SDS_UBYTE) { 00505 } 00506 00507 }; 00514 class SdsArrayByte : public SdsArrayAccessHelper<signed char> { 00515 public: 00516 SdsArrayByte() : SdsArrayAccessHelper<signed char>(SDS_BYTE) { 00517 } 00518 00519 }; 00520 00521 00528 class SdsArrayUshort : public SdsArrayAccessHelper<unsigned short> { 00529 public: 00530 SdsArrayUshort() : SdsArrayAccessHelper<unsigned short>(SDS_USHORT) { 00531 } 00532 00533 }; 00540 class SdsArrayShort : public SdsArrayAccessHelper<short> { 00541 public: 00542 SdsArrayShort() : SdsArrayAccessHelper<short>(SDS_SHORT) { 00543 } 00544 00545 }; 00546 00547 00548 00555 class SdsArrayINT32 : public SdsArrayAccessHelper<INT32> { 00556 public: 00557 SdsArrayINT32() : SdsArrayAccessHelper<INT32>(SDS_INT) { 00558 } 00559 00560 }; 00567 class SdsArrayUINT32 : public SdsArrayAccessHelper<UINT32> { 00568 public: 00569 SdsArrayUINT32() : SdsArrayAccessHelper<UINT32>(SDS_UINT) { 00570 } 00571 }; 00572 00573 00580 class SdsArrayINT64 : public SdsArrayAccessHelper<INT64> { 00581 public: 00582 SdsArrayINT64() : SdsArrayAccessHelper<INT64>(SDS_I64) { 00583 } 00584 00585 }; 00592 class SdsArrayUINT64 : public SdsArrayAccessHelper<UINT64> { 00593 public: 00594 SdsArrayUINT64() : SdsArrayAccessHelper<UINT64>(SDS_UI64) { 00595 } 00596 }; 00597 00604 class SdsArrayDouble : public SdsArrayAccessHelper<double> { 00605 public: 00606 SdsArrayDouble() : SdsArrayAccessHelper<double>(SDS_DOUBLE) { 00607 } 00608 }; 00615 class SdsArrayFloat : public SdsArrayAccessHelper<float> { 00616 public: 00617 SdsArrayFloat() : SdsArrayAccessHelper<float>(SDS_FLOAT) { 00618 } 00619 }; 00620 00621 #endif /* defined DRAMA_ALLOW_CPP_STDLIB */ 00622 00677 SDSCLASS SdsId { 00678 private: 00679 SdsIdType id; /* Actual Sds id. If 0, then no id is allocated */ 00680 struct { 00681 bool free : 1;/* Set true to cause destructor to free the id*/ 00682 bool del : 1;/* If free is true, destructor will do SdsDelete*/ 00683 bool readfree : 1;/* if free and del, to SdsReadFree */ 00684 } flags; 00685 00686 /* Private routine to clean up, will be called by destructor and 00687 Shallow and Deep copy operations */ 00688 00689 /* If this check free code is not to be run, we don't want the from_where argument, it 00690 causes warnings in all using code. This macro setup allows that 00691 */ 00692 #if defined(SDS_CHECK_FREE)||defined(SDS_CHECK_FREE_W) 00693 #define SDS__CHECK_ARG(_arg_) _arg_ 00694 #else 00695 #define SDS__CHECK_ARG(_arg_) 00696 #endif 00697 00698 00699 void CleanUp(const char * SDS__CHECK_ARG(from_where)) { 00700 /* If we have an id and the free flag is set */ 00701 /* In the future, we should consider do a throw if status goes */ 00702 /* bad, instead of just ignoring it */ 00703 00704 if ((id)&&(flags.free)) 00705 { 00706 /* If del and readfree, we need to do SdsReadFree */ 00707 if ((flags.del)&&(flags.readfree)) 00708 { 00709 StatusType ignore = STATUS__OK; 00710 SdsReadFree(id,&ignore); 00711 } 00712 /* If del and not readfree, we need to to SdsDelete */ 00713 else if (flags.del) 00714 { 00715 StatusType ignore = STATUS__OK; 00716 SdsDelete(id,&ignore); 00717 } 00718 /* Free the id */ 00719 StatusType ignore = STATUS__OK; 00720 #if defined(SDS_CHECK_FREE)||defined(SDS_CHECK_FREE_W) 00721 SdsFreeIdAndCheck("", id, &ignore); 00722 if (ignore != STATUS__OK) 00723 { 00724 fprintf(stderr, "SDS FreeId failure in C++ cleanup(), called from \"%s\" for id %d\n", from_where,(int)id); 00725 fprintf(stderr, " Status Code:%s\n", SdsErrorCodeString(ignore)); 00726 fprintf(stderr, " SdsId object address is %p\n", (void *)(this)); 00727 fprintf(stderr, " Sorry - don't have more exact location information\n"); 00728 fprintf(stderr, " This warning was enabled by SDS_CHECK_FREE or SDS_CHECK_FREE_W macro\n"); 00729 } 00730 #else 00731 SdsFreeId(id,&ignore); 00732 #endif 00733 00734 } 00735 } 00736 /* Assignment and Copy operators, made private to avoid misuse */ 00737 SdsId& operator=(const SdsId& a); /* Assignment */ 00738 SdsId(const SdsId&); /* Copy */ 00739 00740 00741 #ifdef DRAMA_ALLOW_CPP_STDLIB 00742 /* This is used by the ArrayAccess methods to check the item 00743 is appropiate for the SdsArrayAccessHelper being used 00744 */ 00745 void CheckArrayType( 00746 const SdsCodeType code, /* Expected code */ 00747 const int ndims, /* Expected number of dims */ 00748 unsigned long * const dims, /* Actual dims written here */ 00749 StatusType * const status) { 00750 00751 if (*status != STATUS__OK) return; 00752 char name[SDS_C_NAMELEN]; 00753 SdsCodeType tcode; 00754 long tndims; 00755 /* 00756 * Get details on the object. 00757 */ 00758 Info(name, &tcode, &tndims, dims, status); 00759 /* 00760 * Check the code and number of dimensions are correct. 00761 */ 00762 if (tcode != code) 00763 { 00764 *status = SDS__TYPE; 00765 return; 00766 } 00767 if (tndims == 0) 00768 { 00769 *status = SDS__NOTARR; 00770 return; 00771 } 00772 if (tndims != ndims) 00773 { 00774 *status = SDS__INVDIMS; 00775 return; 00776 } 00777 00778 } 00779 /* 00780 * A simplified access to CheckArrayType, for a single dimensional 00781 * array. 00782 */ 00783 void CheckArrayTypeSingleDim( 00784 const SdsCodeType code, 00785 unsigned long * const nitems, /* Actual number of items written here*/ 00786 StatusType * const status) { 00787 00788 unsigned long dims[SDS_C_MAXARRAYDIMS]; 00789 CheckArrayType(code, 1, dims, status); 00790 if (*status != STATUS__OK) return; 00791 *nitems = dims[0]; 00792 00793 } 00794 #endif /* defined DRAMA_ALLOW_CPP_STDLIB */ 00795 00796 public: 00825 SdsId(const SdsIdType item = 0, const bool free=false, 00826 const bool del = false, const bool readfree = false) : 00827 id(item) { 00828 flags.free = free; 00829 flags.del = del; 00830 flags.readfree = readfree; 00831 } 00851 SdsId(void * const data, StatusType * const status, 00852 const bool import = false) : 00853 id(0) { 00854 flags.free = true; 00855 flags.readfree = false; 00856 if (import) 00857 { 00858 SdsImport(data,&id,status); 00859 flags.del = true; 00860 } 00861 else 00862 { 00863 SdsAccess(data,&id,status); 00864 flags.del = false; 00865 } 00866 } 00883 SdsId(const void * const data, StatusType * const status) : id(0) { 00884 flags.free = true; 00885 flags.readfree = false; 00886 flags.del = true; 00887 SdsImport(data,&id,status); 00888 } 00902 SdsId(const char * const filename, StatusType * const status) : 00903 id(0) { 00904 flags.free = true; 00905 flags.del = true; 00906 flags.readfree = true; 00907 SdsRead(filename,&id,status); 00908 } 00924 SdsId(const SdsId &parent_id, const char * const name, 00925 const SdsCodeType code, 00926 StatusType * const status, const long nextra = 0, 00927 const char * const extra = 0) : 00928 id(0) { 00929 flags.free = true; 00930 flags.del = false; 00931 flags.readfree = false; 00932 SdsNew(parent_id.id,name,nextra,extra,code,0,0,&id,status); 00933 } 00945 SdsId(const char * const name, const SdsCodeType code, 00946 StatusType * const status, const long nextra = 0, 00947 const char * const extra = 0) : 00948 id(0) { 00949 flags.free = true; 00950 flags.del = true; 00951 flags.readfree = false; 00952 SdsNew(0,name,nextra,extra,code,0,0,&id,status); 00953 } 00971 SdsId(const SdsId &parent_id, const char * const name, 00972 const SdsCodeType code, 00973 const long ndims, const unsigned long *dims, 00974 StatusType * const status, const long nextra = 0, 00975 const char * const extra = 0) : 00976 id(0) { 00977 flags.free = true; 00978 flags.del = false; 00979 flags.readfree = false; 00980 SdsNew(parent_id.id,name,nextra,extra,code,ndims,dims,&id,status); 00981 } 00997 /* Constructor which creates a new array top-level item */ 00998 SdsId(const char * const name, const SdsCodeType code, 00999 const long ndims, const unsigned long *dims, 01000 StatusType * const status, const long nextra = 0, 01001 const char * const extra = 0) : 01002 id(0) { 01003 flags.free = true; 01004 flags.del = true; 01005 flags.readfree = false; 01006 SdsNew(0,name,nextra,extra,code,ndims,dims,&id,status); 01007 } 01008 01022 SdsId(const SdsId &array_id, const long nindicies, 01023 const unsigned long * const indicies, StatusType * const status) : 01024 id(0) { 01025 flags.free = true; 01026 flags.del = false; 01027 flags.readfree = false; 01028 SdsCell(array_id.id, nindicies, indicies, &id,status); 01029 } 01042 SdsId(const SdsId& source, StatusType * const status): 01043 id(0) { 01044 flags.free = true; 01045 flags.del = true; 01046 flags.readfree = false; 01047 SdsCopy(source.id, &id, status); 01048 } 01061 SdsId(const SdsId& source, const char * const name, 01062 StatusType * const status) : 01063 id(0) { 01064 flags.free = true; 01065 flags.del = false; 01066 flags.readfree = false; 01067 SdsFind(source.id,name,&id,status); 01068 } 01069 01084 SdsId(const SdsId& source, const long index, StatusType * const status): 01085 id(0) { 01086 flags.free = true; 01087 flags.del = false; 01088 flags.readfree = false; 01089 SdsIndex(source.id,index,&id,status); 01090 } 01091 01108 /*Just invoke the private cleanup routine */ 01109 virtual ~SdsId() { 01110 CleanUp("SdsId destructor"); 01111 } 01112 /* Modify flags */ 01113 01119 void SetFree() { flags.free = true; } 01125 void SetDelete() { flags.del = true; } 01126 01135 void ClearDelete() { flags.del = false; } 01136 01144 void Outlive() { flags.free = false; flags.del = false; 01145 flags.readfree = false; } 01146 01147 /* 01148 * General operations, as per similar Sds operation. 01149 * Currently only Delete, Get and Put are virtual. 01150 */ 01151 01168 virtual void Delete(StatusType * const status) { 01169 SdsDelete(id,status); 01170 if (*status == STATUS__OK) 01171 { 01172 flags.del = false; 01173 if (flags.free) 01174 { 01175 SdsFreeId(id, status); 01176 if (*status == STATUS__OK) 01177 { 01178 id = 0; 01179 flags.free = false; 01180 } 01181 } 01182 } 01183 } 01206 void Export(const unsigned long length, 01207 void * const data, 01208 StatusType * const status) { 01209 SdsExport(id,length,data,status); 01210 } 01230 void ExportDefined(const unsigned long length, 01231 void * const data, 01232 StatusType * const status) { 01233 SdsExportDefined(id,length,data,status); 01234 } 01247 void Extract(StatusType * const status) { 01248 SdsExtract(id,status); 01249 /* If we succeed, we need to modify the flags to appropiate for 01250 and indepent toplevel item */ 01251 if (*status == STATUS__OK) 01252 { 01253 flags.free = true; 01254 flags.del = true; 01255 flags.readfree = false; 01256 } 01257 } 01271 void Flush(StatusType * const status) { 01272 SdsFlush(id,status); 01273 } 01296 virtual void Get(const unsigned long length, 01297 void * const data, 01298 StatusType * const status, 01299 unsigned long *actlen = 0, 01300 const unsigned long offset=0) const 01301 { 01302 unsigned long myactlen; 01303 if (!actlen) actlen = &myactlen; 01304 SdsGet(id,length,offset,data,actlen,status); 01305 } 01322 void GetExtra(const unsigned long length, 01323 char * const extra, 01324 StatusType * const status, 01325 unsigned long *actlen = 0) const 01326 { 01327 unsigned long myactlen; 01328 if (!actlen) actlen = &myactlen; 01329 SdsGetExtra(id,length,extra,actlen,status); 01330 } 01351 void Info(char * const name, 01352 SdsCodeType * const code, 01353 long * const ndims, 01354 unsigned long * const dims, 01355 StatusType * const status) const { 01356 SdsInfo(id,name,code,ndims,dims,status); 01357 } 01358 /* Give access to individual things normally returned by SdsInfo*/ 01374 void GetName(char * const name, 01375 StatusType * const status) const { 01376 SdsCodeType code; 01377 long ndims; 01378 unsigned long dims[SDS_C_MAXARRAYDIMS]; 01379 SdsInfo(id,name,&code,&ndims,dims,status); 01380 } 01396 void Code(SdsCodeType * const code, 01397 StatusType * const status) const { 01398 char name[16]; 01399 long ndims; 01400 unsigned long dims[SDS_C_MAXARRAYDIMS]; 01401 SdsInfo(id,name,code,&ndims,dims,status); 01402 } 01422 void Dims(long * const ndims, unsigned long * const dims, 01423 StatusType * const status) const { 01424 char name[16]; 01425 SdsCodeType code; 01426 SdsInfo(id,name,&code,ndims,dims,status); 01427 } 01438 void Insert(SdsId & to_insert, StatusType * const status) { 01439 SdsInsert(id,to_insert.id,status); 01440 /* If we succeed, the new child should not be deleted when 01441 it's id is destroyed, so clear the flag */ 01442 if (*status == STATUS__OK) 01443 to_insert.flags.del = false; 01444 } 01459 void Insert(SdsId & to_insert, const long ndims, 01460 const unsigned long * const dims, 01461 StatusType * const status) { 01462 SdsInsertCell(id,ndims,dims,to_insert.id,status); 01463 /* If we succeed, the new child should not be deleted when 01464 it's id is destroyed, so clear the flag */ 01465 if (*status == STATUS__OK) 01466 to_insert.flags.del = false; 01467 } 01468 01480 void FillArray(const SdsId &elem, StatusType * const status) { 01481 SdsFillArray(id,elem.id,status); 01482 } 01483 01508 void Pointer(void **data, StatusType * const status, 01509 unsigned long * length = 0) { 01510 unsigned long mylength; 01511 if (!length) length = &mylength; 01512 SdsPointer(id,data,length,status); 01513 } 01514 01535 virtual void Put(const unsigned long length, 01536 void * const data, 01537 StatusType * const status, 01538 const unsigned long offset=0) 01539 { 01540 SdsPut(id,length,offset,data,status); 01541 } 01556 void PutExtra(const long nextra, 01557 const char * const extra, 01558 StatusType * const status) 01559 { 01560 SdsPutExtra(id,nextra,extra,status); 01561 } 01571 void Rename(const char * const name, 01572 StatusType * const status) { 01573 SdsRename(id,name,status); 01574 } 01598 void Resize(const long ndims, const unsigned long *dims, 01599 StatusType * const status) { 01600 SdsResize(id,ndims,dims,status); 01601 } 01610 void Size(unsigned long * const bytes, 01611 StatusType * const status) const { 01612 SdsSize(id,bytes,status); 01613 } 01623 void SizeDefined(unsigned long * const bytes, 01624 StatusType * const status) const { 01625 SdsSizeDefined(id,bytes,status); 01626 } 01633 void List(StatusType * const status) const { 01634 SdsList(id,status); 01635 } 01647 void Write(const char * const filename, 01648 StatusType * const status) const { 01649 SdsWrite(id,filename,status); 01650 } 01651 01664 void IsExternal(int * const external, 01665 StatusType * const status) const { 01666 SdsIsExternal(id, external, status); 01667 } 01679 void GetExternInfo(void **data, 01680 StatusType * const status) const { 01681 SdsGetExternInfo(id, data, status); 01682 } 01683 01695 operator SdsIdType(void) const { return id; } 01696 01702 /* Note, if there is no bool type, we can just use the above operator which 01703 returns the Sds id. Similary for Borland Cpp which does not like 01704 this operator (ambigious with the above operator 01705 */ 01706 # if (!defined(CPP_NOBOOL)) && (!defined(BORLAND)) 01707 operator bool(void) const { return (id != 0); } 01708 # endif 01709 01737 SdsIdType COut(const bool outlives, bool * const free = 0, 01738 bool * const del= 0, bool * const readfree = 0) { 01739 if (free) 01740 *free = flags.free; 01741 if (del) 01742 *del = flags.del; 01743 if (readfree) 01744 *readfree = flags.readfree; 01745 if (outlives) 01746 flags.free = flags.del = flags.readfree = false; 01747 return (SdsId::id); 01748 } 01749 /* Obsolete version */ 01779 void COut(const bool outlives, SdsIdType *item, bool * const free = 0, 01780 bool * const del= 0, bool * const readfree = 0) { 01781 *item = COut(outlives,free,del,readfree); 01782 } 01783 01801 void ShallowCopy (SdsId & source, const bool outlives=true) { 01802 if (this != &source) 01803 { 01804 CleanUp("SdsId::ShallowCopy 1"); /* Run destructor on old id */ 01805 id = source.id; 01806 if (outlives) 01807 { 01808 /* If we will outlive the source, then we copy the source's 01809 * flags and set the sources flags to false. 01810 */ 01811 01812 flags.free = source.flags.free; 01813 flags.del = source.flags.del; 01814 flags.readfree = source.flags.readfree; 01815 01816 source.flags.free = source.flags.del = 01817 source.flags.readfree = false; 01818 } 01819 else 01820 { 01821 flags.free = flags.del = flags.readfree = false; 01822 } 01823 } 01824 } 01837 void DeepCopy (const SdsId &source, StatusType * const status) 01838 { 01839 if (this != &source) 01840 { 01841 CleanUp("SdsId::DeepCopy 1"); /* Run destructor code on old id */ 01842 id = 0; 01843 SdsCopy(source.id,&id,status); 01844 flags.free = true; 01845 flags.del = true; 01846 flags.readfree = false; 01847 } 01848 else 01849 { 01850 /* 01851 * this = &source; 01852 * 01853 * Deep copy of self. If this item is external, then 01854 * we actual do a copy - but we have to get the ordering 01855 * right. This ensures that DeepCopy() always gives us 01856 * something we can modify the structure of. 01857 */ 01858 int external; 01859 SdsIsExternal(id, &external, status); 01860 if (external) 01861 { 01862 /* 01863 * copy this to a new SDS id.. 01864 */ 01865 SdsIdType newId; 01866 SdsCopy(id,&newId,status); 01867 01868 if (*status == STATUS__OK) 01869 { 01870 /* 01871 * Run the contructor on "this" and then set up 01872 * this again. 01873 */ 01874 CleanUp("SdsId::DeepCopy 2"); 01875 id = newId; 01876 flags.free = true; 01877 flags.del = true; 01878 flags.readfree = false; 01879 01880 } 01881 01882 } 01883 } 01884 } 01904 void ShallowCopy (const SdsIdType source, const bool free=false, 01905 const bool del = false, const bool readfree = false) 01906 { 01907 CleanUp("SdsId::ShallowCopy 2"); /* Run destructor on old id */ 01908 flags.free = free; 01909 flags.del = del; 01910 flags.readfree = readfree; 01911 id = source; 01912 } 01920 void DeepCopy (const SdsIdType source, StatusType *status) 01921 { 01922 CleanUp("SdsId::DeepCopy 3"); /* Run destructor code on old id */ 01923 id = 0; 01924 SdsCopy(source,&id,status); 01925 flags.free = true; 01926 flags.del = true; 01927 flags.readfree = false; 01928 } 01929 #ifdef DRAMA_ALLOW_CPP_STDLIB 01930 01967 template <typename T> void ArrayAccess( 01968 SdsArrayAccessHelper<T> * const data, 01969 StatusType *const status) { 01970 01971 unsigned long dims[SDS_C_MAXARRAYDIMS]; 01972 CheckArrayTypeSingleDim(data->Code(), dims, status); 01973 if (*status != STATUS__OK) return; 01974 data->SetElements(dims[0]); 01975 01976 Pointer(data->Data(), status); 01977 } 02018 template <typename T> void ArrayAccess( 02019 const unsigned long expitems, /* Expected number of elements in array*/ 02020 SdsArrayAccessHelper<T> * const data, 02021 StatusType *const status) { 02022 02023 unsigned long dims[SDS_C_MAXARRAYDIMS]; 02024 CheckArrayTypeSingleDim(data->Code(), dims, status); 02025 if (*status != STATUS__OK) return; 02026 if (dims[0] != expitems) 02027 { 02028 *status = SDS__INVDIMS; 02029 return; 02030 } 02031 data->SetElements(dims[0]); 02032 Pointer(data->Data(), status); 02033 } 02076 template <typename T> void ArrayAccess( 02077 SdsArrayAccessHelper<T> * const data, 02078 long ndims, 02079 unsigned long dims[], 02080 StatusType *const status) { 02081 02082 if ((ndims < 1)||(ndims > 7)) 02083 { 02084 *status = SDS__INVDIMS; 02085 return; 02086 } 02087 CheckArrayType(data->Code(), ndims, dims, status); 02088 if (*status != STATUS__OK) return; 02089 02090 /* 02091 * work out the number of elements 02092 */ 02093 unsigned long elements = dims[0]; 02094 for (long i = 1; i < ndims ; ++i) 02095 { 02096 elements *= dims[i]; 02097 } 02098 data->SetElements(elements); 02099 /* 02100 * Access the data. 02101 */ 02102 Pointer(data->Data(), status); 02103 } 02104 02105 02151 template <typename T> void ArrayAccess( 02152 SdsArrayAccessHelper<T> * const data, 02153 long *ndims, 02154 unsigned long dims[], 02155 StatusType *const status) { 02156 02157 /* 02158 * A bit of a pain, we need to call Dims to get the number 02159 * of dimensions. 02160 */ 02161 Dims(ndims, dims, status); 02162 /* 02163 * The use the above version where we know the number of dimenions 02164 */ 02165 ArrayAccess(data, *ndims, dims, status); 02166 } 02167 02168 02169 02170 #endif /* defined DRAMA_ALLOW_CPP_STDLIB */ 02171 02172 02173 }; /* class SdsId */ 02174 02175 SDSEXTERN const SdsId SdsNull; 02176 02177 #ifdef DRAMA_ALLOW_CPP_STDLIB 02178 #include <stdio.h> 02187 class SdsIDChecker { 02188 private: 02189 SdsCheckType _chkData; 02190 int _line; 02191 std::string _file; 02192 std::string _function; 02193 public: 02210 SdsIDChecker(int line, const char *file, const char *function) 02211 : _line(line), _file(file), _function(function) { 02212 StatusType ignore = STATUS__OK; 02213 SdsCheckInit(&_chkData, &ignore); 02214 } 02220 virtual ~SdsIDChecker() { 02221 StatusType status = STATUS__OK; 02222 SdsCheck(0, &_chkData, &status); 02223 if (status == SDS__CHK_LEAK) 02224 fprintf(stderr,"Warning:SdsIDChecker:Function leaked SDS id's - function %s, file %s, check object at line %d\n", _function.c_str(), _file.c_str(), _line); 02225 else if (status == SDS__CHK_RELEASED) 02226 fprintf(stderr,"Warning:SdsIDChecker:Function released SDS id's - function %s, file %s, check object at line %d\n", _function.c_str(), _file.c_str(), _line); 02227 } 02228 }; 02240 #define SDS_CHECK_IDS(_function_) SdsIDChecker _sds_id_checker(__LINE__, __FILE__, (_function_)) 02241 #endif /* defined DRAMA_ALLOW_CPP_STDLIB */ 02242 02243 02244 #endif 02245 02246 /* Define SdsMalloc and SdsFree. These are normally just defined 02247 to malloc and free but sometimes when debugging we want different 02248 versions 02249 */ 02250 02251 #define SdsMalloc(_size) (void *)malloc(_size) 02252 #define SdsFree(_where) (void)free((void *)(_where)) 02253 02254 #endif 02255 02256 02257
Click here for the DRAMA home page and here for the AAO home page.
For more information, contact tjf@aaoepp.aao.gov.au Generated on Tue Nov 3 09:09:56 2009 for AAO DRAMA C++ Interfaces by
1.2.18