16 #include "../postgis_config.h"
21 #include "../liblwgeom/liblwgeom.h"
22 #include "../liblwgeom/lwgeom_log.h"
45 #define UTF8_GOOD_RESULT 0
46 #define UTF8_BAD_RESULT 1
47 #define UTF8_NO_RESULT 2
62 utf8(
const char *fromcode,
char *inputbuf,
char **outputbuf)
69 inbytesleft = strlen(inputbuf);
71 cd = iconv_open(
"UTF-8", fromcode);
72 if ( cd == ((iconv_t)(-1)) )
75 outbytesleft = inbytesleft * 3 + 1;
77 *outputbuf = (
char *)
malloc(outbytesleft);
81 memset(*outputbuf, 0, outbytesleft);
82 outputptr = *outputbuf;
85 if ( iconv(cd, &inputbuf, &inbytesleft, &outputptr, &outbytesleft) == (
size_t)-1 )
90 iconvctl(cd, ICONV_SET_TRANSLITERATE, &on);
91 if ( iconv(cd, &inputbuf, &inbytesleft, &outputptr, &outbytesleft) == -1 )
94 iconvctl(cd, ICONV_SET_DISCARD_ILSEQ, &on);
95 if ( iconv(cd, &inputbuf, &inbytesleft, &outputptr, &outbytesleft) == -1 )
142 if (*ptr ==
'\t' || *ptr ==
'\\' || *ptr ==
'\n' || *ptr ==
'\r')
152 size = ptr -
str + toescape + 1;
159 if ( *ptr ==
'\t' || *ptr ==
'\\' || *ptr ==
'\n' || *ptr ==
'\r' )
205 size = ptr -
str + toescape + 1;
263 point4d.
x = obj->
padfX[u];
264 point4d.
y = obj->
padfY[u];
267 point4d.
z = obj->
padfZ[u];
269 point4d.
m = obj->
padfM[u];
286 lwgeom = lwmultipoints[0];
323 LWGEOM **lwmultilinestrings;
327 int u, v, start_vertex, end_vertex;
346 for (u = 0; u < obj->
nParts; u++)
360 for (v = start_vertex; v < end_vertex; v++)
363 point4d.
x = obj->
padfX[v];
364 point4d.
y = obj->
padfY[v];
367 point4d.
z = obj->
padfZ[v];
369 point4d.
m = obj->
padfM[v];
385 lwgeom = lwmultilinestrings[0];
386 lwfree(lwmultilinestrings);
423 for (i = 0; i <
n-1; i++)
425 if (((V[i].
y <= P.
y) && (V[i + 1].
y > P.
y))
426 || ((V[i].
y > P.
y) && (V[i + 1].
y <= P.
y)))
428 double vt = (float)(P.
y - V[i].
y) / (V[i + 1].
y - V[i].
y);
429 if (P.
x < V[i].
x + vt * (V[i + 1].
x - V[i].
x))
447 #if POSTGIS_DEBUG_LEVEL > 0
448 static int call = -1;
452 LWDEBUGF(4,
"FindPolygons[%d]: allocated space for %d rings\n", call, obj->
nParts);
459 for (pi=0; pi < obj->
nParts; pi++)
469 if (pi == obj->
nParts - 1)
487 for (vi = vs; vi < ve; vi++)
509 if (area < 0.0 || obj->nParts == 1)
511 Outer[out_index] = ring;
517 Inner[in_index] = ring;
522 LWDEBUGF(4,
"FindPolygons[%d]: found %d Outer, %d Inners\n", call, out_index, in_index);
526 for (pi = 0; pi < in_index; pi++)
530 Ring *inner = Inner[pi], *outer = NULL;
545 for (i = out_index - 1; i >= 0; i--)
549 in =
PIP(pt, Outer[i]->
list, Outer[i]->
n);
550 if ( in ||
PIP(pt2, Outer[i]->
list, Outer[i]->
n) )
569 LWDEBUGF(4,
"FindPolygons[%d]: hole %d is orphan\n", call, pi);
571 Outer[out_index] = inner;
593 for (pi = 0; pi < npolys; pi++)
621 int polygon_total, ring_total;
641 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"We have a Multipolygon with %d parts, can't use -S switch!"), polygon_total);
650 for (pi = 0; pi < polygon_total; pi++)
659 polyring = Outer[pi];
662 ring_total = ring_total + 1;
663 polyring = polyring->
next;
667 polyring = Outer[pi];
674 for (vi = 0; vi < polyring->
n; vi++)
677 point4d.
x = polyring->
list[vi].
x;
678 point4d.
y = polyring->
list[vi].
y;
681 point4d.
z = polyring->
list[vi].
z;
683 point4d.
m = polyring->
list[vi].
m;
691 polyring = polyring->
next;
692 ring_index = ring_index + 1;
706 lwgeom = lwpolygons[0];
748 for (j = 0; j < strlen(
s); j++)
749 s[j] = tolower(
s[j]);
758 config->
table = NULL;
889 char *newencoding = NULL;
940 state->
pgtype =
"MULTILINESTRING";
947 state->
pgtype =
"MULTIPOLYGON";
954 state->
pgtype =
"MULTIPOINT";
971 state->
pgtype =
"MULTILINESTRINGM";
979 state->
pgtype =
"MULTIPOLYGONM";
987 state->
pgtype =
"MULTIPOINTM";
1002 state->
pgtype =
"MULTILINESTRING";
1011 state->
pgtype =
"MULTIPOLYGON";
1020 state->
pgtype =
"MULTIPOINT";
1028 state->
pgtype =
"GEOMETRY";
1108 int field_precision = 0, field_width = 0;
1112 state->
widths[j] = field_width;
1118 char *encoding_msg =
_(
"Try \"LATIN1\" (Western European), or one of the values described at http://www.gnu.org/software/libiconv/.");
1125 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"Unable to convert field name \"%s\" to UTF-8 (iconv reports \"%s\"). Current encoding is \"%s\". %s"), utf8str, strerror(errno), state->
config->
encoding, encoding_msg);
1127 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"Unable to convert field name to UTF-8 (iconv reports \"%s\"). Current encoding is \"%s\". %s"), strerror(errno), state->
config->
encoding, encoding_msg);
1165 if (name[0] ==
'_' ||
1166 ! strcmp(name,
"gid") ||
1167 ! strcmp(name,
"tableoid") ||
1168 ! strcmp(name,
"cmin") ||
1169 ! strcmp(name,
"cmax") ||
1170 ! strcmp(name,
"xmin") ||
1171 ! strcmp(name,
"xmax") ||
1172 ! strcmp(name,
"primary") ||
1173 ! strcmp(name,
"oid") ||
1174 ! strcmp(name,
"ctid"))
1182 for (
int z = 0; z < j; z++)
1187 snprintf(name + strlen(name),
1198 switch (state->
types[j])
1214 else if (state->
widths[j] >=10 && state->
widths[j] < 19)
1218 else if (state->
widths[j] < 5)
1230 fprintf(stderr,
"Field %s is an FTDouble with width %d and precision %d\n",
1232 if (state->
widths[j] > 18)
1443 int32_t srid = state->
to_srid;
1526 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"Internal error: attempt to generate a COPY statement for data that hasn't been requested in COPY format"));
1550 char *geometry=NULL, *ret;
1618 switch (state->
types[i])
1637 if (val[strlen(val) - 1] ==
'.')
1638 val[strlen(val) - 1] =
'\0';
1658 if (strlen(val) == 0)
1680 char *encoding_msg =
_(
"Try \"LATIN1\" (Western European), or one of the values described at http://www.postgresql.org/docs/current/static/multibyte.html.");
1687 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"Unable to convert data value \"%s\" to UTF-8 (iconv reports \"%s\"). Current encoding is \"%s\". %s"), utf8str, strerror(errno), state->
config->
encoding, encoding_msg);
1689 snprintf(state->
message,
SHPLOADERMSGLEN,
_(
"Unable to convert data value to UTF-8 (iconv reports \"%s\"). Current encoding is \"%s\". %s"), strerror(errno), state->
config->
encoding, encoding_msg);
1744 char *oldlocale = setlocale(LC_NUMERIC,
"C");
1839 setlocale(LC_NUMERIC, oldlocale);
char result[OUT_DOUBLE_BUFFER_SIZE]
int SHPAPI_CALL DBFGetFieldCount(DBFHandle psDBF)
DBFHandle SHPAPI_CALL DBFOpen(const char *pszFilename, const char *pszAccess)
int SHPAPI_CALL DBFGetRecordCount(DBFHandle psDBF)
void SHPAPI_CALL DBFClose(DBFHandle psDBF)
int SHPAPI_CALL DBFIsAttributeNULL(DBFHandle psDBF, int iRecord, int iField)
int SHPAPI_CALL DBFIsRecordDeleted(DBFHandle psDBF, int iShape)
const char SHPAPI_CALL1 * DBFReadStringAttribute(DBFHandle psDBF, int iRecord, int iField){ return STATIC_CAST(const char *, DBFReadAttribute(psDBF, iRecord, iField, 'C')
DBFFieldType SHPAPI_CALL DBFGetFieldInfo(DBFHandle psDBF, int iField, char *pszFieldName, int *pnWidth, int *pnDecimals)
LWPOINT * lwpoint_construct_empty(int32_t srid, char hasz, char hasm)
LWGEOM * lwline_as_lwgeom(const LWLINE *obj)
LWGEOM * lwcollection_as_lwgeom(const LWCOLLECTION *obj)
void lwgeom_free(LWGEOM *geom)
LWGEOM * lwpoly_as_lwgeom(const LWPOLY *obj)
char * lwgeom_to_hexwkb_buffer(const LWGEOM *geom, uint8_t variant)
int lwpoly_add_ring(LWPOLY *poly, POINTARRAY *pa)
Add a ring, allocating extra space if necessary.
#define POINTTYPE
LWTYPE numbers, used internally by PostGIS.
LWLINE * lwline_construct(int32_t srid, GBOX *bbox, POINTARRAY *points)
LWGEOM * lwpoint_as_lwgeom(const LWPOINT *obj)
LWPOINT * lwpoint_construct(int32_t srid, GBOX *bbox, POINTARRAY *point)
POINTARRAY * ptarray_construct_empty(char hasz, char hasm, uint32_t maxpoints)
Create a new POINTARRAY with no points.
char * lwgeom_to_wkt(const LWGEOM *geom, uint8_t variant, int precision, size_t *size_out)
WKT emitter function.
int ptarray_append_point(POINTARRAY *pa, const POINT4D *pt, int allow_duplicates)
Append a point to the end of an existing POINTARRAY If allow_duplicate is LW_FALSE,...
LWCOLLECTION * lwcollection_construct(uint8_t type, int32_t srid, GBOX *bbox, uint32_t ngeoms, LWGEOM **geoms)
#define LW_TRUE
Return types for functions with status returns.
#define FLAGS_SET_M(flags, value)
#define SRID_UNKNOWN
Unknown SRID value.
#define FLAGS_SET_Z(flags, value)
LWPOLY * lwpoly_construct_empty(int32_t srid, char hasz, char hasm)
#define LWDEBUGF(level, msg,...)
SHPObject SHPAPI_CALL1 * SHPReadObject(SHPHandle hSHP, int iShape);int SHPAPI_CALL SHPWriteObject(SHPHandle hSHP, int iShape, SHPObject *psObject
void SHPAPI_CALL SHPClose(SHPHandle hSHP)
void SHPAPI_CALL SHPDestroyObject(SHPObject *psObject)
SHPHandle SHPAPI_CALL SHPOpen(const char *pszShapeFile, const char *pszAccess)
void SHPAPI_CALL SHPGetInfo(SHPHandle hSHP, int *pnEntities, int *pnShapeType, double *padfMinBound, double *padfMaxBound)
static int utf8(const char *fromcode, char *inputbuf, char **outputbuf)
int GeneratePointGeometry(SHPLOADERSTATE *state, SHPObject *obj, char **geometry, int force_multi)
Generate an allocated geometry string for shapefile object obj using the state parameters if "force_m...
int ShpLoaderGetRecordCount(SHPLOADERSTATE *state)
int PIP(Point P, Point *V, int n)
PIP(): crossing number test for a point in a polygon input: P = a point, V[] = vertex points of a pol...
char * escape_insert_string(char *str)
Escape input string suitable for INSERT.
int GeneratePolygonGeometry(SHPLOADERSTATE *state, SHPObject *obj, char **geometry)
Generate an allocated geometry string for shapefile object obj using the state parameters.
int FindPolygons(SHPObject *obj, Ring ***Out)
void ShpLoaderDestroy(SHPLOADERSTATE *state)
char * escape_copy_string(char *str)
Escape input string suitable for COPY.
int ShpLoaderGetSQLCopyStatement(SHPLOADERSTATE *state, char **strheader)
int ShpLoaderOpenShape(SHPLOADERSTATE *state)
void ReleasePolygons(Ring **polys, int npolys)
int ShpLoaderGenerateSQLRowStatement(SHPLOADERSTATE *state, int item, char **strrecord)
void set_loader_config_defaults(SHPLOADERCONFIG *config)
int ShpLoaderGetSQLFooter(SHPLOADERSTATE *state, char **strfooter)
struct struct_point Point
SHPLOADERSTATE * ShpLoaderCreate(SHPLOADERCONFIG *config)
int GenerateLineStringGeometry(SHPLOADERSTATE *state, SHPObject *obj, char **geometry)
Generate an allocated geometry string for shapefile object obj using the state parameters.
int ShpLoaderGetSQLHeader(SHPLOADERSTATE *state, char **strheader)
#define POLICY_NULL_ABORT
#define GEOGRAPHY_DEFAULT
#define SHPLOADERRECISNULL
#define POLICY_NULL_INSERT
#define FORCE_OUTPUT_DISABLE
#define SHPLOADERRECDELETED
int colmap_read(const char *filename, colmap *map, char *errbuf, size_t errbuflen)
Read the content of filename into a symbol map.
void colmap_init(colmap *map)
const char * colmap_pg_by_dbf(colmap *map, const char *dbfname)
void colmap_clean(colmap *map)
char * codepage2encoding(const char *cpg)
void stringbuffer_clear(stringbuffer_t *s)
Reset the stringbuffer_t.
int stringbuffer_aprintf(stringbuffer_t *s, const char *fmt,...)
Appends a formatted string to the current string buffer, using the format and argument list provided.
stringbuffer_t * stringbuffer_create(void)
Allocate a new stringbuffer_t.
void stringbuffer_destroy(stringbuffer_t *s)
Free the stringbuffer_t and all memory managed within it.
const char * stringbuffer_getstring(stringbuffer_t *s)
Returns a reference to the internal string being managed by the stringbuffer.
char * column_map_filename
char message[SHPLOADERMSGLEN]
struct struct_ring * next