shapelib 0.7.2 → 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -27,10 +27,11 @@ static VALUE pt_wkt(VALUE obj)
27
27
  shape_t *self;
28
28
  size_t buflen;
29
29
  char *buf, *cur, *stop;
30
- VALUE wkt;
30
+ VALUE wkt, storage = 0;
31
31
  TypedData_Get_Struct(obj, shape_t, &shape_data_type, self);
32
+ CheckPointVertices(self->obj);
32
33
  buflen = wkt_dlen * 2 + 9;
33
- cur = buf = xmalloc(buflen + 1);
34
+ cur = buf = ALLOCV_N(char, storage, buflen + 1);
34
35
  stop = buf + buflen;
35
36
  strcpy(cur, "POINT(");
36
37
  cur = DblFmtCat(cur, self->obj->padfX[0], stop);
@@ -38,20 +39,20 @@ static VALUE pt_wkt(VALUE obj)
38
39
  cur = DblFmtCat(cur, self->obj->padfY[0], stop);
39
40
  cur = StringCat(cur, ")", stop);
40
41
  wkt = rb_str_new(buf, strlen(buf));
41
- free(buf);
42
+ ALLOCV_END(storage);
42
43
  return wkt;
43
44
  }
44
45
 
45
46
  static VALUE mp_wkt(VALUE obj)
46
47
  {
47
48
  shape_t *self;
48
- VALUE wkt;
49
+ VALUE wkt, storage = 0;
49
50
  size_t buflen;
50
51
  char *buf, *cur, *stop;
51
52
  int iv;
52
53
  TypedData_Get_Struct(obj, shape_t, &shape_data_type, self);
53
- buflen = (2 * wkt_dlen + 3) * self->obj->nVertices + 11;
54
- cur = buf = xmalloc(buflen + 1);
54
+ buflen = (2 * (size_t)wkt_dlen + 3) * self->obj->nVertices + 12;
55
+ cur = buf = ALLOCV_N(char, storage, buflen + 1);
55
56
  stop = buf + buflen;
56
57
  strcpy(buf, "MULTIPOINT(");
57
58
  for (iv = 0; iv < self->obj->nVertices; iv++) {
@@ -63,18 +64,19 @@ static VALUE mp_wkt(VALUE obj)
63
64
  }
64
65
  StringCat(cur, ")", stop);
65
66
  wkt = rb_str_new(buf, strlen(buf));
66
- free(buf);
67
+ ALLOCV_END(storage);
67
68
  return wkt;
68
69
  }
69
70
 
70
71
  static VALUE WKTSinglePolygon(SHPObject *obj)
71
72
  {
72
73
  size_t buflen;
73
- VALUE wkt;
74
+ VALUE wkt, storage = 0;
74
75
  char *buf, *cur, *stop;
75
76
  int ipart, endvert, ivert;
76
- buflen = (2 * wkt_dlen + 3) * obj->nVertices + obj->nParts * 2 + 9;
77
- cur = buf = xmalloc(buflen + 1);
77
+ CheckPartStarts(obj);
78
+ buflen = (2 * (size_t)wkt_dlen + 3) * obj->nVertices + (size_t)obj->nParts * 4 + 9;
79
+ cur = buf = ALLOCV_N(char, storage, buflen + 1);
78
80
  stop = cur + buflen;
79
81
  strcpy(buf, "POLYGON(");
80
82
  for (ipart = 0; ipart < obj->nParts; ipart++) {
@@ -97,7 +99,7 @@ static VALUE WKTSinglePolygon(SHPObject *obj)
97
99
  }
98
100
  cur = StringCat(cur, ")", stop);
99
101
  wkt = rb_str_new(buf, strlen(buf));
100
- free(buf);
102
+ ALLOCV_END(storage);
101
103
  return wkt;
102
104
  }
103
105
 
@@ -120,11 +122,13 @@ static VALUE pl_wkt(VALUE obj)
120
122
  static VALUE WKTSingleArc(SHPObject *obj)
121
123
  {
122
124
  size_t buflen;
123
- VALUE wkt;
125
+ VALUE wkt, storage = 0;
124
126
  char *buf, *cur, *stop;
125
127
  int ivert;
128
+ if (obj->nVertices < 1)
129
+ rb_raise(rb_eArgError, "cannot format an empty line");
126
130
  buflen = (2 * wkt_dlen + 3) * obj->nVertices + 10;
127
- cur = buf = xmalloc(buflen + 1);
131
+ cur = buf = ALLOCV_N(char, storage, buflen + 1);
128
132
  stop = cur + buflen;
129
133
  strcpy(buf, "LINESTRING(");
130
134
  for (ivert = 0; ivert < obj->nVertices; ivert++) {
@@ -136,18 +140,19 @@ static VALUE WKTSingleArc(SHPObject *obj)
136
140
  }
137
141
  cur = StringCat(cur, ")", stop);
138
142
  wkt = rb_str_new(buf, strlen(buf));
139
- free(buf);
143
+ ALLOCV_END(storage);
140
144
  return wkt;
141
145
  }
142
146
 
143
147
  static VALUE WKTMultiArc(SHPObject *obj)
144
148
  {
145
149
  size_t buflen;
146
- VALUE wkt;
150
+ VALUE wkt, storage = 0;
147
151
  char *buf, *cur, *stop;
148
152
  int ipart, endvert, ivert;
149
- buflen = (2 * wkt_dlen + 3) * obj->nVertices + obj->nParts * 1 + 16;
150
- cur = buf = xmalloc(buflen + 1);
153
+ CheckPartStarts(obj);
154
+ buflen = (2 * (size_t)wkt_dlen + 3) * obj->nVertices + (size_t)obj->nParts * 4 + 16;
155
+ cur = buf = ALLOCV_N(char, storage, buflen + 1);
151
156
  stop = cur + buflen;
152
157
  strcpy(buf, "MULTILINESTRING(");
153
158
  for (ipart = 0; ipart < obj->nParts; ipart++) {
@@ -170,7 +175,7 @@ static VALUE WKTMultiArc(SHPObject *obj)
170
175
  }
171
176
  cur = StringCat(cur, ")", stop);
172
177
  wkt = rb_str_new(buf, strlen(buf));
173
- free(buf);
178
+ ALLOCV_END(storage);
174
179
  return wkt;
175
180
  }
176
181
 
@@ -214,6 +219,6 @@ static VALUE sp_wkt(VALUE obj)
214
219
  return pl_wkt(obj);
215
220
  break;
216
221
  }
217
- rb_bug("invalid shape type %d", self->obj->nSHPType);
222
+ rb_raise(rb_eArgError, "unsupported WKT shape type %d", self->obj->nSHPType);
218
223
  return Qnil;
219
224
  }
@@ -1,9 +1,11 @@
1
1
  /* valconv.h */
2
2
 
3
- #define SHP_NODATA_LIM -1.0e-38
4
- #define SHP_NODATA -2.0e-38
3
+ #define SHP_NODATA_LIM -1.0e38
4
+ #define SHP_NODATA -2.0e38
5
+ /* Preserve null measures written by earlier versions of this gem. */
6
+ #define SHP_NODATA_LEGACY -2.0e-38
5
7
  #define SHP_NUM2DBL(value) (NIL_P(value) ? SHP_NODATA : NUM2DBL(value))
6
- #define SHP_FLOAT_NEW(f) (((f) < SHP_NODATA_LIM) ? Qnil : rb_float_new((f)))
8
+ #define SHP_FLOAT_NEW(f) (((f) < SHP_NODATA_LIM || (f) == SHP_NODATA_LEGACY) ? Qnil : rb_float_new((f)))
7
9
  #define CSTR2SYM(s) (ID2SYM(rb_intern((s))))
8
10
  static int NUM2INT_nil(VALUE v) { return NIL_P(v) ? -1 : NUM2INT(v); }
9
11
 
@@ -12,6 +14,9 @@ static const_table_entry sl_consts[] = {
12
14
  { "Integer", INT2FIX((int)FTInteger) },
13
15
  { "Float", INT2FIX((int)FTDouble) },
14
16
  { "Logical", INT2FIX((int)FTLogical) },
17
+ #ifdef HAVE_CONST_FTDATE
18
+ { "Date", INT2FIX((int)FTDate) },
19
+ #endif
15
20
  { NULL, Qnil }
16
21
  };
17
22
 
@@ -48,6 +53,9 @@ static ID *FieldTypeNameTable(void)
48
53
  ids[FTInteger] = rb_intern("Integer");
49
54
  ids[FTDouble] = rb_intern("Float");
50
55
  ids[FTLogical] = rb_intern("Logical");
56
+ #ifdef HAVE_CONST_FTDATE
57
+ ids[FTDate] = rb_intern("Date");
58
+ #endif
51
59
  ids[FTInvalid] = rb_intern("Invalid");
52
60
  return ids;
53
61
  }
@@ -82,13 +90,18 @@ static int Ruby2PartType(VALUE ptype)
82
90
  if (ids[i] == given)
83
91
  return i;
84
92
  }
85
- return -1;
93
+ rb_raise(rb_eArgError, "invalid part type name");
86
94
  break;
87
95
  case T_FIXNUM:
88
- return FIX2INT(ptype);
96
+ i = FIX2INT(ptype);
97
+ break;
89
98
  default:
90
- return NUM2INT(ptype);
99
+ i = NUM2INT(ptype);
100
+ break;
91
101
  }
102
+ if (i < 0 || i > 5)
103
+ rb_raise(rb_eArgError, "invalid part_type %d", i);
104
+ return i;
92
105
  }
93
106
 
94
107
  static VALUE PartType2Ruby(int part_type)
@@ -111,6 +124,9 @@ static DBFFieldType Ruby2FieldType(VALUE obj)
111
124
  case FTInteger:
112
125
  case FTDouble:
113
126
  case FTLogical:
127
+ #ifdef HAVE_CONST_FTDATE
128
+ case FTDate:
129
+ #endif
114
130
  case FTInvalid:
115
131
  return ft;
116
132
  default:
@@ -133,7 +149,7 @@ static VALUE FieldType2Ruby(DBFFieldType ftype)
133
149
  {
134
150
  int ft;
135
151
  ft = ftype;
136
- if (ft < 0 || ft >= FTInvalid)
152
+ if (ft < 0 || ft >= FTInvalid || FieldTypeNameTable()[ft] == 0)
137
153
  return INT2FIX(ft);
138
154
  return ID2SYM(FieldTypeNameTable()[ft]);
139
155
  }
@@ -250,8 +266,12 @@ static int ShapeSym_to_Int(VALUE stype)
250
266
  static int Ruby2ShapeType(VALUE stype)
251
267
  {
252
268
  switch (TYPE(stype)) {
253
- case T_FIXNUM:
254
- return FIX2INT(stype);
269
+ case T_FIXNUM: {
270
+ int type = FIX2INT(stype);
271
+ if (type >= SHPT_NULL && type <= SHPT_MULTIPATCH && ShapeTypeNameTable()[type] != 0)
272
+ return type;
273
+ rb_raise(rb_eArgError, "invalid shape_type %d", type);
274
+ }
255
275
  case T_CLASS:
256
276
  return ShapeClass_to_Int(stype);
257
277
  case T_STRING:
@@ -294,9 +314,10 @@ static VALUE IntUnpack(int *up, unsigned num)
294
314
  static VALUE unpackfmt = 0;
295
315
  VALUE buf;
296
316
  if (unpackfmt == 0) {
297
- unpackid = rb_intern("unpack");
298
- unpackfmt = rb_str_new2("i*");
299
- rb_global_variable(&unpackfmt);
317
+ unpackid = rb_intern("unpack");
318
+ /* Register first: registration can trigger GC. */
319
+ rb_global_variable(&unpackfmt);
320
+ unpackfmt = rb_str_new2("i*");
300
321
  }
301
322
  buf = rb_str_new((char *)up, sizeof(int) * num);
302
323
  return rb_funcall(buf, unpackid, 1, unpackfmt);
@@ -7,7 +7,10 @@ module Shapelib
7
7
  end
8
8
 
9
9
  def latlngs
10
- @latlngs ||= yvals.zip(xvals)
10
+ return @latlngs if @latlngs
11
+ coordinates = yvals.zip(xvals)
12
+ @latlngs = coordinates unless frozen?
13
+ coordinates
11
14
  end
12
15
 
13
16
  def inspect
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Shapelib
2
- VERSION = "0.7.2"
4
+ VERSION = '0.8.0'
3
5
  end
data/lib/shapelib.rb CHANGED
@@ -1,2 +1,3 @@
1
1
  require 'shapelib_ext'
2
- require 'shapelib/shape'
2
+ require 'shapelib/version'
3
+ require 'shapelib/shape'
data/shapelib.gemspec CHANGED
@@ -1,58 +1,58 @@
1
- # Generated by jeweler
2
- # DO NOT EDIT THIS FILE DIRECTLY
3
- # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
- # -*- encoding: utf-8 -*-
5
- # stub: shapelib 0.7.2 ruby lib
6
- # stub: ext/shapelib_ext/extconf.rb
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'lib/shapelib/version'
7
4
 
8
5
  Gem::Specification.new do |s|
9
- s.name = "shapelib".freeze
10
- s.version = "0.7.2"
6
+ s.name = 'shapelib'
7
+ s.version = Shapelib::VERSION
8
+ s.required_ruby_version = '>= 2.6'
9
+ s.licenses = ['MIT', 'LGPL-2.0-only', 'CC-BY-SA-3.0']
11
10
 
12
- s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
13
- s.require_paths = ["lib".freeze]
14
- s.authors = ["prasinos@users.sourceforge.net".freeze, "Mike Mangino".freeze, "Mike Perham".freeze, "Nick Estes".freeze]
15
- s.date = "2026-10-14"
16
- s.description = "Simple wrapper around the shapelib library".freeze
17
- s.email = "nick@nickstoys.com".freeze
18
- s.extensions = ["ext/shapelib_ext/extconf.rb".freeze]
11
+ s.required_rubygems_version = Gem::Requirement.new('>= 0') if s.respond_to? :required_rubygems_version=
12
+ s.require_paths = ['lib']
13
+ s.authors = ['prasinos@users.sourceforge.net', 'Mike Mangino', 'Mike Perham', 'Nick Estes']
14
+ s.description = 'Simple wrapper around the shapelib library'
15
+ s.email = 'nick@nickstoys.com'
16
+ s.extensions = ['ext/shapelib_ext/extconf.rb']
19
17
  s.extra_rdoc_files = [
20
- "README.md"
18
+ 'README.md'
21
19
  ]
22
20
  s.files = [
23
- "README.md",
24
- "Rakefile",
25
- "doc/Interface.html",
26
- "doc/Interface.rd",
27
- "doc/style.css",
28
- "ext/shapelib_ext/depend",
29
- "ext/shapelib_ext/extconf.rb",
30
- "ext/shapelib_ext/main.c",
31
- "ext/shapelib_ext/sfcode.h",
32
- "ext/shapelib_ext/sflist.h",
33
- "ext/shapelib_ext/shpplus.c",
34
- "ext/shapelib_ext/shpplus.h",
35
- "ext/shapelib_ext/spcode.h",
36
- "ext/shapelib_ext/splist.h",
37
- "ext/shapelib_ext/spwkt.h",
38
- "ext/shapelib_ext/valconv.h",
39
- "lib/shapelib.rb",
40
- "lib/shapelib/shape.rb",
41
- "lib/shapelib/version.rb",
42
- "shapelib.gemspec",
43
- "test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.dbf",
44
- "test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.prj",
45
- "test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shp",
46
- "test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shp.xml",
47
- "test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shx",
48
- "test/test_zillow_data.rb"
21
+ 'LICENSE',
22
+ 'LICENSE-MIT',
23
+ 'LICENSE-LGPL',
24
+ 'LICENSE-CC-BY-SA-3.0',
25
+ 'README.md',
26
+ 'Rakefile',
27
+ 'doc/Interface.html',
28
+ 'doc/Interface.rd',
29
+ 'doc/style.css',
30
+ 'ext/shapelib_ext/depend',
31
+ 'ext/shapelib_ext/extconf.rb',
32
+ 'ext/shapelib_ext/main.c',
33
+ 'ext/shapelib_ext/sfcode.h',
34
+ 'ext/shapelib_ext/sflist.h',
35
+ 'ext/shapelib_ext/shpplus.c',
36
+ 'ext/shapelib_ext/shpplus.h',
37
+ 'ext/shapelib_ext/spcode.h',
38
+ 'ext/shapelib_ext/splist.h',
39
+ 'ext/shapelib_ext/spwkt.h',
40
+ 'ext/shapelib_ext/valconv.h',
41
+ 'lib/shapelib.rb',
42
+ 'lib/shapelib/shape.rb',
43
+ 'lib/shapelib/version.rb',
44
+ 'shapelib.gemspec',
45
+ 'test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.dbf',
46
+ 'test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.prj',
47
+ 'test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shp',
48
+ 'test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shp.xml',
49
+ 'test/data/ZillowNeighborhoods-CA/ZillowNeighborhoods-CA.shx',
50
+ 'test/test_zillow_data.rb'
49
51
  ]
50
- s.homepage = "http://github.com/mperham/shapelib".freeze
51
- s.rubygems_version = "3.4.20".freeze
52
- s.summary = "Simple wrapper around the shapelib library".freeze
53
-
54
- s.specification_version = 4
52
+ s.homepage = 'https://github.com/gravatite/shapelib'
53
+ s.summary = 'Simple wrapper around the shapelib library'
55
54
 
56
- s.add_development_dependency(%q<rake-compiler>.freeze, [">= 0.7.0"])
55
+ s.add_development_dependency 'rake', '>= 13.0'
56
+ s.add_development_dependency 'test-unit', '>= 3.0'
57
+ s.metadata['rubygems_mfa_required'] = 'true'
57
58
  end
58
-