From: Sandro Santilli Date: Wed, 6 Apr 2005 10:46:10 +0000 (+0000) Subject: Bugfix in -w (hwgeom) handling of ZM shapefiles. X-Git-Tag: pgis_1_0_0~23 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=ed152bfe96b45bbc9a931a9f609c79473c4107f8;p=postgis Bugfix in -w (hwgeom) handling of ZM shapefiles. Big reorganizzation of code to easy maintainance. git-svn-id: http://svn.osgeo.org/postgis/trunk@1599 b70326c6-7e19-0410-871a-916f4a2858ee --- diff --git a/loader/shp2pgsql.c b/loader/shp2pgsql.c index 4a8ac0990..a24829ca9 100644 --- a/loader/shp2pgsql.c +++ b/loader/shp2pgsql.c @@ -55,19 +55,17 @@ typedef struct Ring { unsigned int linked; // number of "next" rings } Ring; - /* globals */ int dump_format = 0; //0=insert statements, 1 = dump int quoteidentifiers = 0; int forceint4 = 0; -char opt; +char opt = ' '; char *col_names; -char *geom; char *pgtype; -int istypeM; +int istypeM = 0; int pgdims; unsigned int wkbtype; -char *shp_file; +char *shp_file = NULL; int hwgeom = 0; // old (hwgeom) mode #ifdef USE_ICONV char *encoding=NULL; @@ -77,13 +75,13 @@ DBFFieldType *types; /* Fields type, width and precision */ SHPHandle hSHPHandle; DBFHandle hDBFHandle; int shpfiletype; -SHPObject *obj; +SHPObject *obj=NULL; int *widths; int *precisions; -char *table,*schema; -int num_fields,num_records; +char *table=NULL,*schema=NULL,*geom=NULL; +int num_fields,num_records,num_entities; char **field_names; -char *sr_id; +char *sr_id = NULL; /* Prototypes */ int Insert_attributes(DBFHandle hDBFHandle, int row); @@ -91,7 +89,7 @@ char *make_good_string(char *str); char *protect_quotes_string(char *str); int PIP( Point P, Point* V, int n ); void *safe_malloc(size_t size); -void create_table(void); +void CreateTable(void); void usage(char *me, int exitcode); void InsertPoint(void); void InsertPointWKT(void); @@ -100,12 +98,21 @@ void InsertPolygon(void); void InsertPolygonWKT(void); void InsertLineString(int id); void InsertLineStringWKT(int id); -int parse_cmdline(int ARGC, char **ARGV); +int ParseCmdline(int ARGC, char **ARGV); void SetPgType(void); char *dump_ring(Ring *ring); #ifdef USE_ICONV char *utf8(const char *fromcode, char *inputbuf); #endif +int FindPolygons(SHPObject *obj, Ring ***Out); +void ReleasePolygons(Ring **polys, int npolys); +void DropTable(char *schema, char *table, char *geom); +void GetFieldsSpec(void); +void LoadData(void); +void UpdateSerials(void); +void OpenShape(void); +void LowerCase(char *s); +void Cleanup(void); // WKB @@ -342,41 +349,84 @@ Insert_attributes(DBFHandle hDBFHandle, int row) int main (int ARGC, char **ARGV) { - int trans,field_precision, field_width; - int num_entities, phnshapetype; - double padminbound[8], padmaxbound[8]; - int j,z; - char name[64]; - char name2[64]; - DBFFieldType type = -1; - extern char *optarg; - extern int optind; - istypeM = 0; - - opt = ' '; - j=0; - sr_id = shp_file = table = schema = geom = NULL; - obj=NULL; + /* + * Parse command line + */ + if ( ! ParseCmdline(ARGC, ARGV) ) usage(ARGV[0], 2); - if ( ! parse_cmdline(ARGC, ARGV) ) usage(ARGV[0], 2); + /* + * Open shapefile and initialize globals + */ + OpenShape(); - /* - * Transform table name to lower case unless asked - * to keep original case (we'll quote it later on) + /* + * Compute output geometry type */ - if ( ! quoteidentifiers ) + SetPgType(); + + fprintf(stderr, "Shapefile type: %s\n", SHPTypeName(shpfiletype)); + fprintf(stderr, "Postgis type: %s[%d]\n", pgtype, pgdims); + +#ifdef USE_ICONV + if ( encoding ) { - for (j=0; jnVertices == 0 ) && j--) + obj = SHPReadObject(hSHPHandle,j); + if ( obj == NULL) { - printf("SET CLIENT_ENCODING TO UTF8;\n"); + fprintf(stderr, "Shapefile contains %d NULL object(s)\n", + num_entities); + exit(-1); } -#endif // defined USE_ICONV - if(opt == 'd') +} + +void +UpdateSerials(void) +{ + if ( schema ) { - //---------------Drop the table-------------------------- - // TODO: if the table has more then one geometry column - // the DROP TABLE call will leave spurious records in - // geometry_columns. - // - // If the geometry column in the table being dropped - // does not match 'the_geom' or the name specified with - // -g an error is returned by DropGeometryColumn. - // - // The table to be dropped might not exist. - // - if ( schema ) - { - printf("SELECT DropGeometryColumn('%s','%s','%s');\n", - schema, table, geom); - printf("DROP TABLE \"%s\".\"%s\";\n", schema, table); + if(num_entities>1){ + printf("SELECT setval('\"%s\".\"%s_gid_seq\"', %i, true);\n", schema, table, num_entities-1); } - else - { - printf("SELECT DropGeometryColumn('','%s','%s');\n", - table, geom); - printf("DROP TABLE \"%s\";\n", table); + } + else + { + if(num_entities>1){ + printf("SELECT setval('\"%s_gid_seq\"', %i, true);\n", table, num_entities-1); } } +} +void +CreateTable(void) +{ + int j; + int field_precision, field_width; + DBFFieldType type = -1; - /* - * Get col names and types to fully specify them in inserts + /* + * Create a table for inserting the shapes into with appropriate + * columns and types */ - num_fields = DBFGetFieldCount( hDBFHandle ); - num_records = DBFGetRecordCount(hDBFHandle); - field_names = malloc(num_fields*sizeof(char*)); - types = (DBFFieldType *)malloc(num_fields*sizeof(int)); - widths = malloc(num_fields*sizeof(int)); - precisions = malloc(num_fields*sizeof(int)); - col_names = malloc((num_fields+2) * sizeof(char) * 32); - if(opt != 'a'){ - strcpy(col_names, "(gid," ); - }else{ - strcpy(col_names, "(" ); + + if ( schema ) + { + printf("CREATE TABLE \"%s\".\"%s\" (gid serial PRIMARY KEY", + schema, table); + } + else + { + printf("CREATE TABLE \"%s\" (gid serial PRIMARY KEY", table); } - //fprintf(stderr, "Number of fields from DBF: %d\n", num_fields); for(j=0;jpachFieldType[j] == 'D' ) /* Date field */ { - strcpy(name2+2, name); - name2[0] = '_'; - name2[1] = '_'; - strcpy(name, name2); - } - - /* - * Escape attributes named 'gid' - * and pgsql reserved attribute names - */ - else if( - ! strcmp(name,"gid") || - ! strcmp(name, "tableoid") || - ! strcmp(name, "cmax") || - ! strcmp(name, "xmax") || - ! strcmp(name, "cmin") || - ! strcmp(name, "primary") || - ! strcmp(name, "oid") || - ! strcmp(name, "ctid") - ) { - strcpy(name2+2, name); - name2[0] = '_'; - name2[1] = '_'; - strcpy(name, name2); + printf ("varchar(8)");//date data-type is not supported in API so check for it explicity before the api call. } + + else + { - /* Avoid duplicating field names */ - for(z=0; z < j ; z++){ - if(strcmp(field_names[z],name)==0){ - strcat(name,"__"); - sprintf(name,"%s%i",name,j); - break; + if(type == FTString) + { + printf ("varchar"); + } + else if(type == FTInteger) + { + if ( forceint4 || field_width <= 9 ) + { + printf ("int4"); + } + else if( field_width > 18 ) + { + printf("numeric(%d,0)", + field_width); + } + else + { + printf ("int8"); + } + } + else if(type == FTDouble) + { + if( field_width > 18 ) + { + printf ("numeric"); + } + else + { + printf ("float8"); + } + } + else if(type == FTLogical) + { + printf ("boolean"); + } + else + { + printf ("Invalid type in DBF file"); } } - - - field_names[j] = malloc ( strlen(name)+3 ); - strcpy(field_names[j], name); - - sprintf(col_names, "%s\"%s\",", col_names, name); } - sprintf(col_names, "%s\"%s\")", col_names, geom); - + printf (");\n"); - SHPGetInfo( hSHPHandle, &num_entities, &phnshapetype, &padminbound[0], &padmaxbound[0]); - j=num_entities; - while( ( obj == NULL || obj->nVertices == 0 ) && j--) + //create the geometry column with an addgeometry call to dave's function + if ( schema ) { - obj = SHPReadObject(hSHPHandle,j); + printf("SELECT AddGeometryColumn('%s','%s','%s','%s',", + schema, table, geom, sr_id); } - if ( obj == NULL) + else { - fprintf(stderr, "Shapefile contains %d NULL object(s)\n", num_entities); - exit(-1); + printf("SELECT AddGeometryColumn('','%s','%s','%s',", + table, geom, sr_id); } - trans=0; - - printf("BEGIN;\n"); + printf("'%s',%d);\n", pgtype, pgdims); +} - //if opt is 'a' do nothing, go straight to making inserts - if(opt == 'c' || opt == 'd') create_table(); +void +LoadData(void) +{ + int j, trans=0; if (dump_format){ if ( schema ) @@ -547,15 +584,13 @@ main (int ARGC, char **ARGV) } } - obj = SHPReadObject(hSHPHandle,0); - -/************************************************************** - * - * MAIN SHAPE OBJECTS SCAN - * - **************************************************************/ - for (j=0;j 1) - { - printf("SELECT setval ('\"%s\".\"%s_gid_seq\"', %i, true);\n", schema, table, j-1); - } - } - else - { - printf("\nALTER TABLE ONLY \"%s\" ADD CONSTRAINT \"%s_pkey\" PRIMARY KEY (gid);\n",table,table); - if(j > 1){ - printf("SELECT setval ('\"%s_gid_seq\"', %i, true);\n", table, j-1); - } - } - } - - printf("END;\n"); //End the last transaction - - return(1); -}//end main() - -void -create_table(void) -{ - int j; - int field_precision, field_width; - DBFFieldType type = -1; - - /* - * Create a table for inserting the shapes into with appropriate - * columns and types - */ - - if ( schema ) - { - printf("CREATE TABLE \"%s\".\"%s\" (gid serial", schema, table); - } - else - { - printf("CREATE TABLE \"%s\" (gid serial", table); - } - - for(j=0;jpachFieldType[j] == 'D' ) /* Date field */ - { - printf ("varchar(8)");//date data-type is not supported in API so check for it explicity before the api call. - } - - else - { - - if(type == FTString) - { - printf ("varchar"); - } - else if(type == FTInteger) - { - if ( forceint4 || field_width <= 9 ) - { - printf ("int4"); - } - else if( field_width > 18 ) - { - printf("numeric(%d,0)", - field_width); - } - else - { - printf ("int8"); - } - } - else if(type == FTDouble) - { - if( field_width > 18 ) - { - printf ("numeric"); - } - else - { - printf ("float8"); - } - } - else if(type == FTLogical) - { - printf ("boolean"); - } - else - { - printf ("Invalid type in DBF file"); - } - } - } - printf (");\n"); - - //create the geometry column with an addgeometry call to dave's function - if ( schema ) - { - printf("SELECT AddGeometryColumn('%s','%s','%s','%s',", - schema, table, geom, sr_id); - } - else - { - printf("SELECT AddGeometryColumn('','%s','%s','%s',", - table, geom, sr_id); - } - - printf("'%s',%d);\n", pgtype, pgdims); } void @@ -909,214 +825,19 @@ InsertLineStringWKT(int id) obj->padfX[vi], obj->padfY[vi]); if ( wkbtype & WKBZOFFSET ) - printf(" %.15g", obj->padfZ[vi]); - } - - printf(")"); - - } - - if (dump_format) printf(")\n"); - else printf(")',%s) );\n",sr_id); -} - -//This function basically deals with the polygon case. -//it sorts the polys in order of outer,inner,inner, so that inners -//always come after outers they are within -void -InsertPolygon(void) -{ - Ring **Outer; // Pointers to Outer rings - int out_index=0; // Count of Outer rings - Ring **Inner; // Pointers to Inner rings - int in_index=0; // Count of Inner rings - int pi; // part index - unsigned int subtype = POLYGONTYPE | (wkbtype&WKBZOFFSET) | - (wkbtype&WKBMOFFSET); - -#ifdef DEBUG - static int call = -1; - call++; - - fprintf(stderr, "InsertPolygon[%d]: allocated space for %d rings\n", - call, obj->nParts); -#endif - - // Allocate initial memory - Outer = (Ring**)malloc(sizeof(Ring*)*obj->nParts); - Inner = (Ring**)malloc(sizeof(Ring*)*obj->nParts); - - // Iterate over rings dividing in Outers and Inners - for (pi=0; pinParts; pi++) - { - int vi; // vertex index - int vs; // start index - int ve; // end index - int nv; // number of vertex - double area = 0.0; - Ring *ring; - - // Set start and end vertexes - if ( pi==obj->nParts-1 ) ve = obj->nVertices; - else ve = obj->panPartStart[pi+1]; - vs = obj->panPartStart[pi]; - - // Compute number of vertexes - nv = ve-vs; - - // Allocate memory for a ring - ring = (Ring*)malloc(sizeof(Ring)); - ring->list = (Point*)malloc(sizeof(Point)*nv); - ring->n = nv; - ring->next = NULL; - ring->linked = 0; - - // Iterate over ring vertexes - for ( vi=vs; vilist[vi-vs].x = obj->padfX[vi]; - ring->list[vi-vs].y = obj->padfY[vi]; - ring->list[vi-vs].z = obj->padfZ[vi]; - ring->list[vi-vs].m = obj->padfM[vi]; - - area += (obj->padfX[vi] * obj->padfY[vn]) - - (obj->padfY[vi] * obj->padfX[vn]); - } - - // Close the ring with first vertex - //ring->list[vi].x = obj->padfX[vs]; - //ring->list[vi].y = obj->padfY[vs]; - //ring->list[vi].z = obj->padfZ[vs]; - //ring->list[vi].m = obj->padfM[vs]; - - // Clockwise (or single-part). It's an Outer Ring ! - if(area < 0.0 || obj->nParts ==1) { - Outer[out_index] = ring; - out_index++; - } - - // Counterclockwise. It's an Inner Ring ! - else { - Inner[in_index] = ring; - in_index++; - } - } - -#ifdef DEBUG - fprintf(stderr, "InsertPolygon[%d]: found %d Outer, %d Inners\n", - call, out_index, in_index); -#endif - - // Put the inner rings into the list of the outer rings - // of which they are within - for(pi=0; pilist[0].x; - pt.y = inner->list[0].y; - - pt2.x = inner->list[1].x; - pt2.y = inner->list[1].y; - - for(i=0; ilist, Outer[i]->n); - if( in || PIP(pt2, Outer[i]->list, Outer[i]->n) ) - { - outer = Outer[i]; - break; - } - //fprintf(stderr, "!PIP %s\nOUTE %s\n", dump_ring(inner), dump_ring(Outer[i])); - } - - if ( outer ) - { - outer->linked++; - while(outer->next) outer = outer->next; - outer->next = inner; - } - else - { - // The ring wasn't within any outer rings, - // assume it is a new outer ring. -#ifdef DEBUG - fprintf(stderr, - "InsertPolygon[%d]: hole %d is orphan\n", - call, pi); -#endif - Outer[out_index] = inner; - out_index++; - } - } - - if (!dump_format) printf("'"); - if ( sr_id && sr_id != "-1" ) printf("SRID=%s;", sr_id); - - print_wkb_byte(getEndianByte()); - print_wkb_int(wkbtype); - print_wkb_int(out_index); // npolys - - // Write the coordinates - for(pi=0; pilinked+1); // nrings - - while(poly) - { - int vi; // vertex index - - print_wkb_int(poly->n); // npoints - - for(vi=0; vin; vi++) - { - print_wkb_double(poly->list[vi].x); - print_wkb_double(poly->list[vi].y); - if ( wkbtype & WKBZOFFSET ) - print_wkb_double(poly->list[vi].z); - if ( wkbtype & WKBMOFFSET ) - print_wkb_double(poly->list[vi].m); - } - - poly = poly->next; - } - - } - - if (dump_format) printf("\n"); - else printf("');\n"); - - // Release all memory - for(pi=0; pinext; - free(temp->list); - free(temp); + printf(" %.15g", obj->padfZ[vi]); } + + printf(")"); + } - free(Outer); - free(Inner); + + if (dump_format) printf(")\n"); + else printf(")',%s) );\n",sr_id); } -void -InsertPolygonWKT(void) +int +FindPolygons(SHPObject *obj, Ring ***Out) { Ring **Outer; // Pointers to Outer rings int out_index=0; // Count of Outer rings @@ -1128,7 +849,7 @@ InsertPolygonWKT(void) static int call = -1; call++; - fprintf(stderr, "InsertPolygon[%d]: allocated space for %d rings\n", + fprintf(stderr, "FindPolygons[%d]: allocated space for %d rings\n", call, obj->nParts); #endif @@ -1196,7 +917,7 @@ InsertPolygonWKT(void) } #ifdef DEBUG - fprintf(stderr, "InsertPolygon[%d]: found %d Outer, %d Inners\n", + fprintf(stderr, "FindPolygons[%d]: found %d Outer, %d Inners\n", call, out_index, in_index); #endif @@ -1239,7 +960,7 @@ InsertPolygonWKT(void) // assume it is a new outer ring. #ifdef DEBUG fprintf(stderr, - "InsertPolygon[%d]: hole %d is orphan\n", + "FindPolygons[%d]: hole %d is orphan\n", call, pi); #endif Outer[out_index] = inner; @@ -1247,6 +968,108 @@ InsertPolygonWKT(void) } } + *Out = Outer; + free(Inner); + + return out_index; +} + +void +ReleasePolygons(Ring **polys, int npolys) +{ + int pi; + // Release all memory + for(pi=0; pinext; + free(temp->list); + free(temp); + } + } +} + +//This function basically deals with the polygon case. +//it sorts the polys in order of outer,inner,inner, so that inners +//always come after outers they are within +void +InsertPolygon(void) +{ + unsigned int subtype = POLYGONTYPE | (wkbtype&WKBZOFFSET) | + (wkbtype&WKBMOFFSET); + Ring **Outer; + int out_index; + int pi; // part index + + out_index = FindPolygons(obj, &Outer); + + if (!dump_format) printf("'"); + if ( sr_id && sr_id != "-1" ) printf("SRID=%s;", sr_id); + + print_wkb_byte(getEndianByte()); + print_wkb_int(wkbtype); + print_wkb_int(out_index); // npolys + + // Write the coordinates + for(pi=0; pilinked+1); // nrings + + while(poly) + { + int vi; // vertex index + + print_wkb_int(poly->n); // npoints + + for(vi=0; vin; vi++) + { + print_wkb_double(poly->list[vi].x); + print_wkb_double(poly->list[vi].y); + if ( wkbtype & WKBZOFFSET ) + print_wkb_double(poly->list[vi].z); + if ( wkbtype & WKBMOFFSET ) + print_wkb_double(poly->list[vi].m); + } + + poly = poly->next; + } + + } + + if (dump_format) printf("\n"); + else printf("');\n"); + + // Release all memory + ReleasePolygons(Outer, out_index); + free(Outer); +} + +void +InsertPolygonWKT(void) +{ + Ring **Outer; // Pointers to Outer rings + int out_index=0; // Count of Outer rings + int pi; // part index + +#ifdef DEBUG + static int call = -1; + call++; + + fprintf(stderr, "InsertPolygon[%d]: allocated space for %d rings\n", + call, obj->nParts); +#endif + + out_index = FindPolygons(obj, &Outer); + if (dump_format) printf("SRID=%s;MULTIPOLYGON(",sr_id ); else printf("GeometryFromText('MULTIPOLYGON("); @@ -1288,19 +1111,8 @@ InsertPolygonWKT(void) else printf(")',%s) );\n",sr_id); // Release all memory - for(pi=0; pinext; - free(temp->list); - free(temp); - } - } + ReleasePolygons(Outer, out_index); free(Outer); - free(Inner); } void @@ -1366,11 +1178,13 @@ InsertMultiPoint(void) } int -parse_cmdline(int ARGC, char **ARGV) +ParseCmdline(int ARGC, char **ARGV) { int c; int curindex=0; char *ptr; + extern char *optarg; + extern int optind; while ((c = getopt(ARGC, ARGV, "kcdaDs:g:iW:w")) != EOF){ switch (c) { @@ -1450,6 +1264,16 @@ parse_cmdline(int ARGC, char **ARGV) return 0; } + /* + * Transform table name to lower case unless asked + * to keep original case (we'll quote it later on) + */ + if ( ! quoteidentifiers ) + { + LowerCase(table); + if ( schema ) LowerCase(schema); + } + return 1; } @@ -1480,48 +1304,72 @@ SetPgType(void) pgdims = 2; break; case SHPT_POINTM: // PointM - pgtype = "POINTM"; wkbtype = POINTTYPE | WKBMOFFSET; - pgdims = 3; - istypeM = 1; + if ( ! hwgeom ) { + pgtype = "POINTM"; + pgdims = 3; + istypeM = 1; + } else { + pgtype = "POINT"; + pgdims = 2; + } break; case SHPT_ARCM: // PolyLineM - pgtype = "MULTILINESTRINGM"; wkbtype = MULTILINETYPE | WKBMOFFSET; - pgdims = 3; - istypeM = 1; + if ( ! hwgeom ) { + pgtype = "MULTILINESTRINGM"; + pgdims = 3; + istypeM = 1; + } else { + pgtype = "MULTILINESTRING"; + pgdims = 2; + } break; case SHPT_POLYGONM: // PolygonM - pgtype = "MULTIPOLYGONM"; wkbtype = MULTIPOLYGONTYPE | WKBMOFFSET; - pgdims = 3; - istypeM = 1; + if ( ! hwgeom ) { + pgtype = "MULTIPOLYGONM"; + pgdims = 3; + istypeM = 1; + } else { + pgtype = "MULTIPOLYGON"; + pgdims = 2; + } break; case SHPT_MULTIPOINTM: // MultiPointM - pgtype = "MULTIPOINTM"; wkbtype = MULTIPOINTTYPE | WKBMOFFSET; - pgdims = 3; - istypeM = 1; + if ( ! hwgeom ) { + pgtype = "MULTIPOINTM"; + pgdims = 3; + istypeM = 1; + } else { + pgtype = "MULTIPOINT"; + pgdims = 2; + } break; case SHPT_POINTZ: // PointZ - pgtype = "POINT"; wkbtype = POINTTYPE | WKBMOFFSET | WKBZOFFSET; - pgdims = 4; + pgtype = "POINT"; + if ( ! hwgeom ) pgdims = 4; + else pgdims = 3; break; case SHPT_ARCZ: // PolyLineZ pgtype = "MULTILINESTRING"; wkbtype = MULTILINETYPE | WKBZOFFSET | WKBMOFFSET; - pgdims = 4; + if ( ! hwgeom ) pgdims = 4; + else pgdims = 3; break; case SHPT_POLYGONZ: // MultiPolygonZ pgtype = "MULTIPOLYGON"; wkbtype = MULTIPOLYGONTYPE | WKBZOFFSET | WKBMOFFSET; - pgdims = 4; + if ( ! hwgeom ) pgdims = 4; + else pgdims = 3; break; case SHPT_MULTIPOINTZ: // MultiPointZ pgtype = "MULTIPOINT"; wkbtype = MULTIPOINTTYPE | WKBZOFFSET | WKBMOFFSET; - pgdims = 4; + if ( ! hwgeom ) pgdims = 4; + else pgdims = 3; break; default: pgtype = "GEOMETRY"; @@ -1608,6 +1456,125 @@ print_wkb_bytes(unsigned char *ptr, unsigned int cnt, size_t size) printf("%s", buf); } +void +DropTable(char *schema, char *table, char *geom) +{ + //---------------Drop the table-------------------------- + // TODO: if the table has more then one geometry column + // the DROP TABLE call will leave spurious records in + // geometry_columns. + // + // If the geometry column in the table being dropped + // does not match 'the_geom' or the name specified with + // -g an error is returned by DropGeometryColumn. + // + // The table to be dropped might not exist. + // + if ( schema ) + { + printf("SELECT DropGeometryColumn('%s','%s','%s');\n", + schema, table, geom); + printf("DROP TABLE \"%s\".\"%s\";\n", schema, table); + } + else + { + printf("SELECT DropGeometryColumn('','%s','%s');\n", + table, geom); + printf("DROP TABLE \"%s\";\n", table); + } +} + +void +GetFieldsSpec(void) +{ + int field_precision, field_width; + int j, z; + char name[64]; + char name2[64]; + DBFFieldType type = -1; + + num_fields = DBFGetFieldCount( hDBFHandle ); + num_records = DBFGetRecordCount(hDBFHandle); + field_names = malloc(num_fields*sizeof(char*)); + types = (DBFFieldType *)malloc(num_fields*sizeof(int)); + widths = malloc(num_fields*sizeof(int)); + precisions = malloc(num_fields*sizeof(int)); + col_names = malloc((num_fields+2) * sizeof(char) * 32); + if(opt != 'a'){ + strcpy(col_names, "(gid," ); + }else{ + strcpy(col_names, "(" ); + } + + //fprintf(stderr, "Number of fields from DBF: %d\n", num_fields); + for(j=0;j @@ -1656,6 +1623,10 @@ utf8 (const char *fromcode, char *inputbuf) /********************************************************************** * $Log$ + * Revision 1.85 2005/04/06 10:46:10 strk + * Bugfix in -w (hwgeom) handling of ZM shapefiles. + * Big reorganizzation of code to easy maintainance. + * * Revision 1.84 2005/04/04 20:51:26 strk * Added -w flag to output old (WKT/HWGEOM) sql. *