Skip to content

Improve MEOS examples#669

Merged
mschoema merged 1 commit intoMobilityDB:masterfrom
estebanzimanyi:tcbuffer
May 11, 2025
Merged

Improve MEOS examples#669
mschoema merged 1 commit intoMobilityDB:masterfrom
estebanzimanyi:tcbuffer

Conversation

@estebanzimanyi
Copy link
Copy Markdown
Member

  • Replicate PostGIS PROJ cache in MEOS
  • Improve functions for spatial types

* Replicate PostGIS PROJ cache in MEOS
* Improve functions for spatial types
@estebanzimanyi estebanzimanyi requested a review from mschoema April 27, 2025 12:21
Copy link
Copy Markdown
Member

@mschoema mschoema left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm still going through the PR, but it will take a bit more time. These are the things I've already noticed.

Comment on lines +223 to +225
install(
FILES "${CMAKE_SOURCE_DIR}/meos/src/geo/spatial_ref_sys.csv"
DESTINATION "${CMAKE_INSTALL_LIBDIR}")
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure this should go to ${CMAKE_INSTALL_LIBDIR}. It should probably go into ${CMAKE_INSTALL_DATAROOTDIR} (/share). Either change this or open an issue related to this so we don't forget to change it later.

Comment on lines +236 to +238
install(
FILES "${CMAKE_SOURCE_DIR}/meos/src/npoint/ways.csv"
DESTINATION "${CMAKE_INSTALL_LIBDIR}")
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same as above

Comment on lines +337 to +802
/*****************************************************************************
* Validity macros
*****************************************************************************/

/**
* @brief Macro for ensuring that a pointer is not null
*/
#if MEOS
#define VALIDATE_NOT_NULL(ptr, ret) \
do { if (! ensure_not_null((void *) (ptr))) return (ret); } while (0)
#else
#define VALIDATE_NOT_NULL(ptr, ret) \
do { assert(ptr); } while (0)
#endif /* MEOS */

/*****************************************************************************/

/**
* @brief Macro for ensuring that a set is an integer set
*/
#if MEOS
#define VALIDATE_INTSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_INTSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_INTSET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_INTSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a set is a big integer set
*/
#if MEOS
#define VALIDATE_BIGINTSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_BIGINTSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_BIGINTSET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_BIGINTSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a set is a float set
*/
#if MEOS
#define VALIDATE_FLOATSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_FLOATSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_FLOATSET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_FLOATSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a set is a text set
*/
#if MEOS
#define VALIDATE_TEXTSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_TEXTSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TEXTSET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_TEXTSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a set is a date set
*/
#if MEOS
#define VALIDATE_DATESET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_DATESET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_DATESET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_DATESET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a set is a timestamptz set
*/
#if MEOS
#define VALIDATE_TSTZSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_set_isof_type((set), T_TSTZSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TSTZSET(set, ret) \
do { \
assert(set); \
assert((set)->settype == T_TSTZSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the span is a number span
*/
#if MEOS
#define VALIDATE_NUMSET(set, ret) \
do { \
if (! ensure_not_null((void *) (set)) || \
! ensure_numset_type((set)->settype) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_NUMSET(set, ret) \
do { \
assert(set); \
assert(numset_type((set)->settype)); \
} while (0)
#endif /* MEOS */

/*****************************************************************************/

/**
* @brief Macro for ensuring that a span is an integer span
*/
#if MEOS
#define VALIDATE_INTSPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_span_isof_type((span), T_INTSPAN) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_INTSPAN(span, ret) \
do { \
assert(span); \
assert((span)->spantype == T_INTSPAN); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span is a big integer span
*/
#if MEOS
#define VALIDATE_BIGINTSPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_span_isof_type((span), T_BIGINTSPAN) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_BIGINTSPAN(span, ret) \
do { \
assert(span); \
assert((span)->spantype == T_BIGINTSPAN); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span is a float span
*/
#if MEOS
#define VALIDATE_FLOATSPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_span_isof_type((span), T_FLOATSPAN) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_FLOATSPAN(span, ret) \
do { \
assert(span); \
assert((span)->spantype == T_FLOATSPAN); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span is a date span
*/
#if MEOS
#define VALIDATE_DATESPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_span_isof_type((span), T_DATESPAN) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_DATESPAN(span, ret) \
do { \
assert(span); \
assert((span)->spantype == T_DATESPAN); \
} while (0)
#endif /* MEOS */


/**
* @brief Macro for ensuring that the span is a timestamptz span
*/
#if MEOS
#define VALIDATE_TSTZSPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_span_isof_type((span), T_TSTZSPAN) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TSTZSPAN(span, ret) \
do { \
assert(span); \
assert((span)->spantype == T_TSTZSPAN); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the span is a number span
*/
#if MEOS
#define VALIDATE_NUMSPAN(span, ret) \
do { \
if (! ensure_not_null((void *) (span)) || \
! ensure_numspan_type((span)->spantype) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_NUMSPAN(span, ret) \
do { \
assert(span); \
assert(numspan_type((span)->spantype)); \
} while (0)
#endif /* MEOS */

/*****************************************************************************/

/**
* @brief Macro for ensuring that a span set is an integer span set
*/
#if MEOS
#define VALIDATE_INTSPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_spanset_isof_type((ss), T_INTSPANSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_INTSPANSET(ss, ret) \
do { \
assert(ss); \
assert((ss)->spansettype == T_INTSPANSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span set is a big integer span set
*/
#if MEOS
#define VALIDATE_BIGINTSPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_spanset_isof_type((ss), T_BIGINTSPANSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_BIGINTSPANSET(ss, ret) \
do { \
assert(ss); \
assert((ss)->spansettype == T_BIGINTSPANSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span set is a float span set
*/
#if MEOS
#define VALIDATE_FLOATSPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_spanset_isof_type((ss), T_FLOATSPANSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_FLOATSPANSET(ss, ret) \
do { \
assert(ss); \
assert((ss)->spansettype == T_FLOATSPANSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that a span set is a date span set
*/
#if MEOS
#define VALIDATE_DATESPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_spanset_isof_type((ss), T_DATESPANSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_DATESPANSET(ss, ret) \
do { \
assert(ss); \
assert((ss)->spansettype == T_DATESPANSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the span set is a timestamptz span set
*/
#if MEOS
#define VALIDATE_TSTZSPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_spanset_isof_type(ss, T_TSTZSPANSET) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TSTZSPANSET(ss, ret) \
do { \
assert(ss); \
assert((ss)->spansettype == T_TSTZSPANSET); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the span set is a number span set
*/
#if MEOS
#define VALIDATE_NUMSPANSET(ss, ret) \
do { \
if (! ensure_not_null((void *) (ss)) || \
! ensure_numspanset_type((ss)->spansettype) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_NUMSPANSET(ss, ret) \
do { \
assert(ss); \
assert(numspanset_type((ss)->spansettype)); \
} while (0)
#endif /* MEOS */

/*****************************************************************************/

/**
* @brief Macro for ensuring that the temporal value is a temporal Boolean
* @note The macro works for the Temporal type and its subtypes TInstant,
* TSequence, and TSequenceSet
*/
#if MEOS
#define VALIDATE_TBOOL(temp, ret) \
do { \
if (! ensure_not_null((void *) (temp)) || \
! ensure_temporal_isof_type((Temporal *) (temp), T_TBOOL) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TBOOL(temp, ret) \
do { \
assert(temp); \
assert(((Temporal *) (temp))->temptype == T_TBOOL); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the temporal value is a temporal integer
* @note The macro works for the Temporal type and its subtypes TInstant,
* TSequence, and TSequenceSet
*/
#if MEOS
#define VALIDATE_TINT(temp, ret) \
do { \
if (! ensure_not_null((void *) (temp)) || \
! ensure_temporal_isof_type((Temporal *) (temp), T_TINT) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TINT(temp, ret) \
do { \
assert(temp); \
assert(((Temporal *) (temp))->temptype == T_TINT); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the temporal value is a temporal float
* @note The macro works for the Temporal type and its subtypes TInstant,
* TSequence, and TSequenceSet
*/
#if MEOS
#define VALIDATE_TFLOAT(temp, ret) \
do { \
if (! ensure_not_null((void *) (temp)) || \
! ensure_temporal_isof_type((Temporal *) (temp), T_TFLOAT) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TFLOAT(temp, ret) \
do { \
assert(temp); \
assert(((Temporal *) (temp))->temptype == T_TFLOAT); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the temporal value is a temporal text
* @note The macro works for the Temporal type and its subtypes TInstant,
* TSequence, and TSequenceSet
*/
#if MEOS
#define VALIDATE_TTEXT(temp, ret) \
do { \
if (! ensure_not_null((void *) (temp)) || \
! ensure_temporal_isof_type((Temporal *) (temp), T_TTEXT) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TTEXT(temp, ret) \
do { \
assert(temp); \
assert(((Temporal *) (temp))->temptype == T_TTEXT); \
} while (0)
#endif /* MEOS */

/**
* @brief Macro for ensuring that the temporal value is a temporal number
* @note The macro works for the Temporal type and its subtypes TInstant,
* TSequence, and TSequenceSet
*/
#if MEOS
#define VALIDATE_TNUMBER(temp, ret) \
do { \
if (! ensure_not_null((void *) (temp)) || \
! ensure_tnumber_type(((Temporal *) (temp))->temptype) ) \
return (ret); \
} while (0)
#else
#define VALIDATE_TNUMBER(temp, ret) \
do { \
assert(temp); \
assert(tnumber_type(((Temporal *) (temp))->temptype)); \
} while (0)
#endif /* MEOS */

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is a mistake, these macros are already in meos_internal.h

Comment on lines +49 to +114
/* An entry in the PROJ SRS cache */
typedef struct struct_PROJSRSCacheItem
{
int32_t srid_from;
int32_t srid_to;
uint64_t hits;
LWPROJ *projection;
} PROJSRSCacheItem;

/* PROJ 4 lookup transaction cache methods */
#define PROJ_CACHE_ITEMS 128

/**
* @brief The proj4 cache holds a fixed number of reprojection entries.
* In normal usage we don't expect it to have many entries, so we always
* linearly scanthe list.
* @note The structure removes the context field from PostGIS PROJSRSCache
*/
typedef struct struct_MEOSPROJSRSCache
{
PROJSRSCacheItem MEOSPROJSRSCache[PROJ_CACHE_ITEMS];
uint32_t PROJSRSCacheCount;
} MEOSPROJSRSCache;

/**
* @brief PROJ 4 backend hash table initial hash size (since 16 is the default
* portal hash table size, and we would typically have 2 entries per portal
* then we shall use a default size of 256)
*/
#define PROJ_BACKEND_HASH_SIZE 256

/* Global variable to hold the Proj object cache */
MEOSPROJSRSCache *MEOS_PROJ_CACHE = NULL;

/**
* @brief Utility structure to get many potential string representations
* from spatial_ref_sys query
*/
typedef struct
{
char *authtext; /* auth_name:auth_srid */
char *srtext;
char *proj4text;
} PjStrs;

/*****************************************************************************
* Definitions for reading the spatial_ref_sys.csv file
*****************************************************************************/

#if MEOS
/* Maximum length in characters of a header record in the input CSV file */
#define MAX_LENGTH_HEADER 1024
/* Maximum length in characters of a geometry in the input data */
#define MAX_LENGTH_SRS_RECORD 5120
/* Location of the spatial_ref_sys.csv file */
#define SPATIAL_REF_SYS_CSV "/usr/local/lib/spatial_ref_sys.csv"

typedef struct
{
char auth_name[256];
int32_t auth_srid;
char proj4text[2048];
char srtext[2048];
} spatial_ref_sys_record;
#endif /* MEOS */

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think most of this should be in a header file.

Copy link
Copy Markdown
Member

@mschoema mschoema left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Requested changes will be included in next PR

@mschoema mschoema merged commit 3ac012c into MobilityDB:master May 11, 2025
10 of 16 checks passed
@mschoema mschoema deleted the tcbuffer branch May 11, 2025 06:08
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants