~ubuntu-branches/ubuntu/precise/spatialite/precise

« back to all changes in this revision

Viewing changes to libspatialite/src/gaiageo/gg_kml.c

  • Committer: Package Import Robot
  • Author(s): David Paleino, Francesco Paolo Lovergine, David Paleino
  • Date: 2011-11-21 12:10:43 UTC
  • mfrom: (4.1.3 sid)
  • Revision ID: package-import@ubuntu.com-20111121121043-0g14o2uf0r343a82
Tags: 3.0.0~beta20110817-3
[ Francesco Paolo Lovergine ]
* Fixed linking order for sqlite3 in debian patch 00-systemlibs.patch.
  (closes: #638929)

[ David Paleino ]
* Conditionally disable full EPSG initialization (for srs_init.c)
  on powerpc, and document what projections are available on that
  architecture (Closes: #649302)

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 
 
3
 gg_kml.c -- KML parser/lexer 
 
4
  
 
5
 version 3.0, 2011 July 20
 
6
 
 
7
 Author: Sandro Furieri a.furieri@lqt.it
 
8
 
 
9
 ------------------------------------------------------------------------------
 
10
 
 
11
 Version: MPL 1.1/GPL 2.0/LGPL 2.1
 
12
 
 
13
 The contents of this file are subject to the Mozilla Public License Version
 
14
 1.1 (the "License"); you may not use this file except in compliance with
 
15
 the License. You may obtain a copy of the License at
 
16
 http://www.mozilla.org/MPL/
 
17
 
 
18
Software distributed under the License is distributed on an "AS IS" basis,
 
19
WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 
20
for the specific language governing rights and limitations under the
 
21
License.
 
22
 
 
23
The Original Code is the SpatiaLite library
 
24
 
 
25
The Initial Developer of the Original Code is Alessandro Furieri
 
26
 
 
27
Portions created by the Initial Developer are Copyright (C) 2011
 
28
the Initial Developer. All Rights Reserved.
 
29
 
 
30
Alternatively, the contents of this file may be used under the terms of
 
31
either the GNU General Public License Version 2 or later (the "GPL"), or
 
32
the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 
33
in which case the provisions of the GPL or the LGPL are applicable instead
 
34
of those above. If you wish to allow use of your version of this file only
 
35
under the terms of either the GPL or the LGPL, and not to allow others to
 
36
use your version of this file under the terms of the MPL, indicate your
 
37
decision by deleting the provisions above and replace them with the notice
 
38
and other provisions required by the GPL or the LGPL. If you do not delete
 
39
the provisions above, a recipient may use your version of this file under
 
40
the terms of any one of the MPL, the GPL or the LGPL.
 
41
 
 
42
*/
 
43
 
 
44
#include <sys/types.h>
 
45
#include <stdlib.h>
 
46
#include <stdio.h>
 
47
#include <string.h>
 
48
 
 
49
#include <assert.h>
 
50
 
 
51
#ifdef SPL_AMALGAMATION         /* spatialite-amalgamation */
 
52
#include <spatialite/sqlite3ext.h>
 
53
#else
 
54
#include <sqlite3ext.h>
 
55
#endif
 
56
 
 
57
#include <spatialite/gaiageo.h>
 
58
 
 
59
int kml_parse_error;
 
60
 
 
61
#define KML_PARSER_OPEN_NODE            1
 
62
#define KML_PARSER_SELF_CLOSED_NODE     2
 
63
#define KML_PARSER_CLOSED_NODE          3
 
64
 
 
65
#define GAIA_KML_UNKNOWN                0
 
66
#define GAIA_KML_POINT                  1
 
67
#define GAIA_KML_LINESTRING             2
 
68
#define GAIA_KML_POLYGON                3
 
69
#define GAIA_KML_MULTIGEOMETRY          4
 
70
 
 
71
/*
 
72
** This is a linked-list struct to store all the values for each token.
 
73
*/
 
74
typedef struct kmlFlexTokenStruct
 
75
{
 
76
    char *value;
 
77
    struct kmlFlexTokenStruct *Next;
 
78
} kmlFlexToken;
 
79
 
 
80
typedef struct kml_coord
 
81
{
 
82
    char *Value;
 
83
    struct kml_coord *Next;
 
84
} kmlCoord;
 
85
typedef kmlCoord *kmlCoordPtr;
 
86
 
 
87
typedef struct kml_attr
 
88
{
 
89
    char *Key;
 
90
    char *Value;
 
91
    struct kml_attr *Next;
 
92
} kmlAttr;
 
93
typedef kmlAttr *kmlAttrPtr;
 
94
 
 
95
typedef struct kml_node
 
96
{
 
97
    char *Tag;
 
98
    int Type;
 
99
    int Error;
 
100
    struct kml_attr *Attributes;
 
101
    struct kml_coord *Coordinates;
 
102
    struct kml_node *Next;
 
103
} kmlNode;
 
104
typedef kmlNode *kmlNodePtr;
 
105
 
 
106
typedef struct kml_dynamic_ring
 
107
{
 
108
    gaiaDynamicLinePtr ring;
 
109
    int interior;
 
110
    int has_z;
 
111
    struct kml_dynamic_ring *next;
 
112
} kmlDynamicRing;
 
113
typedef kmlDynamicRing *kmlDynamicRingPtr;
 
114
 
 
115
typedef struct kml_dynamic_polygon
 
116
{
 
117
    struct kml_dynamic_ring *first;
 
118
    struct kml_dynamic_ring *last;
 
119
} kmlDynamicPolygon;
 
120
typedef kmlDynamicPolygon *kmlDynamicPolygonPtr;
 
121
 
 
122
static kmlDynamicPolygonPtr
 
123
kml_alloc_dyn_polygon (void)
 
124
{
 
125
/* creating a dynamic polygon (ring collection) */
 
126
    kmlDynamicPolygonPtr p = malloc (sizeof (kmlDynamicPolygon));
 
127
    p->first = NULL;
 
128
    p->last = NULL;
 
129
    return p;
 
130
}
 
131
 
 
132
static void
 
133
kml_free_dyn_polygon (kmlDynamicPolygonPtr dyn)
 
134
{
 
135
/* deleting a dynamic polygon (ring collection) */
 
136
    kmlDynamicRingPtr r;
 
137
    kmlDynamicRingPtr rn;
 
138
    if (!dyn)
 
139
        return;
 
140
    r = dyn->first;
 
141
    while (r)
 
142
      {
 
143
          rn = r->next;
 
144
          if (r->ring)
 
145
              gaiaFreeDynamicLine (r->ring);
 
146
          free (r);
 
147
          r = rn;
 
148
      }
 
149
    free (dyn);
 
150
}
 
151
 
 
152
static void
 
153
kml_add_polygon_ring (kmlDynamicPolygonPtr dyn_pg, gaiaDynamicLinePtr dyn,
 
154
                      int interior, int has_z)
 
155
{
 
156
/* inserting a further ring into the collection (dynamic polygon) */
 
157
    kmlDynamicRingPtr p = malloc (sizeof (kmlDynamicRing));
 
158
    p->ring = dyn;
 
159
    p->interior = interior;
 
160
    p->has_z = has_z;
 
161
    p->next = NULL;
 
162
    if (dyn_pg->first == NULL)
 
163
        dyn_pg->first = p;
 
164
    if (dyn_pg->last != NULL)
 
165
        dyn_pg->last->next = p;
 
166
    dyn_pg->last = p;
 
167
}
 
168
 
 
169
static void
 
170
kml_freeString (char **ptr)
 
171
{
 
172
/* releasing a string from the lexer */
 
173
    if (*ptr != NULL)
 
174
        free (*ptr);
 
175
    *ptr = NULL;
 
176
}
 
177
 
 
178
static void
 
179
kml_saveString (char **ptr, const char *str)
 
180
{
 
181
/* saving a string from the lexer */
 
182
    int len = strlen (str);
 
183
    kml_freeString (ptr);
 
184
    *ptr = malloc (len + 1);
 
185
    strcpy (*ptr, str);
 
186
}
 
187
 
 
188
static kmlCoordPtr
 
189
kml_coord (void *value)
 
190
{
 
191
/* creating a coord Item */
 
192
    int len;
 
193
    kmlFlexToken *tok = (kmlFlexToken *) value;
 
194
    kmlCoordPtr c = malloc (sizeof (kmlCoord));
 
195
    len = strlen (tok->value);
 
196
    c->Value = malloc (len + 1);
 
197
    strcpy (c->Value, tok->value);
 
198
    c->Next = NULL;
 
199
    return c;
 
200
}
 
201
 
 
202
static void
 
203
kml_freeCoordinate (kmlCoordPtr c)
 
204
{
 
205
/* deleting a KML coordinate */
 
206
    if (c == NULL)
 
207
        return;
 
208
    if (c->Value)
 
209
        free (c->Value);
 
210
    free (c);
 
211
}
 
212
 
 
213
static kmlAttrPtr
 
214
kml_attribute (void *key, void *value)
 
215
{
 
216
/* creating an attribute */
 
217
    int len;
 
218
    kmlFlexToken *k_tok = (kmlFlexToken *) key;
 
219
    kmlFlexToken *v_tok = (kmlFlexToken *) value;
 
220
    kmlAttrPtr a = malloc (sizeof (kmlAttr));
 
221
    len = strlen (k_tok->value);
 
222
    a->Key = malloc (len + 1);
 
223
    strcpy (a->Key, k_tok->value);
 
224
    len = strlen (v_tok->value);
 
225
/* we need to de-quote the string, removing first and last ".." */
 
226
    if (*(v_tok->value + 0) == '"' && *(v_tok->value + len - 1) == '"')
 
227
      {
 
228
          a->Value = malloc (len - 1);
 
229
          memcpy (a->Value, v_tok->value + 1, len - 1);
 
230
          *(a->Value + len - 1) = '\0';
 
231
      }
 
232
    else
 
233
      {
 
234
          a->Value = malloc (len + 1);
 
235
          strcpy (a->Value, v_tok->value);
 
236
      }
 
237
    a->Next = NULL;
 
238
    return a;
 
239
}
 
240
 
 
241
static void
 
242
kml_freeAttribute (kmlAttrPtr a)
 
243
{
 
244
/* deleting a KML attribute */
 
245
    if (a == NULL)
 
246
        return;
 
247
    if (a->Key)
 
248
        free (a->Key);
 
249
    if (a->Value)
 
250
        free (a->Value);
 
251
    free (a);
 
252
}
 
253
 
 
254
static void
 
255
kml_freeNode (kmlNodePtr n)
 
256
{
 
257
/* deleting a KML node */
 
258
    kmlAttrPtr a;
 
259
    kmlAttrPtr an;
 
260
    kmlCoordPtr c;
 
261
    kmlCoordPtr cn;
 
262
    if (n == NULL)
 
263
        return;
 
264
    a = n->Attributes;
 
265
    while (a)
 
266
      {
 
267
          an = a->Next;
 
268
          kml_freeAttribute (a);
 
269
          a = an;
 
270
      }
 
271
    c = n->Coordinates;
 
272
    while (c)
 
273
      {
 
274
          cn = c->Next;
 
275
          kml_freeCoordinate (c);
 
276
          c = cn;
 
277
      }
 
278
    if (n->Tag)
 
279
        free (n->Tag);
 
280
    free (n);
 
281
}
 
282
 
 
283
static void
 
284
kml_freeTree (kmlNodePtr t)
 
285
{
 
286
/* deleting a KML tree */
 
287
    kmlNodePtr n;
 
288
    kmlNodePtr nn;
 
289
    n = t;
 
290
    while (n)
 
291
      {
 
292
          nn = n->Next;
 
293
          kml_freeNode (n);
 
294
          n = nn;
 
295
      }
 
296
}
 
297
 
 
298
static kmlNodePtr
 
299
kml_createNode (void *tag, void *attributes, void *coords)
 
300
{
 
301
/* creating a node */
 
302
    int len;
 
303
    kmlFlexToken *tok = (kmlFlexToken *) tag;
 
304
    kmlNodePtr n = malloc (sizeof (kmlNode));
 
305
    len = strlen (tok->value);
 
306
    n->Tag = malloc (len + 1);
 
307
    strcpy (n->Tag, tok->value);
 
308
    n->Type = KML_PARSER_OPEN_NODE;
 
309
    n->Error = 0;
 
310
    n->Attributes = attributes;
 
311
    n->Coordinates = coords;
 
312
    n->Next = NULL;
 
313
    return n;
 
314
}
 
315
 
 
316
static kmlNodePtr
 
317
kml_createSelfClosedNode (void *tag, void *attributes)
 
318
{
 
319
/* creating a self-closed node */
 
320
    int len;
 
321
    kmlFlexToken *tok = (kmlFlexToken *) tag;
 
322
    kmlNodePtr n = malloc (sizeof (kmlNode));
 
323
    len = strlen (tok->value);
 
324
    n->Tag = malloc (len + 1);
 
325
    strcpy (n->Tag, tok->value);
 
326
    n->Type = KML_PARSER_SELF_CLOSED_NODE;
 
327
    n->Error = 0;
 
328
    n->Attributes = attributes;
 
329
    n->Coordinates = NULL;
 
330
    n->Next = NULL;
 
331
    return n;
 
332
}
 
333
 
 
334
static kmlNodePtr
 
335
kml_closingNode (void *tag)
 
336
{
 
337
/* creating a closing node */
 
338
    int len;
 
339
    kmlFlexToken *tok = (kmlFlexToken *) tag;
 
340
    kmlNodePtr n = malloc (sizeof (kmlNode));
 
341
    len = strlen (tok->value);
 
342
    n->Tag = malloc (len + 1);
 
343
    strcpy (n->Tag, tok->value);
 
344
    n->Type = KML_PARSER_CLOSED_NODE;
 
345
    n->Error = 0;
 
346
    n->Attributes = NULL;
 
347
    n->Coordinates = NULL;
 
348
    n->Next = NULL;
 
349
    return n;
 
350
}
 
351
 
 
352
static int
 
353
kml_cleanup (kmlFlexToken * token)
 
354
{
 
355
    kmlFlexToken *ptok;
 
356
    kmlFlexToken *ptok_n;
 
357
    if (token == NULL)
 
358
        return 0;
 
359
    ptok = token;
 
360
    while (ptok)
 
361
      {
 
362
          ptok_n = ptok->Next;
 
363
          if (ptok->value != NULL)
 
364
              free (ptok->value);
 
365
          free (ptok);
 
366
          ptok = ptok_n;
 
367
      }
 
368
    return 0;
 
369
}
 
370
 
 
371
static void
 
372
kml_xferString (char **p, const char *str)
 
373
{
 
374
/* saving some token */
 
375
    int len;
 
376
    if (str == NULL)
 
377
      {
 
378
          *p = NULL;
 
379
          return;
 
380
      }
 
381
    len = strlen (str);
 
382
    *p = malloc (len + 1);
 
383
    strcpy (*p, str);
 
384
}
 
385
 
 
386
static int
 
387
guessKmlGeometryType (kmlNodePtr node)
 
388
{
 
389
/* attempting to guess the Geometry Type for a KML node */
 
390
    int type = GAIA_KML_UNKNOWN;
 
391
    if (strcmp (node->Tag, "Point") == 0)
 
392
        type = GAIA_KML_POINT;
 
393
    if (strcmp (node->Tag, "LineString") == 0)
 
394
        type = GAIA_KML_LINESTRING;
 
395
    if (strcmp (node->Tag, "Polygon") == 0)
 
396
        type = GAIA_KML_POLYGON;
 
397
    if (strcmp (node->Tag, "MultiGeometry") == 0)
 
398
        type = GAIA_KML_MULTIGEOMETRY;
 
399
    return type;
 
400
}
 
401
 
 
402
static int
 
403
kml_check_coord (const char *value)
 
404
{
 
405
/* checking a KML coordinate */
 
406
    int decimal = 0;
 
407
    const char *p = value;
 
408
    if (*p == '+' || *p == '-')
 
409
        p++;
 
410
    while (*p != '\0')
 
411
      {
 
412
          if (*p == '.')
 
413
            {
 
414
                if (!decimal)
 
415
                    decimal = 1;
 
416
                else
 
417
                    return 0;
 
418
            }
 
419
          else if (*p >= '0' && *p <= '9')
 
420
              ;
 
421
          else
 
422
              return 0;
 
423
          p++;
 
424
      }
 
425
    return 1;
 
426
}
 
427
 
 
428
static int
 
429
kml_extract_coords (const char *value, double *x, double *y, double *z,
 
430
                    int *count)
 
431
{
 
432
/* extracting KML coords from a comma-separated string */
 
433
    const char *in = value;
 
434
    char buf[1024];
 
435
    char *out = buf;
 
436
    *out = '\0';
 
437
 
 
438
    while (*in != '\0')
 
439
      {
 
440
          if (*in == ',')
 
441
            {
 
442
                *out = '\0';
 
443
                if (*buf != '\0')
 
444
                  {
 
445
                      if (!kml_check_coord (buf))
 
446
                          return 0;
 
447
                      switch (*count)
 
448
                        {
 
449
                        case 0:
 
450
                            *x = atof (buf);
 
451
                            *count += 1;
 
452
                            break;
 
453
                        case 1:
 
454
                            *y = atof (buf);
 
455
                            *count += 1;
 
456
                            break;
 
457
                        case 2:
 
458
                            *z = atof (buf);
 
459
                            *count += 1;
 
460
                            break;
 
461
                        default:
 
462
                            *count += 1;
 
463
                            break;
 
464
                        };
 
465
                  }
 
466
                in++;
 
467
                out = buf;
 
468
                *out = '\0';
 
469
                continue;
 
470
            }
 
471
          *out++ = *in++;
 
472
      }
 
473
    *out = '\0';
 
474
/* parsing the last item */
 
475
    if (*buf != '\0')
 
476
      {
 
477
          if (!kml_check_coord (buf))
 
478
              return 0;
 
479
          switch (*count)
 
480
            {
 
481
            case 0:
 
482
                *x = atof (buf);
 
483
                *count += 1;
 
484
                break;
 
485
            case 1:
 
486
                *y = atof (buf);
 
487
                *count += 1;
 
488
                break;
 
489
            case 2:
 
490
                *z = atof (buf);
 
491
                *count += 1;
 
492
                break;
 
493
            default:
 
494
                *count += 1;
 
495
                break;
 
496
            };
 
497
      }
 
498
    return 1;
 
499
}
 
500
 
 
501
static int
 
502
kml_parse_point_v2 (kmlCoordPtr coord, double *x, double *y, double *z,
 
503
                    int *has_z)
 
504
{
 
505
/* parsing KML <coordinates> [Point] */
 
506
    int count = 0;
 
507
    kmlCoordPtr c = coord;
 
508
    while (c)
 
509
      {
 
510
          if (!kml_extract_coords (c->Value, x, y, z, &count))
 
511
              return 0;
 
512
          c = c->Next;
 
513
      }
 
514
    if (count == 2)
 
515
      {
 
516
          *has_z = 0;
 
517
          return 1;
 
518
      }
 
519
    if (count == 3)
 
520
      {
 
521
          *has_z = 1;
 
522
          return 1;
 
523
      }
 
524
    return 0;
 
525
}
 
526
 
 
527
static int
 
528
kml_parse_point (gaiaGeomCollPtr geom, kmlNodePtr node, kmlNodePtr * next)
 
529
{
 
530
/* parsing a <Point> */
 
531
    double x;
 
532
    double y;
 
533
    double z;
 
534
    int has_z;
 
535
    gaiaGeomCollPtr pt;
 
536
    gaiaGeomCollPtr last;
 
537
 
 
538
    if (strcmp (node->Tag, "coordinates") == 0)
 
539
      {
 
540
          /* parsing a KML <Point> */
 
541
          if (!kml_parse_point_v2 (node->Coordinates, &x, &y, &z, &has_z))
 
542
              return 0;
 
543
          node = node->Next;
 
544
          if (node == NULL)
 
545
              return 0;
 
546
          if (strcmp (node->Tag, "coordinates") == 0)
 
547
              ;
 
548
          else
 
549
              return 0;
 
550
          node = node->Next;
 
551
          if (node == NULL)
 
552
              return 0;
 
553
          if (strcmp (node->Tag, "Point") == 0)
 
554
              ;
 
555
          else
 
556
              return 0;
 
557
          *next = node->Next;
 
558
          goto ok;
 
559
      }
 
560
    return 0;
 
561
 
 
562
  ok:
 
563
/* ok, KML nodes match as expected */
 
564
    if (has_z)
 
565
      {
 
566
          pt = gaiaAllocGeomCollXYZ ();
 
567
          gaiaAddPointToGeomCollXYZ (pt, x, y, z);
 
568
      }
 
569
    else
 
570
      {
 
571
          pt = gaiaAllocGeomColl ();
 
572
          gaiaAddPointToGeomColl (pt, x, y);
 
573
      }
 
574
    last = geom;
 
575
    while (1)
 
576
      {
 
577
          /* searching the last Geometry within chain */
 
578
          if (last->Next == NULL)
 
579
              break;
 
580
          last = last->Next;
 
581
      }
 
582
    last->Next = pt;
 
583
    return 1;
 
584
}
 
585
 
 
586
static int
 
587
kml_extract_multi_coord (const char *value, double *x, double *y, double *z,
 
588
                         int *count, int *follow)
 
589
{
 
590
/* extracting KML coords from a comma-separated string */
 
591
    const char *in = value;
 
592
    char buf[1024];
 
593
    char *out = buf;
 
594
    int last;
 
595
    *out = '\0';
 
596
    while (*in != '\0')
 
597
      {
 
598
          last = *in;
 
599
          if (*in == ',')
 
600
            {
 
601
                *out = '\0';
 
602
                if (*buf != '\0')
 
603
                  {
 
604
                      if (!kml_check_coord (buf))
 
605
                          return 0;
 
606
                      switch (*count)
 
607
                        {
 
608
                        case 0:
 
609
                            *x = atof (buf);
 
610
                            *count += 1;
 
611
                            break;
 
612
                        case 1:
 
613
                            *y = atof (buf);
 
614
                            *count += 1;
 
615
                            break;
 
616
                        case 2:
 
617
                            *z = atof (buf);
 
618
                            *count += 1;
 
619
                            break;
 
620
                        default:
 
621
                            *count += 1;
 
622
                            break;
 
623
                        };
 
624
                  }
 
625
                in++;
 
626
                out = buf;
 
627
                *out = '\0';
 
628
                continue;
 
629
            }
 
630
          *out++ = *in++;
 
631
      }
 
632
    *out = '\0';
 
633
/* parsing the last item */
 
634
    if (*buf != '\0')
 
635
      {
 
636
          if (!kml_check_coord (buf))
 
637
              return 0;
 
638
          switch (*count)
 
639
            {
 
640
            case 0:
 
641
                *x = atof (buf);
 
642
                *count += 1;
 
643
                break;
 
644
            case 1:
 
645
                *y = atof (buf);
 
646
                *count += 1;
 
647
                break;
 
648
            case 2:
 
649
                *z = atof (buf);
 
650
                *count += 1;
 
651
                break;
 
652
            default:
 
653
                *count += 1;
 
654
                break;
 
655
            };
 
656
      }
 
657
    if (last == ',')
 
658
        *follow = 1;
 
659
    else
 
660
        *follow = 0;
 
661
    return 1;
 
662
}
 
663
 
 
664
static int
 
665
kml_extract_multi_coords (kmlCoordPtr coord, double *x, double *y, double *z,
 
666
                          int *count, kmlCoordPtr * next)
 
667
{
 
668
/* extracting KML coords from a comma-separated string */
 
669
    int follow;
 
670
    kmlCoordPtr c = coord;
 
671
    while (c)
 
672
      {
 
673
          if (!kml_extract_multi_coord (c->Value, x, y, z, count, &follow))
 
674
              return 0;
 
675
          if (!follow && c->Next != NULL)
 
676
            {
 
677
                if (*(c->Next->Value) == ',')
 
678
                    follow = 1;
 
679
            }
 
680
          if (follow)
 
681
              c = c->Next;
 
682
          else
 
683
            {
 
684
                *next = c->Next;
 
685
                break;
 
686
            }
 
687
      }
 
688
    return 1;
 
689
}
 
690
 
 
691
static void
 
692
kml_add_point_to_line (gaiaDynamicLinePtr dyn, double x, double y)
 
693
{
 
694
/* appending a point */
 
695
    gaiaAppendPointToDynamicLine (dyn, x, y);
 
696
}
 
697
 
 
698
static void
 
699
kml_add_point_to_lineZ (gaiaDynamicLinePtr dyn, double x, double y, double z)
 
700
{
 
701
/* appending a point */
 
702
    gaiaAppendPointZToDynamicLine (dyn, x, y, z);
 
703
}
 
704
 
 
705
static int
 
706
kml_parse_coordinates (kmlCoordPtr coord, gaiaDynamicLinePtr dyn, int *has_z)
 
707
{
 
708
/* parsing KML <coordinates> [Linestring or Ring] */
 
709
    int count = 0;
 
710
    double x;
 
711
    double y;
 
712
    double z;
 
713
    kmlCoordPtr next;
 
714
    kmlCoordPtr c = coord;
 
715
    while (c)
 
716
      {
 
717
          if (!kml_extract_multi_coords (c, &x, &y, &z, &count, &next))
 
718
              return 0;
 
719
          if (count == 2)
 
720
            {
 
721
                *has_z = 0;
 
722
                kml_add_point_to_line (dyn, x, y);
 
723
                count = 0;
 
724
            }
 
725
          else if (count == 3)
 
726
            {
 
727
                kml_add_point_to_lineZ (dyn, x, y, z);
 
728
                count = 0;
 
729
            }
 
730
          else
 
731
              return 0;
 
732
          c = next;
 
733
      }
 
734
    return 1;
 
735
}
 
736
 
 
737
static int
 
738
kml_count_dyn_points (gaiaDynamicLinePtr dyn)
 
739
{
 
740
/* count how many vertices are into sone linestring/ring */
 
741
    int iv = 0;
 
742
    gaiaPointPtr pt = dyn->First;
 
743
    while (pt)
 
744
      {
 
745
          iv++;
 
746
          pt = pt->Next;
 
747
      }
 
748
    return iv;
 
749
}
 
750
 
 
751
static int
 
752
kml_parse_linestring (gaiaGeomCollPtr geom, kmlNodePtr node, kmlNodePtr * next)
 
753
{
 
754
/* parsing a <LineString> */
 
755
    gaiaGeomCollPtr ln;
 
756
    gaiaGeomCollPtr last;
 
757
    gaiaLinestringPtr new_ln;
 
758
    gaiaPointPtr pt;
 
759
    gaiaDynamicLinePtr dyn = gaiaAllocDynamicLine ();
 
760
    int iv;
 
761
    int has_z = 1;
 
762
    int points = 0;
 
763
 
 
764
    if (strcmp (node->Tag, "coordinates") == 0)
 
765
      {
 
766
          /* parsing a KML <LineString> */
 
767
          if (!kml_parse_coordinates (node->Coordinates, dyn, &has_z))
 
768
              goto error;
 
769
          node = node->Next;
 
770
          if (node == NULL)
 
771
              goto error;
 
772
          if (strcmp (node->Tag, "coordinates") == 0)
 
773
              ;
 
774
          else
 
775
              goto error;
 
776
          node = node->Next;
 
777
          if (node == NULL)
 
778
              goto error;
 
779
          if (strcmp (node->Tag, "LineString") == 0)
 
780
              ;
 
781
          else
 
782
              goto error;
 
783
          *next = node->Next;
 
784
      }
 
785
 
 
786
/* ok, KML nodes match as expected */
 
787
    points = kml_count_dyn_points (dyn);
 
788
    if (points < 2)
 
789
        goto error;
 
790
    if (has_z)
 
791
      {
 
792
          ln = gaiaAllocGeomCollXYZ ();
 
793
          new_ln = gaiaAddLinestringToGeomColl (ln, points);
 
794
          pt = dyn->First;
 
795
          iv = 0;
 
796
          while (pt)
 
797
            {
 
798
                gaiaSetPointXYZ (new_ln->Coords, iv, pt->X, pt->Y, pt->Z);
 
799
                iv++;
 
800
                pt = pt->Next;
 
801
            }
 
802
      }
 
803
    else
 
804
      {
 
805
          ln = gaiaAllocGeomColl ();
 
806
          new_ln = gaiaAddLinestringToGeomColl (ln, points);
 
807
          pt = dyn->First;
 
808
          iv = 0;
 
809
          while (pt)
 
810
            {
 
811
                gaiaSetPoint (new_ln->Coords, iv, pt->X, pt->Y);
 
812
                iv++;
 
813
                pt = pt->Next;
 
814
            }
 
815
      }
 
816
    last = geom;
 
817
    while (1)
 
818
      {
 
819
          /* searching the last Geometry within chain */
 
820
          if (last->Next == NULL)
 
821
              break;
 
822
          last = last->Next;
 
823
      }
 
824
    last->Next = ln;
 
825
    gaiaFreeDynamicLine (dyn);
 
826
    return 1;
 
827
 
 
828
  error:
 
829
    gaiaFreeDynamicLine (dyn);
 
830
    return 0;
 
831
}
 
832
 
 
833
static gaiaDynamicLinePtr
 
834
kml_parse_ring (kmlNodePtr node, int *interior, int *has_z, kmlNodePtr * next)
 
835
{
 
836
/* parsing a generic KML ring */
 
837
    gaiaDynamicLinePtr dyn = gaiaAllocDynamicLine ();
 
838
    *has_z = 1;
 
839
 
 
840
    if (strcmp (node->Tag, "outerBoundaryIs") == 0)
 
841
      {
 
842
          /* parsing a KML <outerBoundaryIs> */
 
843
          node = node->Next;
 
844
          if (node == NULL)
 
845
              goto error;
 
846
          if (strcmp (node->Tag, "LinearRing") == 0)
 
847
              ;
 
848
          else
 
849
              goto error;
 
850
          node = node->Next;
 
851
          if (node == NULL)
 
852
              goto error;
 
853
          if (strcmp (node->Tag, "coordinates") == 0)
 
854
            {
 
855
                /* parsing a KML <kml:coordinates> */
 
856
                if (!kml_parse_coordinates (node->Coordinates, dyn, has_z))
 
857
                    goto error;
 
858
                node = node->Next;
 
859
                if (node == NULL)
 
860
                    goto error;
 
861
                if (strcmp (node->Tag, "coordinates") == 0)
 
862
                    ;
 
863
                else
 
864
                    goto error;
 
865
            }
 
866
          else
 
867
              goto error;
 
868
          node = node->Next;
 
869
          if (node == NULL)
 
870
              goto error;
 
871
          if (strcmp (node->Tag, "LinearRing") == 0)
 
872
              ;
 
873
          else
 
874
              goto error;
 
875
          node = node->Next;
 
876
          if (node == NULL)
 
877
              goto error;
 
878
          if (strcmp (node->Tag, "outerBoundaryIs") == 0)
 
879
              ;
 
880
          else
 
881
              goto error;
 
882
          *interior = 0;
 
883
          *next = node->Next;
 
884
          return dyn;
 
885
      }
 
886
    if (strcmp (node->Tag, "innerBoundaryIs") == 0)
 
887
      {
 
888
          /* parsing a KML <innerBoundaryIs> */
 
889
          node = node->Next;
 
890
          if (node == NULL)
 
891
              goto error;
 
892
          if (strcmp (node->Tag, "LinearRing") == 0)
 
893
              ;
 
894
          else
 
895
              goto error;
 
896
          node = node->Next;
 
897
          if (node == NULL)
 
898
              goto error;
 
899
          if (strcmp (node->Tag, "coordinates") == 0)
 
900
            {
 
901
                /* parsing a KML <coordinates> */
 
902
                if (!kml_parse_coordinates (node->Coordinates, dyn, has_z))
 
903
                    goto error;
 
904
                node = node->Next;
 
905
                if (node == NULL)
 
906
                    goto error;
 
907
                if (strcmp (node->Tag, "coordinates") == 0)
 
908
                    ;
 
909
                else
 
910
                    goto error;
 
911
            }
 
912
          else
 
913
              goto error;
 
914
          node = node->Next;
 
915
          if (node == NULL)
 
916
              goto error;
 
917
          if (strcmp (node->Tag, "LinearRing") == 0)
 
918
              ;
 
919
          else
 
920
              goto error;
 
921
          node = node->Next;
 
922
          if (node == NULL)
 
923
              goto error;
 
924
          if (strcmp (node->Tag, "innerBoundaryIs") == 0)
 
925
              ;
 
926
          else
 
927
              goto error;
 
928
          *interior = 1;
 
929
          *next = node->Next;
 
930
          return dyn;
 
931
      }
 
932
 
 
933
  error:
 
934
    gaiaFreeDynamicLine (dyn);
 
935
    return 0;
 
936
}
 
937
 
 
938
static int
 
939
kml_parse_polygon (gaiaGeomCollPtr geom, kmlNodePtr node, kmlNodePtr * next_n)
 
940
{
 
941
/* parsing a <Polygon> */
 
942
    int interior;
 
943
    int has_z;
 
944
    int inners;
 
945
    int outers;
 
946
    int points;
 
947
    int iv;
 
948
    int ib = 0;
 
949
    gaiaGeomCollPtr pg;
 
950
    gaiaGeomCollPtr last_g;
 
951
    gaiaPolygonPtr new_pg;
 
952
    gaiaRingPtr ring;
 
953
    gaiaDynamicLinePtr dyn;
 
954
    gaiaPointPtr pt;
 
955
    gaiaDynamicLinePtr exterior_ring;
 
956
    kmlNodePtr next;
 
957
    kmlDynamicRingPtr dyn_rng;
 
958
    kmlDynamicPolygonPtr dyn_pg = kml_alloc_dyn_polygon ();
 
959
    kmlNodePtr n = node;
 
960
    while (n)
 
961
      {
 
962
          /* looping on rings */
 
963
          if (strcmp (n->Tag, "Polygon") == 0)
 
964
            {
 
965
                *next_n = n->Next;
 
966
                break;
 
967
            }
 
968
          dyn = kml_parse_ring (n, &interior, &has_z, &next);
 
969
          if (dyn == NULL)
 
970
              goto error;
 
971
          if (kml_count_dyn_points (dyn) < 4)
 
972
            {
 
973
                /* cannot be a valid ring */
 
974
                goto error;
 
975
            }
 
976
          /* checking if the ring is closed */
 
977
          if (has_z)
 
978
            {
 
979
                if (dyn->First->X == dyn->Last->X
 
980
                    && dyn->First->Y == dyn->Last->Y
 
981
                    && dyn->First->Z == dyn->Last->Z)
 
982
                    ;
 
983
                else
 
984
                    goto error;
 
985
            }
 
986
          else
 
987
            {
 
988
                if (dyn->First->X == dyn->Last->X
 
989
                    && dyn->First->Y == dyn->Last->Y)
 
990
                    ;
 
991
                else
 
992
                    goto error;
 
993
            }
 
994
          kml_add_polygon_ring (dyn_pg, dyn, interior, has_z);
 
995
          n = next;
 
996
      }
 
997
/* ok, KML nodes match as expected */
 
998
    inners = 0;
 
999
    outers = 0;
 
1000
    has_z = 1;
 
1001
    dyn_rng = dyn_pg->first;
 
1002
    while (dyn_rng)
 
1003
      {
 
1004
          /* verifying the rings collection */
 
1005
          if (dyn_rng->has_z == 0)
 
1006
              has_z = 0;
 
1007
          if (dyn_rng->interior)
 
1008
              inners++;
 
1009
          else
 
1010
            {
 
1011
                outers++;
 
1012
                points = kml_count_dyn_points (dyn_rng->ring);
 
1013
                exterior_ring = dyn_rng->ring;
 
1014
            }
 
1015
          dyn_rng = dyn_rng->next;
 
1016
      }
 
1017
    if (outers != 1)            /* no exterior ring declared */
 
1018
        goto error;
 
1019
 
 
1020
    if (has_z)
 
1021
      {
 
1022
          pg = gaiaAllocGeomCollXYZ ();
 
1023
          new_pg = gaiaAddPolygonToGeomColl (pg, points, inners);
 
1024
          /* initializing the EXTERIOR RING */
 
1025
          ring = new_pg->Exterior;
 
1026
          pt = exterior_ring->First;
 
1027
          iv = 0;
 
1028
          while (pt)
 
1029
            {
 
1030
                gaiaSetPointXYZ (ring->Coords, iv, pt->X, pt->Y, pt->Z);
 
1031
                iv++;
 
1032
                pt = pt->Next;
 
1033
            }
 
1034
          dyn_rng = dyn_pg->first;
 
1035
          while (dyn_rng)
 
1036
            {
 
1037
                /* initializing any INTERIOR RING */
 
1038
                if (dyn_rng->interior == 0)
 
1039
                  {
 
1040
                      dyn_rng = dyn_rng->next;
 
1041
                      continue;
 
1042
                  }
 
1043
                points = kml_count_dyn_points (dyn_rng->ring);
 
1044
                ring = gaiaAddInteriorRing (new_pg, ib, points);
 
1045
                ib++;
 
1046
                pt = dyn_rng->ring->First;
 
1047
                iv = 0;
 
1048
                while (pt)
 
1049
                  {
 
1050
                      gaiaSetPointXYZ (ring->Coords, iv, pt->X, pt->Y, pt->Z);
 
1051
                      iv++;
 
1052
                      pt = pt->Next;
 
1053
                  }
 
1054
                dyn_rng = dyn_rng->next;
 
1055
            }
 
1056
      }
 
1057
    else
 
1058
      {
 
1059
          pg = gaiaAllocGeomColl ();
 
1060
          new_pg = gaiaAddPolygonToGeomColl (pg, points, inners);
 
1061
          /* initializing the EXTERIOR RING */
 
1062
          ring = new_pg->Exterior;
 
1063
          pt = exterior_ring->First;
 
1064
          iv = 0;
 
1065
          while (pt)
 
1066
            {
 
1067
                gaiaSetPoint (ring->Coords, iv, pt->X, pt->Y);
 
1068
                iv++;
 
1069
                pt = pt->Next;
 
1070
            }
 
1071
          dyn_rng = dyn_pg->first;
 
1072
          while (dyn_rng)
 
1073
            {
 
1074
                /* initializing any INTERIOR RING */
 
1075
                if (dyn_rng->interior == 0)
 
1076
                  {
 
1077
                      dyn_rng = dyn_rng->next;
 
1078
                      continue;
 
1079
                  }
 
1080
                points = kml_count_dyn_points (dyn_rng->ring);
 
1081
                ring = gaiaAddInteriorRing (new_pg, ib, points);
 
1082
                ib++;
 
1083
                pt = dyn_rng->ring->First;
 
1084
                iv = 0;
 
1085
                while (pt)
 
1086
                  {
 
1087
                      gaiaSetPoint (ring->Coords, iv, pt->X, pt->Y);
 
1088
                      iv++;
 
1089
                      pt = pt->Next;
 
1090
                  }
 
1091
                dyn_rng = dyn_rng->next;
 
1092
            }
 
1093
      }
 
1094
 
 
1095
    last_g = geom;
 
1096
    while (1)
 
1097
      {
 
1098
          /* searching the last Geometry within chain */
 
1099
          if (last_g->Next == NULL)
 
1100
              break;
 
1101
          last_g = last_g->Next;
 
1102
      }
 
1103
    last_g->Next = pg;
 
1104
    kml_free_dyn_polygon (dyn_pg);
 
1105
    return 1;
 
1106
 
 
1107
  error:
 
1108
    kml_free_dyn_polygon (dyn_pg);
 
1109
    return 0;
 
1110
}
 
1111
 
 
1112
static int
 
1113
kml_parse_multi_geometry (gaiaGeomCollPtr geom, kmlNodePtr node)
 
1114
{
 
1115
/* parsing a <MultiGeometry> */
 
1116
    kmlNodePtr next;
 
1117
    kmlNodePtr n = node;
 
1118
    while (n)
 
1119
      {
 
1120
          /* looping on Geometry Members */
 
1121
          if (n->Next == NULL)
 
1122
            {
 
1123
                /* verifying the last KML node */
 
1124
                if (strcmp (n->Tag, "MultiGeometry") == 0)
 
1125
                    break;
 
1126
                else
 
1127
                    return 0;
 
1128
            }
 
1129
          if (strcmp (n->Tag, "Point") == 0)
 
1130
            {
 
1131
                n = n->Next;
 
1132
                if (n == NULL)
 
1133
                    return 0;
 
1134
                if (!kml_parse_point (geom, n, &next))
 
1135
                    return 0;
 
1136
                n = next;
 
1137
                continue;
 
1138
            }
 
1139
          else if (strcmp (n->Tag, "LineString") == 0)
 
1140
            {
 
1141
                n = n->Next;
 
1142
                if (n == NULL)
 
1143
                    return 0;
 
1144
                if (!kml_parse_linestring (geom, n, &next))
 
1145
                    return 0;
 
1146
                n = next;
 
1147
                continue;
 
1148
            }
 
1149
          else if (strcmp (n->Tag, "Polygon") == 0)
 
1150
            {
 
1151
                n = n->Next;
 
1152
                if (n == NULL)
 
1153
                    return 0;
 
1154
                if (!kml_parse_polygon (geom, n, &next))
 
1155
                    return 0;
 
1156
                n = next;
 
1157
                continue;
 
1158
            }
 
1159
          else
 
1160
              return 0;
 
1161
      }
 
1162
    return 1;
 
1163
}
 
1164
 
 
1165
static gaiaGeomCollPtr
 
1166
kml_validate_geometry (gaiaGeomCollPtr chain)
 
1167
{
 
1168
    int xy = 0;
 
1169
    int xyz = 0;
 
1170
    int pts = 0;
 
1171
    int lns = 0;
 
1172
    int pgs = 0;
 
1173
    gaiaPointPtr pt;
 
1174
    gaiaLinestringPtr ln;
 
1175
    gaiaPolygonPtr pg;
 
1176
    gaiaPointPtr save_pt;
 
1177
    gaiaLinestringPtr save_ln;
 
1178
    gaiaPolygonPtr save_pg;
 
1179
    gaiaRingPtr i_ring;
 
1180
    gaiaRingPtr o_ring;
 
1181
    int ib;
 
1182
    gaiaGeomCollPtr g;
 
1183
    gaiaGeomCollPtr geom;
 
1184
 
 
1185
    g = chain;
 
1186
    while (g)
 
1187
      {
 
1188
          if (g != chain)
 
1189
            {
 
1190
                if (g->DimensionModel == GAIA_XY)
 
1191
                    xy++;
 
1192
                if (g->DimensionModel == GAIA_XY_Z)
 
1193
                    xyz++;
 
1194
            }
 
1195
          pt = g->FirstPoint;
 
1196
          while (pt)
 
1197
            {
 
1198
                pts++;
 
1199
                save_pt = pt;
 
1200
                pt = pt->Next;
 
1201
            }
 
1202
          ln = g->FirstLinestring;
 
1203
          while (ln)
 
1204
            {
 
1205
                lns++;
 
1206
                save_ln = ln;
 
1207
                ln = ln->Next;
 
1208
            }
 
1209
          pg = g->FirstPolygon;
 
1210
          while (pg)
 
1211
            {
 
1212
                pgs++;
 
1213
                save_pg = pg;
 
1214
                pg = pg->Next;
 
1215
            }
 
1216
          g = g->Next;
 
1217
      }
 
1218
    if (pts == 1 && lns == 0 && pgs == 0)
 
1219
      {
 
1220
          /* POINT */
 
1221
          if (xy > 0)
 
1222
            {
 
1223
                /* 2D [XY] */
 
1224
                geom = gaiaAllocGeomColl ();
 
1225
                if (chain->DeclaredType == GAIA_GEOMETRYCOLLECTION)
 
1226
                    geom->DeclaredType = GAIA_MULTIPOINT;
 
1227
                else
 
1228
                    geom->DeclaredType = GAIA_POINT;
 
1229
                gaiaAddPointToGeomColl (geom, save_pt->X, save_pt->Y);
 
1230
                return geom;
 
1231
            }
 
1232
          else
 
1233
            {
 
1234
                /* 3D [XYZ] */
 
1235
                geom = gaiaAllocGeomCollXYZ ();
 
1236
                if (chain->DeclaredType == GAIA_GEOMETRYCOLLECTION)
 
1237
                    geom->DeclaredType = GAIA_MULTIPOINT;
 
1238
                else
 
1239
                    geom->DeclaredType = GAIA_POINT;
 
1240
                gaiaAddPointToGeomCollXYZ (geom, save_pt->X, save_pt->Y,
 
1241
                                           save_pt->Z);
 
1242
                return geom;
 
1243
            }
 
1244
      }
 
1245
    if (pts == 0 && lns == 1 && pgs == 0)
 
1246
      {
 
1247
          /* LINESTRING */
 
1248
          if (xy > 0)
 
1249
            {
 
1250
                /* 2D [XY] */
 
1251
                geom = gaiaAllocGeomColl ();
 
1252
            }
 
1253
          else
 
1254
            {
 
1255
                /* 3D [XYZ] */
 
1256
                geom = gaiaAllocGeomCollXYZ ();
 
1257
            }
 
1258
          if (chain->DeclaredType == GAIA_GEOMETRYCOLLECTION)
 
1259
              geom->DeclaredType = GAIA_MULTILINESTRING;
 
1260
          else
 
1261
              geom->DeclaredType = GAIA_LINESTRING;
 
1262
          ln = gaiaAddLinestringToGeomColl (geom, save_ln->Points);
 
1263
          gaiaCopyLinestringCoords (ln, save_ln);
 
1264
          return geom;
 
1265
      }
 
1266
    if (pts == 0 && lns == 0 && pgs == 1)
 
1267
      {
 
1268
          /* POLYGON */
 
1269
          if (xy > 0)
 
1270
            {
 
1271
                /* 2D [XY] */
 
1272
                geom = gaiaAllocGeomColl ();
 
1273
            }
 
1274
          else
 
1275
            {
 
1276
                /* 3D [XYZ] */
 
1277
                geom = gaiaAllocGeomCollXYZ ();
 
1278
            }
 
1279
          if (chain->DeclaredType == GAIA_GEOMETRYCOLLECTION)
 
1280
              geom->DeclaredType = GAIA_MULTIPOLYGON;
 
1281
          else
 
1282
              geom->DeclaredType = GAIA_POLYGON;
 
1283
          i_ring = save_pg->Exterior;
 
1284
          pg = gaiaAddPolygonToGeomColl (geom, i_ring->Points,
 
1285
                                         save_pg->NumInteriors);
 
1286
          o_ring = pg->Exterior;
 
1287
          gaiaCopyRingCoords (o_ring, i_ring);
 
1288
          for (ib = 0; ib < save_pg->NumInteriors; ib++)
 
1289
            {
 
1290
                i_ring = save_pg->Interiors + ib;
 
1291
                o_ring = gaiaAddInteriorRing (pg, ib, i_ring->Points);
 
1292
                gaiaCopyRingCoords (o_ring, i_ring);
 
1293
            }
 
1294
          return geom;
 
1295
      }
 
1296
    if (pts >= 1 && lns == 0 && pgs == 0)
 
1297
      {
 
1298
          /* MULTIPOINT */
 
1299
          if (xy > 0)
 
1300
            {
 
1301
                /* 2D [XY] */
 
1302
                geom = gaiaAllocGeomColl ();
 
1303
                geom->DeclaredType = GAIA_MULTIPOINT;
 
1304
                g = chain;
 
1305
                while (g)
 
1306
                  {
 
1307
                      pt = g->FirstPoint;
 
1308
                      while (pt)
 
1309
                        {
 
1310
                            gaiaAddPointToGeomColl (geom, pt->X, pt->Y);
 
1311
                            pt = pt->Next;
 
1312
                        }
 
1313
                      g = g->Next;
 
1314
                  }
 
1315
                return geom;
 
1316
            }
 
1317
          else
 
1318
            {
 
1319
                /* 3D [XYZ] */
 
1320
                geom = gaiaAllocGeomCollXYZ ();
 
1321
                geom->DeclaredType = GAIA_MULTIPOINT;
 
1322
                g = chain;
 
1323
                while (g)
 
1324
                  {
 
1325
                      pt = g->FirstPoint;
 
1326
                      while (pt)
 
1327
                        {
 
1328
                            gaiaAddPointToGeomCollXYZ (geom, pt->X, pt->Y,
 
1329
                                                       pt->Z);
 
1330
                            pt = pt->Next;
 
1331
                        }
 
1332
                      g = g->Next;
 
1333
                  }
 
1334
                return geom;
 
1335
            }
 
1336
      }
 
1337
    if (pts == 0 && lns >= 1 && pgs == 0)
 
1338
      {
 
1339
          /* MULTILINESTRING */
 
1340
          if (xy > 0)
 
1341
            {
 
1342
                /* 2D [XY] */
 
1343
                geom = gaiaAllocGeomColl ();
 
1344
                geom->DeclaredType = GAIA_MULTILINESTRING;
 
1345
                g = chain;
 
1346
                while (g)
 
1347
                  {
 
1348
                      ln = g->FirstLinestring;
 
1349
                      while (ln)
 
1350
                        {
 
1351
                            save_ln =
 
1352
                                gaiaAddLinestringToGeomColl (geom, ln->Points);
 
1353
                            gaiaCopyLinestringCoords (save_ln, ln);
 
1354
                            ln = ln->Next;
 
1355
                        }
 
1356
                      g = g->Next;
 
1357
                  }
 
1358
                return geom;
 
1359
            }
 
1360
          else
 
1361
            {
 
1362
                /* 3D [XYZ] */
 
1363
                geom = gaiaAllocGeomCollXYZ ();
 
1364
                geom->DeclaredType = GAIA_MULTILINESTRING;
 
1365
                g = chain;
 
1366
                while (g)
 
1367
                  {
 
1368
                      ln = g->FirstLinestring;
 
1369
                      while (ln)
 
1370
                        {
 
1371
                            save_ln =
 
1372
                                gaiaAddLinestringToGeomColl (geom, ln->Points);
 
1373
                            gaiaCopyLinestringCoords (save_ln, ln);
 
1374
                            ln = ln->Next;
 
1375
                        }
 
1376
                      g = g->Next;
 
1377
                  }
 
1378
                return geom;
 
1379
            }
 
1380
      }
 
1381
    if (pts == 0 && lns == 0 && pgs >= 1)
 
1382
      {
 
1383
          /* MULTIPOLYGON */
 
1384
          if (xy > 0)
 
1385
            {
 
1386
                /* 2D [XY] */
 
1387
                geom = gaiaAllocGeomColl ();
 
1388
                geom->DeclaredType = GAIA_MULTIPOLYGON;
 
1389
                g = chain;
 
1390
                while (g)
 
1391
                  {
 
1392
                      pg = g->FirstPolygon;
 
1393
                      while (pg)
 
1394
                        {
 
1395
                            i_ring = pg->Exterior;
 
1396
                            save_pg =
 
1397
                                gaiaAddPolygonToGeomColl (geom, i_ring->Points,
 
1398
                                                          pg->NumInteriors);
 
1399
                            o_ring = save_pg->Exterior;
 
1400
                            gaiaCopyRingCoords (o_ring, i_ring);
 
1401
                            for (ib = 0; ib < pg->NumInteriors; ib++)
 
1402
                              {
 
1403
                                  i_ring = pg->Interiors + ib;
 
1404
                                  o_ring =
 
1405
                                      gaiaAddInteriorRing (save_pg, ib,
 
1406
                                                           i_ring->Points);
 
1407
                                  gaiaCopyRingCoords (o_ring, i_ring);
 
1408
                              }
 
1409
                            pg = pg->Next;
 
1410
                        }
 
1411
                      g = g->Next;
 
1412
                  }
 
1413
                return geom;
 
1414
            }
 
1415
          else
 
1416
            {
 
1417
                /* 3D [XYZ] */
 
1418
                geom = gaiaAllocGeomCollXYZ ();
 
1419
                geom->DeclaredType = GAIA_MULTIPOLYGON;
 
1420
                g = chain;
 
1421
                while (g)
 
1422
                  {
 
1423
                      pg = g->FirstPolygon;
 
1424
                      while (pg)
 
1425
                        {
 
1426
                            i_ring = pg->Exterior;
 
1427
                            save_pg =
 
1428
                                gaiaAddPolygonToGeomColl (geom, i_ring->Points,
 
1429
                                                          pg->NumInteriors);
 
1430
                            o_ring = save_pg->Exterior;
 
1431
                            gaiaCopyRingCoords (o_ring, i_ring);
 
1432
                            for (ib = 0; ib < pg->NumInteriors; ib++)
 
1433
                              {
 
1434
                                  i_ring = pg->Interiors + ib;
 
1435
                                  o_ring =
 
1436
                                      gaiaAddInteriorRing (save_pg, ib,
 
1437
                                                           i_ring->Points);
 
1438
                                  gaiaCopyRingCoords (o_ring, i_ring);
 
1439
                              }
 
1440
                            pg = pg->Next;
 
1441
                        }
 
1442
                      g = g->Next;
 
1443
                  }
 
1444
                return geom;
 
1445
            }
 
1446
      }
 
1447
    if ((pts + lns + pgs) > 0)
 
1448
      {
 
1449
          /* GEOMETRYCOLLECTION */
 
1450
          if (xy > 0)
 
1451
            {
 
1452
                /* 2D [XY] */
 
1453
                geom = gaiaAllocGeomColl ();
 
1454
                geom->DeclaredType = GAIA_GEOMETRYCOLLECTION;
 
1455
                g = chain;
 
1456
                while (g)
 
1457
                  {
 
1458
                      pt = g->FirstPoint;
 
1459
                      while (pt)
 
1460
                        {
 
1461
                            gaiaAddPointToGeomColl (geom, pt->X, pt->Y);
 
1462
                            pt = pt->Next;
 
1463
                        }
 
1464
                      ln = g->FirstLinestring;
 
1465
                      while (ln)
 
1466
                        {
 
1467
                            save_ln =
 
1468
                                gaiaAddLinestringToGeomColl (geom, ln->Points);
 
1469
                            gaiaCopyLinestringCoords (save_ln, ln);
 
1470
                            ln = ln->Next;
 
1471
                        }
 
1472
                      pg = g->FirstPolygon;
 
1473
                      while (pg)
 
1474
                        {
 
1475
                            i_ring = pg->Exterior;
 
1476
                            save_pg =
 
1477
                                gaiaAddPolygonToGeomColl (geom, i_ring->Points,
 
1478
                                                          pg->NumInteriors);
 
1479
                            o_ring = save_pg->Exterior;
 
1480
                            gaiaCopyRingCoords (o_ring, i_ring);
 
1481
                            for (ib = 0; ib < pg->NumInteriors; ib++)
 
1482
                              {
 
1483
                                  i_ring = pg->Interiors + ib;
 
1484
                                  o_ring =
 
1485
                                      gaiaAddInteriorRing (save_pg, ib,
 
1486
                                                           i_ring->Points);
 
1487
                                  gaiaCopyRingCoords (o_ring, i_ring);
 
1488
                              }
 
1489
                            pg = pg->Next;
 
1490
                        }
 
1491
                      g = g->Next;
 
1492
                  }
 
1493
                return geom;
 
1494
            }
 
1495
          else
 
1496
            {
 
1497
                /* 3D [XYZ] */
 
1498
                geom = gaiaAllocGeomCollXYZ ();
 
1499
                geom->DeclaredType = GAIA_GEOMETRYCOLLECTION;
 
1500
                g = chain;
 
1501
                while (g)
 
1502
                  {
 
1503
                      pt = g->FirstPoint;
 
1504
                      while (pt)
 
1505
                        {
 
1506
                            gaiaAddPointToGeomCollXYZ (geom, pt->X, pt->Y,
 
1507
                                                       pt->Z);
 
1508
                            pt = pt->Next;
 
1509
                        }
 
1510
                      ln = g->FirstLinestring;
 
1511
                      while (ln)
 
1512
                        {
 
1513
                            save_ln =
 
1514
                                gaiaAddLinestringToGeomColl (geom, ln->Points);
 
1515
                            gaiaCopyLinestringCoords (save_ln, ln);
 
1516
                            ln = ln->Next;
 
1517
                        }
 
1518
                      pg = g->FirstPolygon;
 
1519
                      while (pg)
 
1520
                        {
 
1521
                            i_ring = pg->Exterior;
 
1522
                            save_pg =
 
1523
                                gaiaAddPolygonToGeomColl (geom, i_ring->Points,
 
1524
                                                          pg->NumInteriors);
 
1525
                            o_ring = save_pg->Exterior;
 
1526
                            gaiaCopyRingCoords (o_ring, i_ring);
 
1527
                            for (ib = 0; ib < pg->NumInteriors; ib++)
 
1528
                              {
 
1529
                                  i_ring = pg->Interiors + ib;
 
1530
                                  o_ring =
 
1531
                                      gaiaAddInteriorRing (save_pg, ib,
 
1532
                                                           i_ring->Points);
 
1533
                                  gaiaCopyRingCoords (o_ring, i_ring);
 
1534
                              }
 
1535
                            pg = pg->Next;
 
1536
                        }
 
1537
                      g = g->Next;
 
1538
                  }
 
1539
                return geom;
 
1540
            }
 
1541
      }
 
1542
    return NULL;
 
1543
}
 
1544
 
 
1545
static void
 
1546
kml_free_geom_chain (gaiaGeomCollPtr geom)
 
1547
{
 
1548
/* deleting a chain of preliminary geometries */
 
1549
    gaiaGeomCollPtr gn;
 
1550
    while (geom)
 
1551
      {
 
1552
          gn = geom->Next;
 
1553
          gaiaFreeGeomColl (geom);
 
1554
          geom = gn;
 
1555
      }
 
1556
}
 
1557
 
 
1558
static gaiaGeomCollPtr
 
1559
kml_build_geometry (kmlNodePtr tree)
 
1560
{
 
1561
/* attempting to build a geometry from KML nodes */
 
1562
    gaiaGeomCollPtr geom;
 
1563
    gaiaGeomCollPtr result;
 
1564
    int geom_type;
 
1565
    kmlNodePtr next;
 
1566
 
 
1567
    if (tree == NULL)
 
1568
        return NULL;
 
1569
    geom_type = guessKmlGeometryType (tree);
 
1570
    if (geom_type == GAIA_KML_UNKNOWN)
 
1571
      {
 
1572
          /* unsupported main geometry type */
 
1573
          return NULL;
 
1574
      }
 
1575
/* creating the main geometry */
 
1576
    geom = gaiaAllocGeomColl ();
 
1577
 
 
1578
    switch (geom_type)
 
1579
      {
 
1580
          /* parsing KML nodes accordingly with declared KML type */
 
1581
      case GAIA_KML_POINT:
 
1582
          geom->DeclaredType = GAIA_POINT;
 
1583
          if (!kml_parse_point (geom, tree->Next, &next))
 
1584
              goto error;
 
1585
          break;
 
1586
      case GAIA_KML_LINESTRING:
 
1587
          geom->DeclaredType = GAIA_LINESTRING;
 
1588
          if (!kml_parse_linestring (geom, tree->Next, &next))
 
1589
              goto error;
 
1590
          break;
 
1591
      case GAIA_KML_POLYGON:
 
1592
          geom->DeclaredType = GAIA_POLYGON;
 
1593
          if (!kml_parse_polygon (geom, tree->Next, &next))
 
1594
              goto error;
 
1595
          if (next != NULL)
 
1596
              goto error;
 
1597
          break;
 
1598
      case GAIA_KML_MULTIGEOMETRY:
 
1599
          geom->DeclaredType = GAIA_GEOMETRYCOLLECTION;
 
1600
          if (!kml_parse_multi_geometry (geom, tree->Next))
 
1601
              goto error;
 
1602
          break;
 
1603
      };
 
1604
 
 
1605
/* attempting to build the final geometry */
 
1606
    result = kml_validate_geometry (geom);
 
1607
    if (result == NULL)
 
1608
        goto error;
 
1609
    kml_free_geom_chain (geom);
 
1610
    return result;
 
1611
 
 
1612
  error:
 
1613
    kml_free_geom_chain (geom);
 
1614
    return NULL;
 
1615
}
 
1616
 
 
1617
 
 
1618
 
 
1619
/*
 
1620
** CAVEAT: we must redefine any Lemon/Flex own macro
 
1621
*/
 
1622
#define YYMINORTYPE             KML_MINORTYPE
 
1623
#define YY_CHAR                 KML_YY_CHAR
 
1624
#define input                   kml_input
 
1625
#define ParseAlloc              kmlParseAlloc
 
1626
#define ParseFree               kmlParseFree
 
1627
#define ParseStackPeak          kmlParseStackPeak
 
1628
#define Parse                   kmlParse
 
1629
#define yyStackEntry            kml_yyStackEntry
 
1630
#define yyzerominor             kml_yyzerominor
 
1631
#define yy_accept               kml_yy_accept
 
1632
#define yy_action               kml_yy_action
 
1633
#define yy_base                 kml_yy_base
 
1634
#define yy_buffer_stack         kml_yy_buffer_stack
 
1635
#define yy_buffer_stack_max     kml_yy_buffer_stack_max
 
1636
#define yy_buffer_stack_top     kml_yy_buffer_stack_top
 
1637
#define yy_c_buf_p              kml_yy_c_buf_p
 
1638
#define yy_chk                  kml_yy_chk
 
1639
#define yy_def                  kml_yy_def
 
1640
#define yy_default              kml_yy_default
 
1641
#define yy_destructor           kml_yy_destructor
 
1642
#define yy_ec                   kml_yy_ec
 
1643
#define yy_fatal_error          kml_yy_fatal_error
 
1644
#define yy_find_reduce_action   kml_yy_find_reduce_action
 
1645
#define yy_find_shift_action    kml_yy_find_shift_action
 
1646
#define yy_get_next_buffer      kml_yy_get_next_buffer
 
1647
#define yy_get_previous_state   kml_yy_get_previous_state
 
1648
#define yy_init                 kml_yy_init
 
1649
#define yy_init_globals         kml_yy_init_globals
 
1650
#define yy_lookahead            kml_yy_lookahead
 
1651
#define yy_meta                 kml_yy_meta
 
1652
#define yy_nxt                  kml_yy_nxt
 
1653
#define yy_parse_failed         kml_yy_parse_failed
 
1654
#define yy_pop_parser_stack     kml_yy_pop_parser_stack
 
1655
#define yy_reduce               kml_yy_reduce
 
1656
#define yy_reduce_ofst          kml_yy_reduce_ofst
 
1657
#define yy_shift                kml_yy_shift
 
1658
#define yy_shift_ofst           kml_yy_shift_ofst
 
1659
#define yy_start                kml_yy_start
 
1660
#define yy_state_type           kml_yy_state_type
 
1661
#define yy_syntax_error         kml_yy_syntax_error
 
1662
#define yy_trans_info           kml_yy_trans_info
 
1663
#define yy_try_NUL_trans        kml_yy_try_NUL_trans
 
1664
#define yyParser                kml_yyParser
 
1665
#define yyStackEntry            kml_yyStackEntry
 
1666
#define yyStackOverflow         kml_yyStackOverflow
 
1667
#define yyRuleInfo              kml_yyRuleInfo
 
1668
#define yyunput                 kml_yyunput
 
1669
#define yyzerominor             kml_yyzerominor
 
1670
#define yyTraceFILE             kml_yyTraceFILE
 
1671
#define yyTracePrompt           kml_yyTracePrompt
 
1672
#define yyTokenName             kml_yyTokenName
 
1673
#define yyRuleName              kml_yyRuleName
 
1674
#define ParseTrace              kml_ParseTrace
 
1675
 
 
1676
 
 
1677
/*
 
1678
 KML_LEMON_H_START - LEMON generated header starts here 
 
1679
*/
 
1680
#define KML_NEWLINE                     1
 
1681
#define KML_END                         2
 
1682
#define KML_CLOSE                       3
 
1683
#define KML_OPEN                        4
 
1684
#define KML_KEYWORD                     5
 
1685
#define KML_EQ                          6
 
1686
#define KML_VALUE                       7
 
1687
#define KML_COORD                       8
 
1688
/*
 
1689
 KML_LEMON_H_END - LEMON generated header ends here 
 
1690
*/
 
1691
 
 
1692
 
 
1693
typedef union
 
1694
{
 
1695
    char *pval;
 
1696
    struct symtab *symp;
 
1697
} kml_yystype;
 
1698
#define YYSTYPE kml_yystype
 
1699
 
 
1700
 
 
1701
/* extern YYSTYPE yylval; */
 
1702
YYSTYPE KmlLval;
 
1703
 
 
1704
 
 
1705
 
 
1706
/*
 
1707
 KML_LEMON_START - LEMON generated code starts here 
 
1708
*/
 
1709
 
 
1710
/* Driver template for the LEMON parser generator.
 
1711
** The author disclaims copyright to this source code.
 
1712
*/
 
1713
/* First off, code is included that follows the "include" declaration
 
1714
** in the input grammar file. */
 
1715
#include <stdio.h>
 
1716
 
 
1717
/* Next is all token values, in a form suitable for use by makeheaders.
 
1718
** This section will be null unless lemon is run with the -m switch.
 
1719
*/
 
1720
/* 
 
1721
** These constants (all generated automatically by the parser generator)
 
1722
** specify the various kinds of tokens (terminals) that the parser
 
1723
** understands. 
 
1724
**
 
1725
** Each symbol here is a terminal symbol in the grammar.
 
1726
*/
 
1727
/* Make sure the INTERFACE macro is defined.
 
1728
*/
 
1729
#ifndef INTERFACE
 
1730
# define INTERFACE 1
 
1731
#endif
 
1732
/* The next thing included is series of defines which control
 
1733
** various aspects of the generated parser.
 
1734
**    YYCODETYPE         is the data type used for storing terminal
 
1735
**                       and nonterminal numbers.  "unsigned char" is
 
1736
**                       used if there are fewer than 250 terminals
 
1737
**                       and nonterminals.  "int" is used otherwise.
 
1738
**    YYNOCODE           is a number of type YYCODETYPE which corresponds
 
1739
**                       to no legal terminal or nonterminal number.  This
 
1740
**                       number is used to fill in empty slots of the hash 
 
1741
**                       table.
 
1742
**    YYFALLBACK         If defined, this indicates that one or more tokens
 
1743
**                       have fall-back values which should be used if the
 
1744
**                       original value of the token will not parse.
 
1745
**    YYACTIONTYPE       is the data type used for storing terminal
 
1746
**                       and nonterminal numbers.  "unsigned char" is
 
1747
**                       used if there are fewer than 250 rules and
 
1748
**                       states combined.  "int" is used otherwise.
 
1749
**    ParseTOKENTYPE     is the data type used for minor tokens given 
 
1750
**                       directly to the parser from the tokenizer.
 
1751
**    YYMINORTYPE        is the data type used for all minor tokens.
 
1752
**                       This is typically a union of many types, one of
 
1753
**                       which is ParseTOKENTYPE.  The entry in the union
 
1754
**                       for base tokens is called "yy0".
 
1755
**    YYSTACKDEPTH       is the maximum depth of the parser's stack.  If
 
1756
**                       zero the stack is dynamically sized using realloc()
 
1757
**    ParseARG_SDECL     A static variable declaration for the %extra_argument
 
1758
**    ParseARG_PDECL     A parameter declaration for the %extra_argument
 
1759
**    ParseARG_STORE     Code to store %extra_argument into yypParser
 
1760
**    ParseARG_FETCH     Code to extract %extra_argument from yypParser
 
1761
**    YYNSTATE           the combined number of states.
 
1762
**    YYNRULE            the number of rules in the grammar
 
1763
**    YYERRORSYMBOL      is the code number of the error symbol.  If not
 
1764
**                       defined, then do no error processing.
 
1765
*/
 
1766
#define YYCODETYPE unsigned char
 
1767
#define YYNOCODE 28
 
1768
#define YYACTIONTYPE unsigned char
 
1769
#define ParseTOKENTYPE void *
 
1770
typedef union {
 
1771
  int yyinit;
 
1772
  ParseTOKENTYPE yy0;
 
1773
} YYMINORTYPE;
 
1774
#ifndef YYSTACKDEPTH
 
1775
#define YYSTACKDEPTH 1000000
 
1776
#endif
 
1777
#define ParseARG_SDECL  kmlNodePtr *result ;
 
1778
#define ParseARG_PDECL , kmlNodePtr *result 
 
1779
#define ParseARG_FETCH  kmlNodePtr *result  = yypParser->result 
 
1780
#define ParseARG_STORE yypParser->result  = result 
 
1781
#define YYNSTATE 49
 
1782
#define YYNRULE 34
 
1783
#define YY_NO_ACTION      (YYNSTATE+YYNRULE+2)
 
1784
#define YY_ACCEPT_ACTION  (YYNSTATE+YYNRULE+1)
 
1785
#define YY_ERROR_ACTION   (YYNSTATE+YYNRULE)
 
1786
 
 
1787
/* The yyzerominor constant is used to initialize instances of
 
1788
** YYMINORTYPE objects to zero. */
 
1789
static const YYMINORTYPE yyzerominor = { 0 };
 
1790
 
 
1791
/* Define the yytestcase() macro to be a no-op if is not already defined
 
1792
** otherwise.
 
1793
**
 
1794
** Applications can choose to define yytestcase() in the %include section
 
1795
** to a macro that can assist in verifying code coverage.  For production
 
1796
** code the yytestcase() macro should be turned off.  But it is useful
 
1797
** for testing.
 
1798
*/
 
1799
#ifndef yytestcase
 
1800
# define yytestcase(X)
 
1801
#endif
 
1802
 
 
1803
 
 
1804
/* Next are the tables used to determine what action to take based on the
 
1805
** current state and lookahead token.  These tables are used to implement
 
1806
** functions that take a state number and lookahead value and return an
 
1807
** action integer.  
 
1808
**
 
1809
** Suppose the action integer is N.  Then the action is determined as
 
1810
** follows
 
1811
**
 
1812
**   0 <= N < YYNSTATE                  Shift N.  That is, push the lookahead
 
1813
**                                      token onto the stack and goto state N.
 
1814
**
 
1815
**   YYNSTATE <= N < YYNSTATE+YYNRULE   Reduce by rule N-YYNSTATE.
 
1816
**
 
1817
**   N == YYNSTATE+YYNRULE              A syntax error has occurred.
 
1818
**
 
1819
**   N == YYNSTATE+YYNRULE+1            The parser accepts its input.
 
1820
**
 
1821
**   N == YYNSTATE+YYNRULE+2            No such action.  Denotes unused
 
1822
**                                      slots in the yy_action[] table.
 
1823
**
 
1824
** The action table is constructed as a single large table named yy_action[].
 
1825
** Given state S and lookahead X, the action is computed as
 
1826
**
 
1827
**      yy_action[ yy_shift_ofst[S] + X ]
 
1828
**
 
1829
** If the index value yy_shift_ofst[S]+X is out of range or if the value
 
1830
** yy_lookahead[yy_shift_ofst[S]+X] is not equal to X or if yy_shift_ofst[S]
 
1831
** is equal to YY_SHIFT_USE_DFLT, it means that the action is not in the table
 
1832
** and that yy_default[S] should be used instead.  
 
1833
**
 
1834
** The formula above is for computing the action when the lookahead is
 
1835
** a terminal symbol.  If the lookahead is a non-terminal (as occurs after
 
1836
** a reduce action) then the yy_reduce_ofst[] array is used in place of
 
1837
** the yy_shift_ofst[] array and YY_REDUCE_USE_DFLT is used in place of
 
1838
** YY_SHIFT_USE_DFLT.
 
1839
**
 
1840
** The following are the tables generated in this section:
 
1841
**
 
1842
**  yy_action[]        A single table containing all actions.
 
1843
**  yy_lookahead[]     A table containing the lookahead for each entry in
 
1844
**                     yy_action.  Used to detect hash collisions.
 
1845
**  yy_shift_ofst[]    For each state, the offset into yy_action for
 
1846
**                     shifting terminals.
 
1847
**  yy_reduce_ofst[]   For each state, the offset into yy_action for
 
1848
**                     shifting non-terminals after a reduce.
 
1849
**  yy_default[]       Default action for each state.
 
1850
*/
 
1851
static const YYACTIONTYPE yy_action[] = {
 
1852
 /*     0 */    20,   28,   29,    4,   48,    5,    3,    3,    5,    5,
 
1853
 /*    10 */    42,   84,    1,   42,   42,   47,   46,    2,   10,    5,
 
1854
 /*    20 */    21,   12,   32,   23,   42,   38,   22,    6,   49,   23,
 
1855
 /*    30 */    13,   19,   14,   15,   35,    8,    8,   10,   25,   11,
 
1856
 /*    40 */    18,   34,   33,   45,   37,   16,   40,   17,   41,   14,
 
1857
 /*    50 */     9,   23,   43,    7,   45,   27,   30,   26,   31,   36,
 
1858
 /*    60 */    39,   44,   24,
 
1859
};
 
1860
static const YYCODETYPE yy_lookahead[] = {
 
1861
 /*     0 */    12,   13,   14,   15,   16,   17,   15,   15,   17,   17,
 
1862
 /*    10 */    22,   10,   11,   22,   22,   24,   24,   15,   18,   17,
 
1863
 /*    20 */     2,    3,    8,    5,   22,   25,    2,    3,    0,    5,
 
1864
 /*    30 */    18,   19,    4,   20,   21,   20,   20,   18,    2,    3,
 
1865
 /*    40 */     2,   26,   26,    5,   25,   20,   21,   20,   21,    4,
 
1866
 /*    50 */    18,    5,   23,   20,    5,    1,    3,   23,    3,    7,
 
1867
 /*    60 */     3,    3,    6,
 
1868
};
 
1869
#define YY_SHIFT_USE_DFLT (-1)
 
1870
#define YY_SHIFT_MAX 26
 
1871
static const signed char yy_shift_ofst[] = {
 
1872
 /*     0 */    -1,   28,   45,   45,   45,   18,   14,   14,   14,   46,
 
1873
 /*    10 */    46,   14,   14,   24,   38,   14,   14,   14,   49,   36,
 
1874
 /*    20 */    54,   53,   55,   56,   52,   57,   58,
 
1875
};
 
1876
#define YY_REDUCE_USE_DFLT (-13)
 
1877
#define YY_REDUCE_MAX 18
 
1878
static const signed char yy_reduce_ofst[] = {
 
1879
 /*     0 */     1,  -12,   -9,   -8,    2,   12,   13,   15,   16,    0,
 
1880
 /*    10 */    19,   25,   27,   32,   29,   33,   33,   33,   34,
 
1881
};
 
1882
static const YYACTIONTYPE yy_default[] = {
 
1883
 /*     0 */    50,   83,   72,   72,   54,   83,   60,   80,   80,   76,
 
1884
 /*    10 */    76,   61,   59,   83,   83,   64,   66,   62,   83,   83,
 
1885
 /*    20 */    83,   83,   83,   83,   83,   83,   83,   51,   52,   53,
 
1886
 /*    30 */    56,   57,   79,   81,   82,   65,   75,   77,   78,   58,
 
1887
 /*    40 */    67,   63,   68,   69,   70,   71,   73,   74,   55,
 
1888
};
 
1889
#define YY_SZ_ACTTAB (int)(sizeof(yy_action)/sizeof(yy_action[0]))
 
1890
 
 
1891
/* The next table maps tokens into fallback tokens.  If a construct
 
1892
** like the following:
 
1893
** 
 
1894
**      %fallback ID X Y Z.
 
1895
**
 
1896
** appears in the grammar, then ID becomes a fallback token for X, Y,
 
1897
** and Z.  Whenever one of the tokens X, Y, or Z is input to the parser
 
1898
** but it does not parse, the type of the token is changed to ID and
 
1899
** the parse is retried before an error is thrown.
 
1900
*/
 
1901
#ifdef YYFALLBACK
 
1902
static const YYCODETYPE yyFallback[] = {
 
1903
};
 
1904
#endif /* YYFALLBACK */
 
1905
 
 
1906
/* The following structure represents a single element of the
 
1907
** parser's stack.  Information stored includes:
 
1908
**
 
1909
**   +  The state number for the parser at this level of the stack.
 
1910
**
 
1911
**   +  The value of the token stored at this level of the stack.
 
1912
**      (In other words, the "major" token.)
 
1913
**
 
1914
**   +  The semantic value stored at this level of the stack.  This is
 
1915
**      the information used by the action routines in the grammar.
 
1916
**      It is sometimes called the "minor" token.
 
1917
*/
 
1918
struct yyStackEntry {
 
1919
  YYACTIONTYPE stateno;  /* The state-number */
 
1920
  YYCODETYPE major;      /* The major token value.  This is the code
 
1921
                         ** number for the token at this stack level */
 
1922
  YYMINORTYPE minor;     /* The user-supplied minor token value.  This
 
1923
                         ** is the value of the token  */
 
1924
};
 
1925
typedef struct yyStackEntry yyStackEntry;
 
1926
 
 
1927
/* The state of the parser is completely contained in an instance of
 
1928
** the following structure */
 
1929
struct yyParser {
 
1930
  int yyidx;                    /* Index of top element in stack */
 
1931
#ifdef YYTRACKMAXSTACKDEPTH
 
1932
  int yyidxMax;                 /* Maximum value of yyidx */
 
1933
#endif
 
1934
  int yyerrcnt;                 /* Shifts left before out of the error */
 
1935
  ParseARG_SDECL                /* A place to hold %extra_argument */
 
1936
#if YYSTACKDEPTH<=0
 
1937
  int yystksz;                  /* Current side of the stack */
 
1938
  yyStackEntry *yystack;        /* The parser's stack */
 
1939
#else
 
1940
  yyStackEntry yystack[YYSTACKDEPTH];  /* The parser's stack */
 
1941
#endif
 
1942
};
 
1943
typedef struct yyParser yyParser;
 
1944
 
 
1945
#ifndef NDEBUG
 
1946
#include <stdio.h>
 
1947
static FILE *yyTraceFILE = 0;
 
1948
static char *yyTracePrompt = 0;
 
1949
#endif /* NDEBUG */
 
1950
 
 
1951
#ifndef NDEBUG
 
1952
/* 
 
1953
** Turn parser tracing on by giving a stream to which to write the trace
 
1954
** and a prompt to preface each trace message.  Tracing is turned off
 
1955
** by making either argument NULL 
 
1956
**
 
1957
** Inputs:
 
1958
** <ul>
 
1959
** <li> A FILE* to which trace output should be written.
 
1960
**      If NULL, then tracing is turned off.
 
1961
** <li> A prefix string written at the beginning of every
 
1962
**      line of trace output.  If NULL, then tracing is
 
1963
**      turned off.
 
1964
** </ul>
 
1965
**
 
1966
** Outputs:
 
1967
** None.
 
1968
*/
 
1969
void ParseTrace(FILE *TraceFILE, char *zTracePrompt){
 
1970
  yyTraceFILE = TraceFILE;
 
1971
  yyTracePrompt = zTracePrompt;
 
1972
  if( yyTraceFILE==0 ) yyTracePrompt = 0;
 
1973
  else if( yyTracePrompt==0 ) yyTraceFILE = 0;
 
1974
}
 
1975
#endif /* NDEBUG */
 
1976
 
 
1977
#ifndef NDEBUG
 
1978
/* For tracing shifts, the names of all terminals and nonterminals
 
1979
** are required.  The following table supplies these names */
 
1980
static const char *const yyTokenName[] = { 
 
1981
  "$",             "KML_NEWLINE",   "KML_END",       "KML_CLOSE",   
 
1982
  "KML_OPEN",      "KML_KEYWORD",   "KML_EQ",        "KML_VALUE",   
 
1983
  "KML_COORD",     "error",         "main",          "in",          
 
1984
  "state",         "program",       "kml_tree",      "node",        
 
1985
  "node_chain",    "open_tag",      "attr",          "attributes",  
 
1986
  "coord",         "coord_chain",   "close_tag",     "keyword",     
 
1987
  "extra_nodes",   "extra_attr",    "extra_coord", 
 
1988
};
 
1989
#endif /* NDEBUG */
 
1990
 
 
1991
#ifndef NDEBUG
 
1992
/* For tracing reduce actions, the names of all rules are required.
 
1993
*/
 
1994
static const char *const yyRuleName[] = {
 
1995
 /*   0 */ "main ::= in",
 
1996
 /*   1 */ "in ::=",
 
1997
 /*   2 */ "in ::= in state KML_NEWLINE",
 
1998
 /*   3 */ "state ::= program",
 
1999
 /*   4 */ "program ::= kml_tree",
 
2000
 /*   5 */ "kml_tree ::= node",
 
2001
 /*   6 */ "kml_tree ::= node_chain",
 
2002
 /*   7 */ "node ::= open_tag KML_END KML_CLOSE",
 
2003
 /*   8 */ "node ::= open_tag attr KML_END KML_CLOSE",
 
2004
 /*   9 */ "node ::= open_tag attributes KML_END KML_CLOSE",
 
2005
 /*  10 */ "node ::= open_tag KML_CLOSE",
 
2006
 /*  11 */ "node ::= open_tag attr KML_CLOSE",
 
2007
 /*  12 */ "node ::= open_tag attributes KML_CLOSE",
 
2008
 /*  13 */ "node ::= open_tag KML_CLOSE coord",
 
2009
 /*  14 */ "node ::= open_tag KML_CLOSE coord_chain",
 
2010
 /*  15 */ "node ::= open_tag attr KML_CLOSE coord",
 
2011
 /*  16 */ "node ::= open_tag attr KML_CLOSE coord_chain",
 
2012
 /*  17 */ "node ::= open_tag attributes KML_CLOSE coord",
 
2013
 /*  18 */ "node ::= open_tag attributes KML_CLOSE coord_chain",
 
2014
 /*  19 */ "node ::= close_tag",
 
2015
 /*  20 */ "open_tag ::= KML_OPEN keyword",
 
2016
 /*  21 */ "close_tag ::= KML_OPEN KML_END keyword KML_CLOSE",
 
2017
 /*  22 */ "keyword ::= KML_KEYWORD",
 
2018
 /*  23 */ "extra_nodes ::=",
 
2019
 /*  24 */ "extra_nodes ::= node extra_nodes",
 
2020
 /*  25 */ "node_chain ::= node node extra_nodes",
 
2021
 /*  26 */ "attr ::= KML_KEYWORD KML_EQ KML_VALUE",
 
2022
 /*  27 */ "extra_attr ::=",
 
2023
 /*  28 */ "extra_attr ::= attr extra_attr",
 
2024
 /*  29 */ "attributes ::= attr attr extra_attr",
 
2025
 /*  30 */ "coord ::= KML_COORD",
 
2026
 /*  31 */ "extra_coord ::=",
 
2027
 /*  32 */ "extra_coord ::= coord extra_coord",
 
2028
 /*  33 */ "coord_chain ::= coord coord extra_coord",
 
2029
};
 
2030
#endif /* NDEBUG */
 
2031
 
 
2032
 
 
2033
#if YYSTACKDEPTH<=0
 
2034
/*
 
2035
** Try to increase the size of the parser stack.
 
2036
*/
 
2037
static void yyGrowStack(yyParser *p){
 
2038
  int newSize;
 
2039
  yyStackEntry *pNew;
 
2040
 
 
2041
  newSize = p->yystksz*2 + 100;
 
2042
  pNew = realloc(p->yystack, newSize*sizeof(pNew[0]));
 
2043
  if( pNew ){
 
2044
    p->yystack = pNew;
 
2045
    p->yystksz = newSize;
 
2046
#ifndef NDEBUG
 
2047
    if( yyTraceFILE ){
 
2048
      fprintf(yyTraceFILE,"%sStack grows to %d entries!\n",
 
2049
              yyTracePrompt, p->yystksz);
 
2050
    }
 
2051
#endif
 
2052
  }
 
2053
}
 
2054
#endif
 
2055
 
 
2056
/* 
 
2057
** This function allocates a new parser.
 
2058
** The only argument is a pointer to a function which works like
 
2059
** malloc.
 
2060
**
 
2061
** Inputs:
 
2062
** A pointer to the function used to allocate memory.
 
2063
**
 
2064
** Outputs:
 
2065
** A pointer to a parser.  This pointer is used in subsequent calls
 
2066
** to Parse and ParseFree.
 
2067
*/
 
2068
void *ParseAlloc(void *(*mallocProc)(size_t)){
 
2069
  yyParser *pParser;
 
2070
  pParser = (yyParser*)(*mallocProc)( (size_t)sizeof(yyParser) );
 
2071
  if( pParser ){
 
2072
    pParser->yyidx = -1;
 
2073
#ifdef YYTRACKMAXSTACKDEPTH
 
2074
    pParser->yyidxMax = 0;
 
2075
#endif
 
2076
#if YYSTACKDEPTH<=0
 
2077
    pParser->yystack = NULL;
 
2078
    pParser->yystksz = 0;
 
2079
    yyGrowStack(pParser);
 
2080
#endif
 
2081
  }
 
2082
  return pParser;
 
2083
}
 
2084
 
 
2085
/* The following function deletes the value associated with a
 
2086
** symbol.  The symbol can be either a terminal or nonterminal.
 
2087
** "yymajor" is the symbol code, and "yypminor" is a pointer to
 
2088
** the value.
 
2089
*/
 
2090
static void yy_destructor(
 
2091
  yyParser *yypParser,    /* The parser */
 
2092
  YYCODETYPE yymajor,     /* Type code for object to destroy */
 
2093
  YYMINORTYPE *yypminor   /* The object to be destroyed */
 
2094
){
 
2095
  ParseARG_FETCH;
 
2096
  switch( yymajor ){
 
2097
    /* Here is inserted the actions which take place when a
 
2098
    ** terminal or non-terminal is destroyed.  This can happen
 
2099
    ** when the symbol is popped from the stack during a
 
2100
    ** reduce or during error processing or when a parser is 
 
2101
    ** being destroyed before it is finished parsing.
 
2102
    **
 
2103
    ** Note: during a reduce, the only symbols destroyed are those
 
2104
    ** which appear on the RHS of the rule, but which are not used
 
2105
    ** inside the C code.
 
2106
    */
 
2107
    default:  break;   /* If no destructor action specified: do nothing */
 
2108
  }
 
2109
}
 
2110
 
 
2111
/*
 
2112
** Pop the parser's stack once.
 
2113
**
 
2114
** If there is a destructor routine associated with the token which
 
2115
** is popped from the stack, then call it.
 
2116
**
 
2117
** Return the major token number for the symbol popped.
 
2118
*/
 
2119
static int yy_pop_parser_stack(yyParser *pParser){
 
2120
  YYCODETYPE yymajor;
 
2121
  yyStackEntry *yytos = &pParser->yystack[pParser->yyidx];
 
2122
 
 
2123
  if( pParser->yyidx<0 ) return 0;
 
2124
#ifndef NDEBUG
 
2125
  if( yyTraceFILE && pParser->yyidx>=0 ){
 
2126
    fprintf(yyTraceFILE,"%sPopping %s\n",
 
2127
      yyTracePrompt,
 
2128
      yyTokenName[yytos->major]);
 
2129
  }
 
2130
#endif
 
2131
  yymajor = yytos->major;
 
2132
  yy_destructor(pParser, yymajor, &yytos->minor);
 
2133
  pParser->yyidx--;
 
2134
  return yymajor;
 
2135
}
 
2136
 
 
2137
/* 
 
2138
** Deallocate and destroy a parser.  Destructors are all called for
 
2139
** all stack elements before shutting the parser down.
 
2140
**
 
2141
** Inputs:
 
2142
** <ul>
 
2143
** <li>  A pointer to the parser.  This should be a pointer
 
2144
**       obtained from ParseAlloc.
 
2145
** <li>  A pointer to a function used to reclaim memory obtained
 
2146
**       from malloc.
 
2147
** </ul>
 
2148
*/
 
2149
void ParseFree(
 
2150
  void *p,                    /* The parser to be deleted */
 
2151
  void (*freeProc)(void*)     /* Function used to reclaim memory */
 
2152
){
 
2153
  yyParser *pParser = (yyParser*)p;
 
2154
  if( pParser==0 ) return;
 
2155
  while( pParser->yyidx>=0 ) yy_pop_parser_stack(pParser);
 
2156
#if YYSTACKDEPTH<=0
 
2157
  free(pParser->yystack);
 
2158
#endif
 
2159
  (*freeProc)((void*)pParser);
 
2160
}
 
2161
 
 
2162
/*
 
2163
** Return the peak depth of the stack for a parser.
 
2164
*/
 
2165
#ifdef YYTRACKMAXSTACKDEPTH
 
2166
int ParseStackPeak(void *p){
 
2167
  yyParser *pParser = (yyParser*)p;
 
2168
  return pParser->yyidxMax;
 
2169
}
 
2170
#endif
 
2171
 
 
2172
/*
 
2173
** Find the appropriate action for a parser given the terminal
 
2174
** look-ahead token iLookAhead.
 
2175
**
 
2176
** If the look-ahead token is YYNOCODE, then check to see if the action is
 
2177
** independent of the look-ahead.  If it is, return the action, otherwise
 
2178
** return YY_NO_ACTION.
 
2179
*/
 
2180
static int yy_find_shift_action(
 
2181
  yyParser *pParser,        /* The parser */
 
2182
  YYCODETYPE iLookAhead     /* The look-ahead token */
 
2183
){
 
2184
  int i;
 
2185
  int stateno = pParser->yystack[pParser->yyidx].stateno;
 
2186
 
 
2187
  if( stateno>YY_SHIFT_MAX || (i = yy_shift_ofst[stateno])==YY_SHIFT_USE_DFLT ){
 
2188
    return yy_default[stateno];
 
2189
  }
 
2190
  assert( iLookAhead!=YYNOCODE );
 
2191
  i += iLookAhead;
 
2192
  if( i<0 || i>=YY_SZ_ACTTAB || yy_lookahead[i]!=iLookAhead ){
 
2193
    if( iLookAhead>0 ){
 
2194
#ifdef YYFALLBACK
 
2195
      YYCODETYPE iFallback;            /* Fallback token */
 
2196
      if( iLookAhead<sizeof(yyFallback)/sizeof(yyFallback[0])
 
2197
             && (iFallback = yyFallback[iLookAhead])!=0 ){
 
2198
#ifndef NDEBUG
 
2199
        if( yyTraceFILE ){
 
2200
          fprintf(yyTraceFILE, "%sFALLBACK %s => %s\n",
 
2201
             yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[iFallback]);
 
2202
        }
 
2203
#endif
 
2204
        return yy_find_shift_action(pParser, iFallback);
 
2205
      }
 
2206
#endif
 
2207
#ifdef YYWILDCARD
 
2208
      {
 
2209
        int j = i - iLookAhead + YYWILDCARD;
 
2210
        if( j>=0 && j<YY_SZ_ACTTAB && yy_lookahead[j]==YYWILDCARD ){
 
2211
#ifndef NDEBUG
 
2212
          if( yyTraceFILE ){
 
2213
            fprintf(yyTraceFILE, "%sWILDCARD %s => %s\n",
 
2214
               yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[YYWILDCARD]);
 
2215
          }
 
2216
#endif /* NDEBUG */
 
2217
          return yy_action[j];
 
2218
        }
 
2219
      }
 
2220
#endif /* YYWILDCARD */
 
2221
    }
 
2222
    return yy_default[stateno];
 
2223
  }else{
 
2224
    return yy_action[i];
 
2225
  }
 
2226
}
 
2227
 
 
2228
/*
 
2229
** Find the appropriate action for a parser given the non-terminal
 
2230
** look-ahead token iLookAhead.
 
2231
**
 
2232
** If the look-ahead token is YYNOCODE, then check to see if the action is
 
2233
** independent of the look-ahead.  If it is, return the action, otherwise
 
2234
** return YY_NO_ACTION.
 
2235
*/
 
2236
static int yy_find_reduce_action(
 
2237
  int stateno,              /* Current state number */
 
2238
  YYCODETYPE iLookAhead     /* The look-ahead token */
 
2239
){
 
2240
  int i;
 
2241
#ifdef YYERRORSYMBOL
 
2242
  if( stateno>YY_REDUCE_MAX ){
 
2243
    return yy_default[stateno];
 
2244
  }
 
2245
#else
 
2246
  assert( stateno<=YY_REDUCE_MAX );
 
2247
#endif
 
2248
  i = yy_reduce_ofst[stateno];
 
2249
  assert( i!=YY_REDUCE_USE_DFLT );
 
2250
  assert( iLookAhead!=YYNOCODE );
 
2251
  i += iLookAhead;
 
2252
#ifdef YYERRORSYMBOL
 
2253
  if( i<0 || i>=YY_SZ_ACTTAB || yy_lookahead[i]!=iLookAhead ){
 
2254
    return yy_default[stateno];
 
2255
  }
 
2256
#else
 
2257
  assert( i>=0 && i<YY_SZ_ACTTAB );
 
2258
  assert( yy_lookahead[i]==iLookAhead );
 
2259
#endif
 
2260
  return yy_action[i];
 
2261
}
 
2262
 
 
2263
/*
 
2264
** The following routine is called if the stack overflows.
 
2265
*/
 
2266
static void yyStackOverflow(yyParser *yypParser, YYMINORTYPE *yypMinor){
 
2267
   ParseARG_FETCH;
 
2268
   yypParser->yyidx--;
 
2269
#ifndef NDEBUG
 
2270
   if( yyTraceFILE ){
 
2271
     fprintf(yyTraceFILE,"%sStack Overflow!\n",yyTracePrompt);
 
2272
   }
 
2273
#endif
 
2274
   while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser);
 
2275
   /* Here code is inserted which will execute if the parser
 
2276
   ** stack every overflows */
 
2277
 
 
2278
     fprintf(stderr,"Giving up.  Parser stack overflow\n");
 
2279
   ParseARG_STORE; /* Suppress warning about unused %extra_argument var */
 
2280
}
 
2281
 
 
2282
/*
 
2283
** Perform a shift action.
 
2284
*/
 
2285
static void yy_shift(
 
2286
  yyParser *yypParser,          /* The parser to be shifted */
 
2287
  int yyNewState,               /* The new state to shift in */
 
2288
  int yyMajor,                  /* The major token to shift in */
 
2289
  YYMINORTYPE *yypMinor         /* Pointer to the minor token to shift in */
 
2290
){
 
2291
  yyStackEntry *yytos;
 
2292
  yypParser->yyidx++;
 
2293
#ifdef YYTRACKMAXSTACKDEPTH
 
2294
  if( yypParser->yyidx>yypParser->yyidxMax ){
 
2295
    yypParser->yyidxMax = yypParser->yyidx;
 
2296
  }
 
2297
#endif
 
2298
#if YYSTACKDEPTH>0 
 
2299
  if( yypParser->yyidx>=YYSTACKDEPTH ){
 
2300
    yyStackOverflow(yypParser, yypMinor);
 
2301
    return;
 
2302
  }
 
2303
#else
 
2304
  if( yypParser->yyidx>=yypParser->yystksz ){
 
2305
    yyGrowStack(yypParser);
 
2306
    if( yypParser->yyidx>=yypParser->yystksz ){
 
2307
      yyStackOverflow(yypParser, yypMinor);
 
2308
      return;
 
2309
    }
 
2310
  }
 
2311
#endif
 
2312
  yytos = &yypParser->yystack[yypParser->yyidx];
 
2313
  yytos->stateno = (YYACTIONTYPE)yyNewState;
 
2314
  yytos->major = (YYCODETYPE)yyMajor;
 
2315
  yytos->minor = *yypMinor;
 
2316
#ifndef NDEBUG
 
2317
  if( yyTraceFILE && yypParser->yyidx>0 ){
 
2318
    int i;
 
2319
    fprintf(yyTraceFILE,"%sShift %d\n",yyTracePrompt,yyNewState);
 
2320
    fprintf(yyTraceFILE,"%sStack:",yyTracePrompt);
 
2321
    for(i=1; i<=yypParser->yyidx; i++)
 
2322
      fprintf(yyTraceFILE," %s",yyTokenName[yypParser->yystack[i].major]);
 
2323
    fprintf(yyTraceFILE,"\n");
 
2324
  }
 
2325
#endif
 
2326
}
 
2327
 
 
2328
/* The following table contains information about every rule that
 
2329
** is used during the reduce.
 
2330
*/
 
2331
static const struct {
 
2332
  YYCODETYPE lhs;         /* Symbol on the left-hand side of the rule */
 
2333
  unsigned char nrhs;     /* Number of right-hand side symbols in the rule */
 
2334
} yyRuleInfo[] = {
 
2335
  { 10, 1 },
 
2336
  { 11, 0 },
 
2337
  { 11, 3 },
 
2338
  { 12, 1 },
 
2339
  { 13, 1 },
 
2340
  { 14, 1 },
 
2341
  { 14, 1 },
 
2342
  { 15, 3 },
 
2343
  { 15, 4 },
 
2344
  { 15, 4 },
 
2345
  { 15, 2 },
 
2346
  { 15, 3 },
 
2347
  { 15, 3 },
 
2348
  { 15, 3 },
 
2349
  { 15, 3 },
 
2350
  { 15, 4 },
 
2351
  { 15, 4 },
 
2352
  { 15, 4 },
 
2353
  { 15, 4 },
 
2354
  { 15, 1 },
 
2355
  { 17, 2 },
 
2356
  { 22, 4 },
 
2357
  { 23, 1 },
 
2358
  { 24, 0 },
 
2359
  { 24, 2 },
 
2360
  { 16, 3 },
 
2361
  { 18, 3 },
 
2362
  { 25, 0 },
 
2363
  { 25, 2 },
 
2364
  { 19, 3 },
 
2365
  { 20, 1 },
 
2366
  { 26, 0 },
 
2367
  { 26, 2 },
 
2368
  { 21, 3 },
 
2369
};
 
2370
 
 
2371
static void yy_accept(yyParser*);  /* Forward Declaration */
 
2372
 
 
2373
/*
 
2374
** Perform a reduce action and the shift that must immediately
 
2375
** follow the reduce.
 
2376
*/
 
2377
static void yy_reduce(
 
2378
  yyParser *yypParser,         /* The parser */
 
2379
  int yyruleno                 /* Number of the rule by which to reduce */
 
2380
){
 
2381
  int yygoto;                     /* The next state */
 
2382
  int yyact;                      /* The next action */
 
2383
  YYMINORTYPE yygotominor;        /* The LHS of the rule reduced */
 
2384
  yyStackEntry *yymsp;            /* The top of the parser's stack */
 
2385
  int yysize;                     /* Amount to pop the stack */
 
2386
  ParseARG_FETCH;
 
2387
  yymsp = &yypParser->yystack[yypParser->yyidx];
 
2388
#ifndef NDEBUG
 
2389
  if( yyTraceFILE && yyruleno>=0 
 
2390
        && yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) ){
 
2391
    fprintf(yyTraceFILE, "%sReduce [%s].\n", yyTracePrompt,
 
2392
      yyRuleName[yyruleno]);
 
2393
  }
 
2394
#endif /* NDEBUG */
 
2395
 
 
2396
  /* Silence complaints from purify about yygotominor being uninitialized
 
2397
  ** in some cases when it is copied into the stack after the following
 
2398
  ** switch.  yygotominor is uninitialized when a rule reduces that does
 
2399
  ** not set the value of its left-hand side nonterminal.  Leaving the
 
2400
  ** value of the nonterminal uninitialized is utterly harmless as long
 
2401
  ** as the value is never used.  So really the only thing this code
 
2402
  ** accomplishes is to quieten purify.  
 
2403
  **
 
2404
  ** 2007-01-16:  The wireshark project (www.wireshark.org) reports that
 
2405
  ** without this code, their parser segfaults.  I'm not sure what there
 
2406
  ** parser is doing to make this happen.  This is the second bug report
 
2407
  ** from wireshark this week.  Clearly they are stressing Lemon in ways
 
2408
  ** that it has not been previously stressed...  (SQLite ticket #2172)
 
2409
  */
 
2410
  /*memset(&yygotominor, 0, sizeof(yygotominor));*/
 
2411
  yygotominor = yyzerominor;
 
2412
 
 
2413
 
 
2414
  switch( yyruleno ){
 
2415
  /* Beginning here are the reduction cases.  A typical example
 
2416
  ** follows:
 
2417
  **   case 0:
 
2418
  **  #line <lineno> <grammarfile>
 
2419
  **     { ... }           // User supplied code
 
2420
  **  #line <lineno> <thisfile>
 
2421
  **     break;
 
2422
  */
 
2423
      case 5: /* kml_tree ::= node */
 
2424
      case 6: /* kml_tree ::= node_chain */ yytestcase(yyruleno==6);
 
2425
{ *result = yymsp[0].minor.yy0; }
 
2426
        break;
 
2427
      case 7: /* node ::= open_tag KML_END KML_CLOSE */
 
2428
{ yygotominor.yy0 = kml_createSelfClosedNode((void *)yymsp[-2].minor.yy0, NULL); }
 
2429
        break;
 
2430
      case 8: /* node ::= open_tag attr KML_END KML_CLOSE */
 
2431
      case 9: /* node ::= open_tag attributes KML_END KML_CLOSE */ yytestcase(yyruleno==9);
 
2432
{ yygotominor.yy0 = kml_createSelfClosedNode((void *)yymsp[-3].minor.yy0, (void *)yymsp[-2].minor.yy0); }
 
2433
        break;
 
2434
      case 10: /* node ::= open_tag KML_CLOSE */
 
2435
{ yygotominor.yy0 = kml_createNode((void *)yymsp[-1].minor.yy0, NULL, NULL); }
 
2436
        break;
 
2437
      case 11: /* node ::= open_tag attr KML_CLOSE */
 
2438
      case 12: /* node ::= open_tag attributes KML_CLOSE */ yytestcase(yyruleno==12);
 
2439
{ yygotominor.yy0 = kml_createNode((void *)yymsp[-2].minor.yy0, (void *)yymsp[-1].minor.yy0, NULL); }
 
2440
        break;
 
2441
      case 13: /* node ::= open_tag KML_CLOSE coord */
 
2442
      case 14: /* node ::= open_tag KML_CLOSE coord_chain */ yytestcase(yyruleno==14);
 
2443
{ yygotominor.yy0 = kml_createNode((void *)yymsp[-2].minor.yy0, NULL, (void *)yymsp[0].minor.yy0); }
 
2444
        break;
 
2445
      case 15: /* node ::= open_tag attr KML_CLOSE coord */
 
2446
      case 16: /* node ::= open_tag attr KML_CLOSE coord_chain */ yytestcase(yyruleno==16);
 
2447
      case 17: /* node ::= open_tag attributes KML_CLOSE coord */ yytestcase(yyruleno==17);
 
2448
      case 18: /* node ::= open_tag attributes KML_CLOSE coord_chain */ yytestcase(yyruleno==18);
 
2449
{ yygotominor.yy0 = kml_createNode((void *)yymsp[-3].minor.yy0, (void *)yymsp[-2].minor.yy0, (void *)yymsp[0].minor.yy0); }
 
2450
        break;
 
2451
      case 19: /* node ::= close_tag */
 
2452
{ yygotominor.yy0 = kml_closingNode((void *)yymsp[0].minor.yy0); }
 
2453
        break;
 
2454
      case 20: /* open_tag ::= KML_OPEN keyword */
 
2455
      case 22: /* keyword ::= KML_KEYWORD */ yytestcase(yyruleno==22);
 
2456
{ yygotominor.yy0 = yymsp[0].minor.yy0; }
 
2457
        break;
 
2458
      case 21: /* close_tag ::= KML_OPEN KML_END keyword KML_CLOSE */
 
2459
{ yygotominor.yy0 = yymsp[-1].minor.yy0; }
 
2460
        break;
 
2461
      case 23: /* extra_nodes ::= */
 
2462
      case 27: /* extra_attr ::= */ yytestcase(yyruleno==27);
 
2463
      case 31: /* extra_coord ::= */ yytestcase(yyruleno==31);
 
2464
{ yygotominor.yy0 = NULL; }
 
2465
        break;
 
2466
      case 24: /* extra_nodes ::= node extra_nodes */
 
2467
{ ((kmlNodePtr)yymsp[-1].minor.yy0)->Next = (kmlNodePtr)yymsp[0].minor.yy0;  yygotominor.yy0 = yymsp[-1].minor.yy0; }
 
2468
        break;
 
2469
      case 25: /* node_chain ::= node node extra_nodes */
 
2470
 
2471
           ((kmlNodePtr)yymsp[-1].minor.yy0)->Next = (kmlNodePtr)yymsp[0].minor.yy0; 
 
2472
           ((kmlNodePtr)yymsp[-2].minor.yy0)->Next = (kmlNodePtr)yymsp[-1].minor.yy0;
 
2473
           yygotominor.yy0 = yymsp[-2].minor.yy0;
 
2474
        }
 
2475
        break;
 
2476
      case 26: /* attr ::= KML_KEYWORD KML_EQ KML_VALUE */
 
2477
{ yygotominor.yy0 = kml_attribute((void *)yymsp[-2].minor.yy0, (void *)yymsp[0].minor.yy0); }
 
2478
        break;
 
2479
      case 28: /* extra_attr ::= attr extra_attr */
 
2480
{ ((kmlAttrPtr)yymsp[-1].minor.yy0)->Next = (kmlAttrPtr)yymsp[0].minor.yy0;  yygotominor.yy0 = yymsp[-1].minor.yy0; }
 
2481
        break;
 
2482
      case 29: /* attributes ::= attr attr extra_attr */
 
2483
 
2484
           ((kmlAttrPtr)yymsp[-1].minor.yy0)->Next = (kmlAttrPtr)yymsp[0].minor.yy0; 
 
2485
           ((kmlAttrPtr)yymsp[-2].minor.yy0)->Next = (kmlAttrPtr)yymsp[-1].minor.yy0;
 
2486
           yygotominor.yy0 = yymsp[-2].minor.yy0;
 
2487
        }
 
2488
        break;
 
2489
      case 30: /* coord ::= KML_COORD */
 
2490
{ yygotominor.yy0 = kml_coord((void *)yymsp[0].minor.yy0); }
 
2491
        break;
 
2492
      case 32: /* extra_coord ::= coord extra_coord */
 
2493
{ ((kmlCoordPtr)yymsp[-1].minor.yy0)->Next = (kmlCoordPtr)yymsp[0].minor.yy0;  yygotominor.yy0 = yymsp[-1].minor.yy0; }
 
2494
        break;
 
2495
      case 33: /* coord_chain ::= coord coord extra_coord */
 
2496
 
2497
           ((kmlCoordPtr)yymsp[-1].minor.yy0)->Next = (kmlCoordPtr)yymsp[0].minor.yy0; 
 
2498
           ((kmlCoordPtr)yymsp[-2].minor.yy0)->Next = (kmlCoordPtr)yymsp[-1].minor.yy0;
 
2499
           yygotominor.yy0 = yymsp[-2].minor.yy0;
 
2500
        }
 
2501
        break;
 
2502
      default:
 
2503
      /* (0) main ::= in */ yytestcase(yyruleno==0);
 
2504
      /* (1) in ::= */ yytestcase(yyruleno==1);
 
2505
      /* (2) in ::= in state KML_NEWLINE */ yytestcase(yyruleno==2);
 
2506
      /* (3) state ::= program */ yytestcase(yyruleno==3);
 
2507
      /* (4) program ::= kml_tree */ yytestcase(yyruleno==4);
 
2508
        break;
 
2509
  };
 
2510
  yygoto = yyRuleInfo[yyruleno].lhs;
 
2511
  yysize = yyRuleInfo[yyruleno].nrhs;
 
2512
  yypParser->yyidx -= yysize;
 
2513
  yyact = yy_find_reduce_action(yymsp[-yysize].stateno,(YYCODETYPE)yygoto);
 
2514
  if( yyact < YYNSTATE ){
 
2515
#ifdef NDEBUG
 
2516
    /* If we are not debugging and the reduce action popped at least
 
2517
    ** one element off the stack, then we can push the new element back
 
2518
    ** onto the stack here, and skip the stack overflow test in yy_shift().
 
2519
    ** That gives a significant speed improvement. */
 
2520
    if( yysize ){
 
2521
      yypParser->yyidx++;
 
2522
      yymsp -= yysize-1;
 
2523
      yymsp->stateno = (YYACTIONTYPE)yyact;
 
2524
      yymsp->major = (YYCODETYPE)yygoto;
 
2525
      yymsp->minor = yygotominor;
 
2526
    }else
 
2527
#endif
 
2528
    {
 
2529
      yy_shift(yypParser,yyact,yygoto,&yygotominor);
 
2530
    }
 
2531
  }else{
 
2532
    assert( yyact == YYNSTATE + YYNRULE + 1 );
 
2533
    yy_accept(yypParser);
 
2534
  }
 
2535
}
 
2536
 
 
2537
/*
 
2538
** The following code executes when the parse fails
 
2539
*/
 
2540
#ifndef YYNOERRORRECOVERY
 
2541
static void yy_parse_failed(
 
2542
  yyParser *yypParser           /* The parser */
 
2543
){
 
2544
  ParseARG_FETCH;
 
2545
#ifndef NDEBUG
 
2546
  if( yyTraceFILE ){
 
2547
    fprintf(yyTraceFILE,"%sFail!\n",yyTracePrompt);
 
2548
  }
 
2549
#endif
 
2550
  while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser);
 
2551
  /* Here code is inserted which will be executed whenever the
 
2552
  ** parser fails */
 
2553
  ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */
 
2554
}
 
2555
#endif /* YYNOERRORRECOVERY */
 
2556
 
 
2557
/*
 
2558
** The following code executes when a syntax error first occurs.
 
2559
*/
 
2560
static void yy_syntax_error(
 
2561
  yyParser *yypParser,           /* The parser */
 
2562
  int yymajor,                   /* The major type of the error token */
 
2563
  YYMINORTYPE yyminor            /* The minor type of the error token */
 
2564
){
 
2565
  ParseARG_FETCH;
 
2566
#define TOKEN (yyminor.yy0)
 
2567
 
 
2568
/* 
 
2569
** when the LEMON parser encounters an error
 
2570
** then this global variable is set 
 
2571
*/
 
2572
        kml_parse_error = 1;
 
2573
        *result = NULL;
 
2574
  ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */
 
2575
}
 
2576
 
 
2577
/*
 
2578
** The following is executed when the parser accepts
 
2579
*/
 
2580
static void yy_accept(
 
2581
  yyParser *yypParser           /* The parser */
 
2582
){
 
2583
  ParseARG_FETCH;
 
2584
#ifndef NDEBUG
 
2585
  if( yyTraceFILE ){
 
2586
    fprintf(yyTraceFILE,"%sAccept!\n",yyTracePrompt);
 
2587
  }
 
2588
#endif
 
2589
  while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser);
 
2590
  /* Here code is inserted which will be executed whenever the
 
2591
  ** parser accepts */
 
2592
  ParseARG_STORE; /* Suppress warning about unused %extra_argument variable */
 
2593
}
 
2594
 
 
2595
/* The main parser program.
 
2596
** The first argument is a pointer to a structure obtained from
 
2597
** "ParseAlloc" which describes the current state of the parser.
 
2598
** The second argument is the major token number.  The third is
 
2599
** the minor token.  The fourth optional argument is whatever the
 
2600
** user wants (and specified in the grammar) and is available for
 
2601
** use by the action routines.
 
2602
**
 
2603
** Inputs:
 
2604
** <ul>
 
2605
** <li> A pointer to the parser (an opaque structure.)
 
2606
** <li> The major token number.
 
2607
** <li> The minor token number.
 
2608
** <li> An option argument of a grammar-specified type.
 
2609
** </ul>
 
2610
**
 
2611
** Outputs:
 
2612
** None.
 
2613
*/
 
2614
void Parse(
 
2615
  void *yyp,                   /* The parser */
 
2616
  int yymajor,                 /* The major token code number */
 
2617
  ParseTOKENTYPE yyminor       /* The value for the token */
 
2618
  ParseARG_PDECL               /* Optional %extra_argument parameter */
 
2619
){
 
2620
  YYMINORTYPE yyminorunion;
 
2621
  int yyact;            /* The parser action. */
 
2622
  int yyendofinput;     /* True if we are at the end of input */
 
2623
#ifdef YYERRORSYMBOL
 
2624
  int yyerrorhit = 0;   /* True if yymajor has invoked an error */
 
2625
#endif
 
2626
  yyParser *yypParser;  /* The parser */
 
2627
 
 
2628
  /* (re)initialize the parser, if necessary */
 
2629
  yypParser = (yyParser*)yyp;
 
2630
  if( yypParser->yyidx<0 ){
 
2631
#if YYSTACKDEPTH<=0
 
2632
    if( yypParser->yystksz <=0 ){
 
2633
      /*memset(&yyminorunion, 0, sizeof(yyminorunion));*/
 
2634
      yyminorunion = yyzerominor;
 
2635
      yyStackOverflow(yypParser, &yyminorunion);
 
2636
      return;
 
2637
    }
 
2638
#endif
 
2639
    yypParser->yyidx = 0;
 
2640
    yypParser->yyerrcnt = -1;
 
2641
    yypParser->yystack[0].stateno = 0;
 
2642
    yypParser->yystack[0].major = 0;
 
2643
  }
 
2644
  yyminorunion.yy0 = yyminor;
 
2645
  yyendofinput = (yymajor==0);
 
2646
  ParseARG_STORE;
 
2647
 
 
2648
#ifndef NDEBUG
 
2649
  if( yyTraceFILE ){
 
2650
    fprintf(yyTraceFILE,"%sInput %s\n",yyTracePrompt,yyTokenName[yymajor]);
 
2651
  }
 
2652
#endif
 
2653
 
 
2654
  do{
 
2655
    yyact = yy_find_shift_action(yypParser,(YYCODETYPE)yymajor);
 
2656
    if( yyact<YYNSTATE ){
 
2657
      assert( !yyendofinput );  /* Impossible to shift the $ token */
 
2658
      yy_shift(yypParser,yyact,yymajor,&yyminorunion);
 
2659
      yypParser->yyerrcnt--;
 
2660
      yymajor = YYNOCODE;
 
2661
    }else if( yyact < YYNSTATE + YYNRULE ){
 
2662
      yy_reduce(yypParser,yyact-YYNSTATE);
 
2663
    }else{
 
2664
      assert( yyact == YY_ERROR_ACTION );
 
2665
#ifdef YYERRORSYMBOL
 
2666
      int yymx;
 
2667
#endif
 
2668
#ifndef NDEBUG
 
2669
      if( yyTraceFILE ){
 
2670
        fprintf(yyTraceFILE,"%sSyntax Error!\n",yyTracePrompt);
 
2671
      }
 
2672
#endif
 
2673
#ifdef YYERRORSYMBOL
 
2674
      /* A syntax error has occurred.
 
2675
      ** The response to an error depends upon whether or not the
 
2676
      ** grammar defines an error token "ERROR".  
 
2677
      **
 
2678
      ** This is what we do if the grammar does define ERROR:
 
2679
      **
 
2680
      **  * Call the %syntax_error function.
 
2681
      **
 
2682
      **  * Begin popping the stack until we enter a state where
 
2683
      **    it is legal to shift the error symbol, then shift
 
2684
      **    the error symbol.
 
2685
      **
 
2686
      **  * Set the error count to three.
 
2687
      **
 
2688
      **  * Begin accepting and shifting new tokens.  No new error
 
2689
      **    processing will occur until three tokens have been
 
2690
      **    shifted successfully.
 
2691
      **
 
2692
      */
 
2693
      if( yypParser->yyerrcnt<0 ){
 
2694
        yy_syntax_error(yypParser,yymajor,yyminorunion);
 
2695
      }
 
2696
      yymx = yypParser->yystack[yypParser->yyidx].major;
 
2697
      if( yymx==YYERRORSYMBOL || yyerrorhit ){
 
2698
#ifndef NDEBUG
 
2699
        if( yyTraceFILE ){
 
2700
          fprintf(yyTraceFILE,"%sDiscard input token %s\n",
 
2701
             yyTracePrompt,yyTokenName[yymajor]);
 
2702
        }
 
2703
#endif
 
2704
        yy_destructor(yypParser, (YYCODETYPE)yymajor,&yyminorunion);
 
2705
        yymajor = YYNOCODE;
 
2706
      }else{
 
2707
         while(
 
2708
          yypParser->yyidx >= 0 &&
 
2709
          yymx != YYERRORSYMBOL &&
 
2710
          (yyact = yy_find_reduce_action(
 
2711
                        yypParser->yystack[yypParser->yyidx].stateno,
 
2712
                        YYERRORSYMBOL)) >= YYNSTATE
 
2713
        ){
 
2714
          yy_pop_parser_stack(yypParser);
 
2715
        }
 
2716
        if( yypParser->yyidx < 0 || yymajor==0 ){
 
2717
          yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
 
2718
          yy_parse_failed(yypParser);
 
2719
          yymajor = YYNOCODE;
 
2720
        }else if( yymx!=YYERRORSYMBOL ){
 
2721
          YYMINORTYPE u2;
 
2722
          u2.YYERRSYMDT = 0;
 
2723
          yy_shift(yypParser,yyact,YYERRORSYMBOL,&u2);
 
2724
        }
 
2725
      }
 
2726
      yypParser->yyerrcnt = 3;
 
2727
      yyerrorhit = 1;
 
2728
#elif defined(YYNOERRORRECOVERY)
 
2729
      /* If the YYNOERRORRECOVERY macro is defined, then do not attempt to
 
2730
      ** do any kind of error recovery.  Instead, simply invoke the syntax
 
2731
      ** error routine and continue going as if nothing had happened.
 
2732
      **
 
2733
      ** Applications can set this macro (for example inside %include) if
 
2734
      ** they intend to abandon the parse upon the first syntax error seen.
 
2735
      */
 
2736
      yy_syntax_error(yypParser,yymajor,yyminorunion);
 
2737
      yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
 
2738
      yymajor = YYNOCODE;
 
2739
      
 
2740
#else  /* YYERRORSYMBOL is not defined */
 
2741
      /* This is what we do if the grammar does not define ERROR:
 
2742
      **
 
2743
      **  * Report an error message, and throw away the input token.
 
2744
      **
 
2745
      **  * If the input token is $, then fail the parse.
 
2746
      **
 
2747
      ** As before, subsequent error messages are suppressed until
 
2748
      ** three input tokens have been successfully shifted.
 
2749
      */
 
2750
      if( yypParser->yyerrcnt<=0 ){
 
2751
        yy_syntax_error(yypParser,yymajor,yyminorunion);
 
2752
      }
 
2753
      yypParser->yyerrcnt = 3;
 
2754
      yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
 
2755
      if( yyendofinput ){
 
2756
        yy_parse_failed(yypParser);
 
2757
      }
 
2758
      yymajor = YYNOCODE;
 
2759
#endif
 
2760
    }
 
2761
  }while( yymajor!=YYNOCODE && yypParser->yyidx>=0 );
 
2762
  return;
 
2763
}
 
2764
 
 
2765
 
 
2766
/*
 
2767
 KML_LEMON_END - LEMON generated code ends here 
 
2768
*/
 
2769
 
 
2770
 
 
2771
 
 
2772
 
 
2773
 
 
2774
 
 
2775
 
 
2776
 
 
2777
 
 
2778
 
 
2779
 
 
2780
 
 
2781
 
 
2782
 
 
2783
 
 
2784
 
 
2785
 
 
2786
/*
 
2787
** CAVEAT: there is an incompatibility between LEMON and FLEX
 
2788
** this macro resolves the issue
 
2789
*/
 
2790
#undef yy_accept
 
2791
#define yy_accept       yy_kml_flex_accept
 
2792
 
 
2793
 
 
2794
 
 
2795
/*
 
2796
 KML_FLEX_START - FLEX generated code starts here 
 
2797
*/
 
2798
 
 
2799
#line 3 "lex.Kml.c"
 
2800
 
 
2801
#define  YY_INT_ALIGNED short int
 
2802
 
 
2803
/* A lexical scanner generated by flex */
 
2804
 
 
2805
#define yy_create_buffer Kml_create_buffer
 
2806
#define yy_delete_buffer Kml_delete_buffer
 
2807
#define yy_flex_debug Kml_flex_debug
 
2808
#define yy_init_buffer Kml_init_buffer
 
2809
#define yy_flush_buffer Kml_flush_buffer
 
2810
#define yy_load_buffer_state Kml_load_buffer_state
 
2811
#define yy_switch_to_buffer Kml_switch_to_buffer
 
2812
#define yyin Kmlin
 
2813
#define yyleng Kmlleng
 
2814
#define yylex Kmllex
 
2815
#define yylineno Kmllineno
 
2816
#define yyout Kmlout
 
2817
#define yyrestart Kmlrestart
 
2818
#define yytext Kmltext
 
2819
#define yywrap Kmlwrap
 
2820
#define yyalloc Kmlalloc
 
2821
#define yyrealloc Kmlrealloc
 
2822
#define yyfree Kmlfree
 
2823
 
 
2824
#define FLEX_SCANNER
 
2825
#define YY_FLEX_MAJOR_VERSION 2
 
2826
#define YY_FLEX_MINOR_VERSION 5
 
2827
#define YY_FLEX_SUBMINOR_VERSION 35
 
2828
#if YY_FLEX_SUBMINOR_VERSION > 0
 
2829
#define FLEX_BETA
 
2830
#endif
 
2831
 
 
2832
/* First, we deal with  platform-specific or compiler-specific issues. */
 
2833
 
 
2834
/* begin standard C headers. */
 
2835
#include <stdio.h>
 
2836
#include <string.h>
 
2837
#include <errno.h>
 
2838
#include <stdlib.h>
 
2839
 
 
2840
/* end standard C headers. */
 
2841
 
 
2842
/* flex integer type definitions */
 
2843
 
 
2844
#ifndef FLEXINT_H
 
2845
#define FLEXINT_H
 
2846
 
 
2847
/* C99 systems have <inttypes.h>. Non-C99 systems may or may not. */
 
2848
 
 
2849
#if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
 
2850
 
 
2851
/* C99 says to define __STDC_LIMIT_MACROS before including stdint.h,
 
2852
 * if you want the limit (max/min) macros for int types. 
 
2853
 */
 
2854
#ifndef __STDC_LIMIT_MACROS
 
2855
#define __STDC_LIMIT_MACROS 1
 
2856
#endif
 
2857
 
 
2858
#include <inttypes.h>
 
2859
typedef int8_t flex_int8_t;
 
2860
typedef uint8_t flex_uint8_t;
 
2861
typedef int16_t flex_int16_t;
 
2862
typedef uint16_t flex_uint16_t;
 
2863
typedef int32_t flex_int32_t;
 
2864
typedef uint32_t flex_uint32_t;
 
2865
#else
 
2866
typedef signed char flex_int8_t;
 
2867
typedef short int flex_int16_t;
 
2868
typedef int flex_int32_t;
 
2869
typedef unsigned char flex_uint8_t; 
 
2870
typedef unsigned short int flex_uint16_t;
 
2871
typedef unsigned int flex_uint32_t;
 
2872
 
 
2873
/* Limits of integral types. */
 
2874
#ifndef INT8_MIN
 
2875
#define INT8_MIN               (-128)
 
2876
#endif
 
2877
#ifndef INT16_MIN
 
2878
#define INT16_MIN              (-32767-1)
 
2879
#endif
 
2880
#ifndef INT32_MIN
 
2881
#define INT32_MIN              (-2147483647-1)
 
2882
#endif
 
2883
#ifndef INT8_MAX
 
2884
#define INT8_MAX               (127)
 
2885
#endif
 
2886
#ifndef INT16_MAX
 
2887
#define INT16_MAX              (32767)
 
2888
#endif
 
2889
#ifndef INT32_MAX
 
2890
#define INT32_MAX              (2147483647)
 
2891
#endif
 
2892
#ifndef UINT8_MAX
 
2893
#define UINT8_MAX              (255U)
 
2894
#endif
 
2895
#ifndef UINT16_MAX
 
2896
#define UINT16_MAX             (65535U)
 
2897
#endif
 
2898
#ifndef UINT32_MAX
 
2899
#define UINT32_MAX             (4294967295U)
 
2900
#endif
 
2901
 
 
2902
#endif /* ! C99 */
 
2903
 
 
2904
#endif /* ! FLEXINT_H */
 
2905
 
 
2906
#ifdef __cplusplus
 
2907
 
 
2908
/* The "const" storage-class-modifier is valid. */
 
2909
#define YY_USE_CONST
 
2910
 
 
2911
#else   /* ! __cplusplus */
 
2912
 
 
2913
/* C99 requires __STDC__ to be defined as 1. */
 
2914
#if defined (__STDC__)
 
2915
 
 
2916
#define YY_USE_CONST
 
2917
 
 
2918
#endif  /* defined (__STDC__) */
 
2919
#endif  /* ! __cplusplus */
 
2920
 
 
2921
#ifdef YY_USE_CONST
 
2922
#define yyconst const
 
2923
#else
 
2924
#define yyconst
 
2925
#endif
 
2926
 
 
2927
/* Returned upon end-of-file. */
 
2928
#define YY_NULL 0
 
2929
 
 
2930
/* Promotes a possibly negative, possibly signed char to an unsigned
 
2931
 * integer for use as an array index.  If the signed char is negative,
 
2932
 * we want to instead treat it as an 8-bit unsigned char, hence the
 
2933
 * double cast.
 
2934
 */
 
2935
#define YY_SC_TO_UI(c) ((unsigned int) (unsigned char) c)
 
2936
 
 
2937
/* Enter a start condition.  This macro really ought to take a parameter,
 
2938
 * but we do it the disgusting crufty way forced on us by the ()-less
 
2939
 * definition of BEGIN.
 
2940
 */
 
2941
#define BEGIN (yy_start) = 1 + 2 *
 
2942
 
 
2943
/* Translate the current start state into a value that can be later handed
 
2944
 * to BEGIN to return to the state.  The YYSTATE alias is for lex
 
2945
 * compatibility.
 
2946
 */
 
2947
#define YY_START (((yy_start) - 1) / 2)
 
2948
#define YYSTATE YY_START
 
2949
 
 
2950
/* Action number for EOF rule of a given start state. */
 
2951
#define YY_STATE_EOF(state) (YY_END_OF_BUFFER + state + 1)
 
2952
 
 
2953
/* Special action meaning "start processing a new file". */
 
2954
#define YY_NEW_FILE Kmlrestart(Kmlin  )
 
2955
 
 
2956
#define YY_END_OF_BUFFER_CHAR 0
 
2957
 
 
2958
/* Size of default input buffer. */
 
2959
#ifndef YY_BUF_SIZE
 
2960
#ifdef __ia64__
 
2961
/* On IA-64, the buffer size is 16k, not 8k.
 
2962
 * Moreover, YY_BUF_SIZE is 2*YY_READ_BUF_SIZE in the general case.
 
2963
 * Ditto for the __ia64__ case accordingly.
 
2964
 */
 
2965
#define YY_BUF_SIZE 32768
 
2966
#else
 
2967
#define YY_BUF_SIZE 16384
 
2968
#endif /* __ia64__ */
 
2969
#endif
 
2970
 
 
2971
/* The state buf must be large enough to hold one state per character in the main buffer.
 
2972
 */
 
2973
#define YY_STATE_BUF_SIZE   ((YY_BUF_SIZE + 2) * sizeof(yy_state_type))
 
2974
 
 
2975
#ifndef YY_TYPEDEF_YY_BUFFER_STATE
 
2976
#define YY_TYPEDEF_YY_BUFFER_STATE
 
2977
typedef struct yy_buffer_state *YY_BUFFER_STATE;
 
2978
#endif
 
2979
 
 
2980
extern int Kmlleng;
 
2981
 
 
2982
extern FILE *Kmlin, *Kmlout;
 
2983
 
 
2984
#define EOB_ACT_CONTINUE_SCAN 0
 
2985
#define EOB_ACT_END_OF_FILE 1
 
2986
#define EOB_ACT_LAST_MATCH 2
 
2987
 
 
2988
    #define YY_LESS_LINENO(n)
 
2989
    
 
2990
/* Return all but the first "n" matched characters back to the input stream. */
 
2991
#define yyless(n) \
 
2992
        do \
 
2993
                { \
 
2994
                /* Undo effects of setting up Kmltext. */ \
 
2995
        int yyless_macro_arg = (n); \
 
2996
        YY_LESS_LINENO(yyless_macro_arg);\
 
2997
                *yy_cp = (yy_hold_char); \
 
2998
                YY_RESTORE_YY_MORE_OFFSET \
 
2999
                (yy_c_buf_p) = yy_cp = yy_bp + yyless_macro_arg - YY_MORE_ADJ; \
 
3000
                YY_DO_BEFORE_ACTION; /* set up Kmltext again */ \
 
3001
                } \
 
3002
        while ( 0 )
 
3003
 
 
3004
#define unput(c) yyunput( c, (yytext_ptr)  )
 
3005
 
 
3006
#ifndef YY_TYPEDEF_YY_SIZE_T
 
3007
#define YY_TYPEDEF_YY_SIZE_T
 
3008
typedef size_t yy_size_t;
 
3009
#endif
 
3010
 
 
3011
#ifndef YY_STRUCT_YY_BUFFER_STATE
 
3012
#define YY_STRUCT_YY_BUFFER_STATE
 
3013
struct yy_buffer_state
 
3014
        {
 
3015
        FILE *yy_input_file;
 
3016
 
 
3017
        char *yy_ch_buf;                /* input buffer */
 
3018
        char *yy_buf_pos;               /* current position in input buffer */
 
3019
 
 
3020
        /* Size of input buffer in bytes, not including room for EOB
 
3021
         * characters.
 
3022
         */
 
3023
        yy_size_t yy_buf_size;
 
3024
 
 
3025
        /* Number of characters read into yy_ch_buf, not including EOB
 
3026
         * characters.
 
3027
         */
 
3028
        int yy_n_chars;
 
3029
 
 
3030
        /* Whether we "own" the buffer - i.e., we know we created it,
 
3031
         * and can realloc() it to grow it, and should free() it to
 
3032
         * delete it.
 
3033
         */
 
3034
        int yy_is_our_buffer;
 
3035
 
 
3036
        /* Whether this is an "interactive" input source; if so, and
 
3037
         * if we're using stdio for input, then we want to use getc()
 
3038
         * instead of fread(), to make sure we stop fetching input after
 
3039
         * each newline.
 
3040
         */
 
3041
        int yy_is_interactive;
 
3042
 
 
3043
        /* Whether we're considered to be at the beginning of a line.
 
3044
         * If so, '^' rules will be active on the next match, otherwise
 
3045
         * not.
 
3046
         */
 
3047
        int yy_at_bol;
 
3048
 
 
3049
    int yy_bs_lineno; /**< The line count. */
 
3050
    int yy_bs_column; /**< The column count. */
 
3051
    
 
3052
        /* Whether to try to fill the input buffer when we reach the
 
3053
         * end of it.
 
3054
         */
 
3055
        int yy_fill_buffer;
 
3056
 
 
3057
        int yy_buffer_status;
 
3058
 
 
3059
#define YY_BUFFER_NEW 0
 
3060
#define YY_BUFFER_NORMAL 1
 
3061
        /* When an EOF's been seen but there's still some text to process
 
3062
         * then we mark the buffer as YY_EOF_PENDING, to indicate that we
 
3063
         * shouldn't try reading from the input source any more.  We might
 
3064
         * still have a bunch of tokens to match, though, because of
 
3065
         * possible backing-up.
 
3066
         *
 
3067
         * When we actually see the EOF, we change the status to "new"
 
3068
         * (via Kmlrestart()), so that the user can continue scanning by
 
3069
         * just pointing Kmlin at a new input file.
 
3070
         */
 
3071
#define YY_BUFFER_EOF_PENDING 2
 
3072
 
 
3073
        };
 
3074
#endif /* !YY_STRUCT_YY_BUFFER_STATE */
 
3075
 
 
3076
/* Stack of input buffers. */
 
3077
static size_t yy_buffer_stack_top = 0; /**< index of top of stack. */
 
3078
static size_t yy_buffer_stack_max = 0; /**< capacity of stack. */
 
3079
static YY_BUFFER_STATE * yy_buffer_stack = 0; /**< Stack as an array. */
 
3080
 
 
3081
/* We provide macros for accessing buffer states in case in the
 
3082
 * future we want to put the buffer states in a more general
 
3083
 * "scanner state".
 
3084
 *
 
3085
 * Returns the top of the stack, or NULL.
 
3086
 */
 
3087
#define YY_CURRENT_BUFFER ( (yy_buffer_stack) \
 
3088
                          ? (yy_buffer_stack)[(yy_buffer_stack_top)] \
 
3089
                          : NULL)
 
3090
 
 
3091
/* Same as previous macro, but useful when we know that the buffer stack is not
 
3092
 * NULL or when we need an lvalue. For internal use only.
 
3093
 */
 
3094
#define YY_CURRENT_BUFFER_LVALUE (yy_buffer_stack)[(yy_buffer_stack_top)]
 
3095
 
 
3096
/* yy_hold_char holds the character lost when Kmltext is formed. */
 
3097
static char yy_hold_char;
 
3098
static int yy_n_chars;          /* number of characters read into yy_ch_buf */
 
3099
int Kmlleng;
 
3100
 
 
3101
/* Points to current character in buffer. */
 
3102
static char *yy_c_buf_p = (char *) 0;
 
3103
static int yy_init = 0;         /* whether we need to initialize */
 
3104
static int yy_start = 0;        /* start state number */
 
3105
 
 
3106
/* Flag which is used to allow Kmlwrap()'s to do buffer switches
 
3107
 * instead of setting up a fresh Kmlin.  A bit of a hack ...
 
3108
 */
 
3109
static int yy_did_buffer_switch_on_eof;
 
3110
 
 
3111
void Kmlrestart (FILE *input_file  );
 
3112
void Kml_switch_to_buffer (YY_BUFFER_STATE new_buffer  );
 
3113
YY_BUFFER_STATE Kml_create_buffer (FILE *file,int size  );
 
3114
void Kml_delete_buffer (YY_BUFFER_STATE b  );
 
3115
void Kml_flush_buffer (YY_BUFFER_STATE b  );
 
3116
void Kmlpush_buffer_state (YY_BUFFER_STATE new_buffer  );
 
3117
void Kmlpop_buffer_state (void );
 
3118
 
 
3119
static void Kmlensure_buffer_stack (void );
 
3120
static void Kml_load_buffer_state (void );
 
3121
static void Kml_init_buffer (YY_BUFFER_STATE b,FILE *file  );
 
3122
 
 
3123
#define YY_FLUSH_BUFFER Kml_flush_buffer(YY_CURRENT_BUFFER )
 
3124
 
 
3125
YY_BUFFER_STATE Kml_scan_buffer (char *base,yy_size_t size  );
 
3126
YY_BUFFER_STATE Kml_scan_string (yyconst char *yy_str  );
 
3127
YY_BUFFER_STATE Kml_scan_bytes (yyconst char *bytes,int len  );
 
3128
 
 
3129
void *Kmlalloc (yy_size_t  );
 
3130
void *Kmlrealloc (void *,yy_size_t  );
 
3131
void Kmlfree (void *  );
 
3132
 
 
3133
#define yy_new_buffer Kml_create_buffer
 
3134
 
 
3135
#define yy_set_interactive(is_interactive) \
 
3136
        { \
 
3137
        if ( ! YY_CURRENT_BUFFER ){ \
 
3138
        Kmlensure_buffer_stack (); \
 
3139
                YY_CURRENT_BUFFER_LVALUE =    \
 
3140
            Kml_create_buffer(Kmlin,YY_BUF_SIZE ); \
 
3141
        } \
 
3142
        YY_CURRENT_BUFFER_LVALUE->yy_is_interactive = is_interactive; \
 
3143
        }
 
3144
 
 
3145
#define yy_set_bol(at_bol) \
 
3146
        { \
 
3147
        if ( ! YY_CURRENT_BUFFER ){\
 
3148
        Kmlensure_buffer_stack (); \
 
3149
                YY_CURRENT_BUFFER_LVALUE =    \
 
3150
            Kml_create_buffer(Kmlin,YY_BUF_SIZE ); \
 
3151
        } \
 
3152
        YY_CURRENT_BUFFER_LVALUE->yy_at_bol = at_bol; \
 
3153
        }
 
3154
 
 
3155
#define YY_AT_BOL() (YY_CURRENT_BUFFER_LVALUE->yy_at_bol)
 
3156
 
 
3157
/* Begin user sect3 */
 
3158
 
 
3159
typedef unsigned char YY_CHAR;
 
3160
 
 
3161
FILE *Kmlin = (FILE *) 0, *Kmlout = (FILE *) 0;
 
3162
 
 
3163
typedef int yy_state_type;
 
3164
 
 
3165
extern int Kmllineno;
 
3166
 
 
3167
int Kmllineno = 1;
 
3168
 
 
3169
extern char *Kmltext;
 
3170
#define yytext_ptr Kmltext
 
3171
 
 
3172
static yy_state_type yy_get_previous_state (void );
 
3173
static yy_state_type yy_try_NUL_trans (yy_state_type current_state  );
 
3174
static int yy_get_next_buffer (void );
 
3175
static void yy_fatal_error (yyconst char msg[]  );
 
3176
 
 
3177
/* Done after the current pattern has been matched and before the
 
3178
 * corresponding action - sets up Kmltext.
 
3179
 */
 
3180
#define YY_DO_BEFORE_ACTION \
 
3181
        (yytext_ptr) = yy_bp; \
 
3182
        Kmlleng = (size_t) (yy_cp - yy_bp); \
 
3183
        (yy_hold_char) = *yy_cp; \
 
3184
        *yy_cp = '\0'; \
 
3185
        (yy_c_buf_p) = yy_cp;
 
3186
 
 
3187
#define YY_NUM_RULES 11
 
3188
#define YY_END_OF_BUFFER 12
 
3189
/* This struct is not used in this scanner,
 
3190
   but its presence is necessary. */
 
3191
struct yy_trans_info
 
3192
        {
 
3193
        flex_int32_t yy_verify;
 
3194
        flex_int32_t yy_nxt;
 
3195
        };
 
3196
static yyconst flex_int16_t yy_accept[19] =
 
3197
    {   0,
 
3198
        5,    5,   12,   10,    8,    9,   10,    5,    1,    3,
 
3199
        2,    4,    7,    0,    6,    5,    7,    0
 
3200
    } ;
 
3201
 
 
3202
static yyconst flex_int32_t yy_ec[256] =
 
3203
    {   0,
 
3204
        1,    1,    1,    1,    1,    1,    1,    1,    2,    3,
 
3205
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3206
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3207
        1,    2,    1,    4,    1,    1,    1,    1,    1,    1,
 
3208
        1,    1,    5,    5,    5,    5,    6,    7,    7,    7,
 
3209
        7,    7,    7,    7,    7,    7,    7,    8,    1,    9,
 
3210
       10,   11,    1,    1,   12,   12,   12,   12,   12,   12,
 
3211
       12,   12,   12,   12,   12,   12,   12,   12,   12,   12,
 
3212
       12,   12,   12,   12,   12,   12,   12,   12,   12,   12,
 
3213
        1,    1,    1,    1,   12,    1,   12,   12,   12,   12,
 
3214
 
 
3215
       12,   12,   12,   12,   12,   12,   12,   12,   12,   12,
 
3216
       12,   12,   12,   12,   12,   12,   12,   12,   12,   12,
 
3217
       12,   12,    1,    1,    1,    1,    1,    1,    1,    1,
 
3218
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3219
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3220
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3221
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3222
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3223
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3224
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3225
 
 
3226
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3227
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3228
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3229
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3230
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3231
        1,    1,    1,    1,    1
 
3232
    } ;
 
3233
 
 
3234
static yyconst flex_int32_t yy_meta[13] =
 
3235
    {   0,
 
3236
        1,    1,    1,    1,    2,    1,    3,    4,    5,    1,
 
3237
        5,    4
 
3238
    } ;
 
3239
 
 
3240
static yyconst flex_int16_t yy_base[22] =
 
3241
    {   0,
 
3242
        0,    0,   23,   24,   24,   24,   18,    0,   24,   24,
 
3243
       24,   24,    0,   17,   24,    0,    0,   24,   12,   15,
 
3244
       16
 
3245
    } ;
 
3246
 
 
3247
static yyconst flex_int16_t yy_def[22] =
 
3248
    {   0,
 
3249
       18,    1,   18,   18,   18,   18,   19,   20,   18,   18,
 
3250
       18,   18,   21,   19,   18,   20,   21,    0,   18,   18,
 
3251
       18
 
3252
    } ;
 
3253
 
 
3254
static yyconst flex_int16_t yy_nxt[37] =
 
3255
    {   0,
 
3256
        4,    5,    6,    7,    8,    9,    8,    4,   10,   11,
 
3257
       12,   13,   14,   14,   14,   14,   16,   16,   17,   17,
 
3258
       15,   15,   18,    3,   18,   18,   18,   18,   18,   18,
 
3259
       18,   18,   18,   18,   18,   18
 
3260
    } ;
 
3261
 
 
3262
static yyconst flex_int16_t yy_chk[37] =
 
3263
    {   0,
 
3264
        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
 
3265
        1,    1,   19,   19,   19,   19,   20,   20,   21,   21,
 
3266
       14,    7,    3,   18,   18,   18,   18,   18,   18,   18,
 
3267
       18,   18,   18,   18,   18,   18
 
3268
    } ;
 
3269
 
 
3270
static yy_state_type yy_last_accepting_state;
 
3271
static char *yy_last_accepting_cpos;
 
3272
 
 
3273
extern int Kml_flex_debug;
 
3274
int Kml_flex_debug = 0;
 
3275
 
 
3276
/* The intent behind this definition is that it'll catch
 
3277
 * any uses of REJECT which flex missed.
 
3278
 */
 
3279
#define REJECT reject_used_but_not_detected
 
3280
#define yymore() yymore_used_but_not_detected
 
3281
#define YY_MORE_ADJ 0
 
3282
#define YY_RESTORE_YY_MORE_OFFSET
 
3283
char *Kmltext;
 
3284
/* 
 
3285
 kmlLexer.l -- KML parser - FLEX config
 
3286
  
 
3287
 version 2.4, 2011 June 14
 
3288
 
 
3289
 Author: Sandro Furieri a.furieri@lqt.it
 
3290
 
 
3291
 ------------------------------------------------------------------------------
 
3292
 
 
3293
 Version: MPL 1.1/GPL 2.0/LGPL 2.1
 
3294
 
 
3295
 The contents of this file are subject to the Mozilla Public License Version
 
3296
 1.1 (the "License"); you may not use this file except in compliance with
 
3297
 the License. You may obtain a copy of the License at
 
3298
 http://www.mozilla.org/MPL/
 
3299
 
 
3300
Software distributed under the License is distributed on an "AS IS" basis,
 
3301
WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 
3302
for the specific language governing rights and limitations under the
 
3303
License.
 
3304
 
 
3305
The Original Code is the SpatiaLite library
 
3306
 
 
3307
The Initial Developer of the Original Code is Alessandro Furieri
 
3308
 
 
3309
Portions created by the Initial Developer are Copyright (C) 2011
 
3310
the Initial Developer. All Rights Reserved.
 
3311
 
 
3312
Alternatively, the contents of this file may be used under the terms of
 
3313
either the GNU General Public License Version 2 or later (the "GPL"), or
 
3314
the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 
3315
in which case the provisions of the GPL or the LGPL are applicable instead
 
3316
of those above. If you wish to allow use of your version of this file only
 
3317
under the terms of either the GPL or the LGPL, and not to allow others to
 
3318
use your version of this file under the terms of the MPL, indicate your
 
3319
decision by deleting the provisions above and replace them with the notice
 
3320
and other provisions required by the GPL or the LGPL. If you do not delete
 
3321
the provisions above, a recipient may use your version of this file under
 
3322
the terms of any one of the MPL, the GPL or the LGPL.
 
3323
 
 
3324
*/
 
3325
 
 
3326
/* For debugging purposes */
 
3327
int kml_line = 1, kml_col = 1;
 
3328
 
 
3329
/**
 
3330
*  The main string-token matcher.
 
3331
*  The lower case part is probably not needed.  We should really be converting 
 
3332
*  The string to all uppercase/lowercase to make it case iNsEnSiTiVe.
 
3333
*  What Flex will do is, For the input string, beginning from the front, Flex
 
3334
*  will try to match with any of the defined tokens from below.  Flex will 
 
3335
*  then match the string of longest length.  Suppose the string is: POINTM,
 
3336
*  Flex would match both POINT and POINTM, but since POINTM is the longer
 
3337
*  of the two tokens, FLEX will match POINTM.
 
3338
*/
 
3339
 
 
3340
#define INITIAL 0
 
3341
 
 
3342
#ifndef YY_NO_UNISTD_H
 
3343
/* Special case for "unistd.h", since it is non-ANSI. We include it way
 
3344
 * down here because we want the user's section 1 to have been scanned first.
 
3345
 * The user has a chance to override it with an option.
 
3346
 */
 
3347
#include <unistd.h>
 
3348
#endif
 
3349
 
 
3350
#ifndef YY_EXTRA_TYPE
 
3351
#define YY_EXTRA_TYPE void *
 
3352
#endif
 
3353
 
 
3354
static int yy_init_globals (void );
 
3355
 
 
3356
/* Accessor methods to globals.
 
3357
   These are made visible to non-reentrant scanners for convenience. */
 
3358
 
 
3359
int Kmllex_destroy (void );
 
3360
 
 
3361
int Kmlget_debug (void );
 
3362
 
 
3363
void Kmlset_debug (int debug_flag  );
 
3364
 
 
3365
YY_EXTRA_TYPE Kmlget_extra (void );
 
3366
 
 
3367
void Kmlset_extra (YY_EXTRA_TYPE user_defined  );
 
3368
 
 
3369
FILE *Kmlget_in (void );
 
3370
 
 
3371
void Kmlset_in  (FILE * in_str  );
 
3372
 
 
3373
FILE *Kmlget_out (void );
 
3374
 
 
3375
void Kmlset_out  (FILE * out_str  );
 
3376
 
 
3377
int Kmlget_leng (void );
 
3378
 
 
3379
char *Kmlget_text (void );
 
3380
 
 
3381
int Kmlget_lineno (void );
 
3382
 
 
3383
void Kmlset_lineno (int line_number  );
 
3384
 
 
3385
/* Macros after this point can all be overridden by user definitions in
 
3386
 * section 1.
 
3387
 */
 
3388
 
 
3389
#ifndef YY_SKIP_YYWRAP
 
3390
#ifdef __cplusplus
 
3391
extern "C" int Kmlwrap (void );
 
3392
#else
 
3393
extern int Kmlwrap (void );
 
3394
#endif
 
3395
#endif
 
3396
 
 
3397
    static void yyunput (int c,char *buf_ptr  );
 
3398
    
 
3399
#ifndef yytext_ptr
 
3400
static void yy_flex_strncpy (char *,yyconst char *,int );
 
3401
#endif
 
3402
 
 
3403
#ifdef YY_NEED_STRLEN
 
3404
static int yy_flex_strlen (yyconst char * );
 
3405
#endif
 
3406
 
 
3407
#ifndef YY_NO_INPUT
 
3408
 
 
3409
#ifdef __cplusplus
 
3410
static int yyinput (void );
 
3411
#else
 
3412
static int input (void );
 
3413
#endif
 
3414
 
 
3415
#endif
 
3416
 
 
3417
/* Amount of stuff to slurp up with each read. */
 
3418
#ifndef YY_READ_BUF_SIZE
 
3419
#ifdef __ia64__
 
3420
/* On IA-64, the buffer size is 16k, not 8k */
 
3421
#define YY_READ_BUF_SIZE 16384
 
3422
#else
 
3423
#define YY_READ_BUF_SIZE 8192
 
3424
#endif /* __ia64__ */
 
3425
#endif
 
3426
 
 
3427
/* Copy whatever the last rule matched to the standard output. */
 
3428
#ifndef ECHO
 
3429
/* This used to be an fputs(), but since the string might contain NUL's,
 
3430
 * we now use fwrite().
 
3431
 */
 
3432
#define ECHO do { if (fwrite( Kmltext, Kmlleng, 1, Kmlout )) {} } while (0)
 
3433
#endif
 
3434
 
 
3435
/* Gets input and stuffs it into "buf".  number of characters read, or YY_NULL,
 
3436
 * is returned in "result".
 
3437
 */
 
3438
#ifndef YY_INPUT
 
3439
#define YY_INPUT(buf,result,max_size) \
 
3440
        if ( YY_CURRENT_BUFFER_LVALUE->yy_is_interactive ) \
 
3441
                { \
 
3442
                int c = '*'; \
 
3443
                size_t n; \
 
3444
                for ( n = 0; n < max_size && \
 
3445
                             (c = getc( Kmlin )) != EOF && c != '\n'; ++n ) \
 
3446
                        buf[n] = (char) c; \
 
3447
                if ( c == '\n' ) \
 
3448
                        buf[n++] = (char) c; \
 
3449
                if ( c == EOF && ferror( Kmlin ) ) \
 
3450
                        YY_FATAL_ERROR( "input in flex scanner failed" ); \
 
3451
                result = n; \
 
3452
                } \
 
3453
        else \
 
3454
                { \
 
3455
                errno=0; \
 
3456
                while ( (result = fread(buf, 1, max_size, Kmlin))==0 && ferror(Kmlin)) \
 
3457
                        { \
 
3458
                        if( errno != EINTR) \
 
3459
                                { \
 
3460
                                YY_FATAL_ERROR( "input in flex scanner failed" ); \
 
3461
                                break; \
 
3462
                                } \
 
3463
                        errno=0; \
 
3464
                        clearerr(Kmlin); \
 
3465
                        } \
 
3466
                }\
 
3467
\
 
3468
 
 
3469
#endif
 
3470
 
 
3471
/* No semi-colon after return; correct usage is to write "yyterminate();" -
 
3472
 * we don't want an extra ';' after the "return" because that will cause
 
3473
 * some compilers to complain about unreachable statements.
 
3474
 */
 
3475
#ifndef yyterminate
 
3476
#define yyterminate() return YY_NULL
 
3477
#endif
 
3478
 
 
3479
/* Number of entries by which start-condition stack grows. */
 
3480
#ifndef YY_START_STACK_INCR
 
3481
#define YY_START_STACK_INCR 25
 
3482
#endif
 
3483
 
 
3484
/* Report a fatal error. */
 
3485
#ifndef YY_FATAL_ERROR
 
3486
#define YY_FATAL_ERROR(msg) yy_fatal_error( msg )
 
3487
#endif
 
3488
 
 
3489
/* end tables serialization structures and prototypes */
 
3490
 
 
3491
/* Default declaration of generated scanner - a define so the user can
 
3492
 * easily add parameters.
 
3493
 */
 
3494
#ifndef YY_DECL
 
3495
#define YY_DECL_IS_OURS 1
 
3496
 
 
3497
extern int Kmllex (void);
 
3498
 
 
3499
#define YY_DECL int Kmllex (void)
 
3500
#endif /* !YY_DECL */
 
3501
 
 
3502
/* Code executed at the beginning of each rule, after Kmltext and Kmlleng
 
3503
 * have been set up.
 
3504
 */
 
3505
#ifndef YY_USER_ACTION
 
3506
#define YY_USER_ACTION
 
3507
#endif
 
3508
 
 
3509
/* Code executed at the end of each rule. */
 
3510
#ifndef YY_BREAK
 
3511
#define YY_BREAK break;
 
3512
#endif
 
3513
 
 
3514
#define YY_RULE_SETUP \
 
3515
        YY_USER_ACTION
 
3516
 
 
3517
/** The main scanner function which does all the work.
 
3518
 */
 
3519
YY_DECL
 
3520
{
 
3521
        register yy_state_type yy_current_state;
 
3522
        register char *yy_cp, *yy_bp;
 
3523
        register int yy_act;
 
3524
    
 
3525
        if ( !(yy_init) )
 
3526
                {
 
3527
                (yy_init) = 1;
 
3528
 
 
3529
#ifdef YY_USER_INIT
 
3530
                YY_USER_INIT;
 
3531
#endif
 
3532
 
 
3533
                if ( ! (yy_start) )
 
3534
                        (yy_start) = 1; /* first start state */
 
3535
 
 
3536
                if ( ! Kmlin )
 
3537
                        Kmlin = stdin;
 
3538
 
 
3539
                if ( ! Kmlout )
 
3540
                        Kmlout = stdout;
 
3541
 
 
3542
                if ( ! YY_CURRENT_BUFFER ) {
 
3543
                        Kmlensure_buffer_stack ();
 
3544
                        YY_CURRENT_BUFFER_LVALUE =
 
3545
                                Kml_create_buffer(Kmlin,YY_BUF_SIZE );
 
3546
                }
 
3547
 
 
3548
                Kml_load_buffer_state( );
 
3549
                }
 
3550
 
 
3551
        while ( 1 )             /* loops until end-of-file is reached */
 
3552
                {
 
3553
                yy_cp = (yy_c_buf_p);
 
3554
 
 
3555
                /* Support of Kmltext. */
 
3556
                *yy_cp = (yy_hold_char);
 
3557
 
 
3558
                /* yy_bp points to the position in yy_ch_buf of the start of
 
3559
                 * the current run.
 
3560
                 */
 
3561
                yy_bp = yy_cp;
 
3562
 
 
3563
                yy_current_state = (yy_start);
 
3564
yy_match:
 
3565
                do
 
3566
                        {
 
3567
                        register YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)];
 
3568
                        if ( yy_accept[yy_current_state] )
 
3569
                                {
 
3570
                                (yy_last_accepting_state) = yy_current_state;
 
3571
                                (yy_last_accepting_cpos) = yy_cp;
 
3572
                                }
 
3573
                        while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
 
3574
                                {
 
3575
                                yy_current_state = (int) yy_def[yy_current_state];
 
3576
                                if ( yy_current_state >= 19 )
 
3577
                                        yy_c = yy_meta[(unsigned int) yy_c];
 
3578
                                }
 
3579
                        yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
 
3580
                        ++yy_cp;
 
3581
                        }
 
3582
                while ( yy_base[yy_current_state] != 24 );
 
3583
 
 
3584
yy_find_action:
 
3585
                yy_act = yy_accept[yy_current_state];
 
3586
                if ( yy_act == 0 )
 
3587
                        { /* have to back up */
 
3588
                        yy_cp = (yy_last_accepting_cpos);
 
3589
                        yy_current_state = (yy_last_accepting_state);
 
3590
                        yy_act = yy_accept[yy_current_state];
 
3591
                        }
 
3592
 
 
3593
                YY_DO_BEFORE_ACTION;
 
3594
 
 
3595
do_action:      /* This label is used only to access EOF actions. */
 
3596
 
 
3597
                switch ( yy_act )
 
3598
        { /* beginning of action switch */
 
3599
                        case 0: /* must back up */
 
3600
                        /* undo the effects of YY_DO_BEFORE_ACTION */
 
3601
                        *yy_cp = (yy_hold_char);
 
3602
                        yy_cp = (yy_last_accepting_cpos);
 
3603
                        yy_current_state = (yy_last_accepting_state);
 
3604
                        goto yy_find_action;
 
3605
 
 
3606
case 1:
 
3607
YY_RULE_SETUP
 
3608
{ kml_freeString(&(KmlLval.pval)); return KML_END; }
 
3609
        YY_BREAK
 
3610
case 2:
 
3611
YY_RULE_SETUP
 
3612
{ kml_freeString(&(KmlLval.pval)); return KML_EQ; }
 
3613
        YY_BREAK
 
3614
case 3:
 
3615
YY_RULE_SETUP
 
3616
{ kml_freeString(&(KmlLval.pval)); return KML_OPEN; }
 
3617
        YY_BREAK
 
3618
case 4:
 
3619
YY_RULE_SETUP
 
3620
{ kml_freeString(&(KmlLval.pval)); return KML_CLOSE; }
 
3621
        YY_BREAK
 
3622
case 5:
 
3623
YY_RULE_SETUP
 
3624
{ kml_saveString(&(KmlLval.pval), Kmltext); return KML_COORD; }
 
3625
        YY_BREAK
 
3626
case 6:
 
3627
/* rule 6 can match eol */
 
3628
YY_RULE_SETUP
 
3629
{ kml_saveString(&(KmlLval.pval), Kmltext); return KML_VALUE; }
 
3630
        YY_BREAK
 
3631
case 7:
 
3632
YY_RULE_SETUP
 
3633
{ kml_saveString(&(KmlLval.pval), Kmltext); return KML_KEYWORD; }
 
3634
        YY_BREAK
 
3635
case 8:
 
3636
YY_RULE_SETUP
 
3637
{ kml_freeString(&(KmlLval.pval)); kml_col += (int) strlen(Kmltext); }               /* ignore but count white space */
 
3638
        YY_BREAK
 
3639
case 9:
 
3640
/* rule 9 can match eol */
 
3641
YY_RULE_SETUP
 
3642
{ kml_freeString(&(KmlLval.pval)); kml_col = 0; ++kml_line; }
 
3643
        YY_BREAK
 
3644
case 10:
 
3645
YY_RULE_SETUP
 
3646
{ kml_freeString(&(KmlLval.pval)); kml_col += (int) strlen(Kmltext); return -1; }
 
3647
        YY_BREAK
 
3648
case 11:
 
3649
YY_RULE_SETUP
 
3650
ECHO;
 
3651
        YY_BREAK
 
3652
case YY_STATE_EOF(INITIAL):
 
3653
        yyterminate();
 
3654
 
 
3655
        case YY_END_OF_BUFFER:
 
3656
                {
 
3657
                /* Amount of text matched not including the EOB char. */
 
3658
                int yy_amount_of_matched_text = (int) (yy_cp - (yytext_ptr)) - 1;
 
3659
 
 
3660
                /* Undo the effects of YY_DO_BEFORE_ACTION. */
 
3661
                *yy_cp = (yy_hold_char);
 
3662
                YY_RESTORE_YY_MORE_OFFSET
 
3663
 
 
3664
                if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_NEW )
 
3665
                        {
 
3666
                        /* We're scanning a new file or input source.  It's
 
3667
                         * possible that this happened because the user
 
3668
                         * just pointed Kmlin at a new source and called
 
3669
                         * Kmllex().  If so, then we have to assure
 
3670
                         * consistency between YY_CURRENT_BUFFER and our
 
3671
                         * globals.  Here is the right place to do so, because
 
3672
                         * this is the first action (other than possibly a
 
3673
                         * back-up) that will match for the new input source.
 
3674
                         */
 
3675
                        (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars;
 
3676
                        YY_CURRENT_BUFFER_LVALUE->yy_input_file = Kmlin;
 
3677
                        YY_CURRENT_BUFFER_LVALUE->yy_buffer_status = YY_BUFFER_NORMAL;
 
3678
                        }
 
3679
 
 
3680
                /* Note that here we test for yy_c_buf_p "<=" to the position
 
3681
                 * of the first EOB in the buffer, since yy_c_buf_p will
 
3682
                 * already have been incremented past the NUL character
 
3683
                 * (since all states make transitions on EOB to the
 
3684
                 * end-of-buffer state).  Contrast this with the test
 
3685
                 * in input().
 
3686
                 */
 
3687
                if ( (yy_c_buf_p) <= &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] )
 
3688
                        { /* This was really a NUL. */
 
3689
                        yy_state_type yy_next_state;
 
3690
 
 
3691
                        (yy_c_buf_p) = (yytext_ptr) + yy_amount_of_matched_text;
 
3692
 
 
3693
                        yy_current_state = yy_get_previous_state(  );
 
3694
 
 
3695
                        /* Okay, we're now positioned to make the NUL
 
3696
                         * transition.  We couldn't have
 
3697
                         * yy_get_previous_state() go ahead and do it
 
3698
                         * for us because it doesn't know how to deal
 
3699
                         * with the possibility of jamming (and we don't
 
3700
                         * want to build jamming into it because then it
 
3701
                         * will run more slowly).
 
3702
                         */
 
3703
 
 
3704
                        yy_next_state = yy_try_NUL_trans( yy_current_state );
 
3705
 
 
3706
                        yy_bp = (yytext_ptr) + YY_MORE_ADJ;
 
3707
 
 
3708
                        if ( yy_next_state )
 
3709
                                {
 
3710
                                /* Consume the NUL. */
 
3711
                                yy_cp = ++(yy_c_buf_p);
 
3712
                                yy_current_state = yy_next_state;
 
3713
                                goto yy_match;
 
3714
                                }
 
3715
 
 
3716
                        else
 
3717
                                {
 
3718
                                yy_cp = (yy_c_buf_p);
 
3719
                                goto yy_find_action;
 
3720
                                }
 
3721
                        }
 
3722
 
 
3723
                else switch ( yy_get_next_buffer(  ) )
 
3724
                        {
 
3725
                        case EOB_ACT_END_OF_FILE:
 
3726
                                {
 
3727
                                (yy_did_buffer_switch_on_eof) = 0;
 
3728
 
 
3729
                                if ( Kmlwrap( ) )
 
3730
                                        {
 
3731
                                        /* Note: because we've taken care in
 
3732
                                         * yy_get_next_buffer() to have set up
 
3733
                                         * Kmltext, we can now set up
 
3734
                                         * yy_c_buf_p so that if some total
 
3735
                                         * hoser (like flex itself) wants to
 
3736
                                         * call the scanner after we return the
 
3737
                                         * YY_NULL, it'll still work - another
 
3738
                                         * YY_NULL will get returned.
 
3739
                                         */
 
3740
                                        (yy_c_buf_p) = (yytext_ptr) + YY_MORE_ADJ;
 
3741
 
 
3742
                                        yy_act = YY_STATE_EOF(YY_START);
 
3743
                                        goto do_action;
 
3744
                                        }
 
3745
 
 
3746
                                else
 
3747
                                        {
 
3748
                                        if ( ! (yy_did_buffer_switch_on_eof) )
 
3749
                                                YY_NEW_FILE;
 
3750
                                        }
 
3751
                                break;
 
3752
                                }
 
3753
 
 
3754
                        case EOB_ACT_CONTINUE_SCAN:
 
3755
                                (yy_c_buf_p) =
 
3756
                                        (yytext_ptr) + yy_amount_of_matched_text;
 
3757
 
 
3758
                                yy_current_state = yy_get_previous_state(  );
 
3759
 
 
3760
                                yy_cp = (yy_c_buf_p);
 
3761
                                yy_bp = (yytext_ptr) + YY_MORE_ADJ;
 
3762
                                goto yy_match;
 
3763
 
 
3764
                        case EOB_ACT_LAST_MATCH:
 
3765
                                (yy_c_buf_p) =
 
3766
                                &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)];
 
3767
 
 
3768
                                yy_current_state = yy_get_previous_state(  );
 
3769
 
 
3770
                                yy_cp = (yy_c_buf_p);
 
3771
                                yy_bp = (yytext_ptr) + YY_MORE_ADJ;
 
3772
                                goto yy_find_action;
 
3773
                        }
 
3774
                break;
 
3775
                }
 
3776
 
 
3777
        default:
 
3778
                YY_FATAL_ERROR(
 
3779
                        "fatal flex scanner internal error--no action found" );
 
3780
        } /* end of action switch */
 
3781
                } /* end of scanning one token */
 
3782
} /* end of Kmllex */
 
3783
 
 
3784
/* yy_get_next_buffer - try to read in a new buffer
 
3785
 *
 
3786
 * Returns a code representing an action:
 
3787
 *      EOB_ACT_LAST_MATCH -
 
3788
 *      EOB_ACT_CONTINUE_SCAN - continue scanning from current position
 
3789
 *      EOB_ACT_END_OF_FILE - end of file
 
3790
 */
 
3791
static int yy_get_next_buffer (void)
 
3792
{
 
3793
        register char *dest = YY_CURRENT_BUFFER_LVALUE->yy_ch_buf;
 
3794
        register char *source = (yytext_ptr);
 
3795
        register int number_to_move, i;
 
3796
        int ret_val;
 
3797
 
 
3798
        if ( (yy_c_buf_p) > &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] )
 
3799
                YY_FATAL_ERROR(
 
3800
                "fatal flex scanner internal error--end of buffer missed" );
 
3801
 
 
3802
        if ( YY_CURRENT_BUFFER_LVALUE->yy_fill_buffer == 0 )
 
3803
                { /* Don't try to fill the buffer, so this is an EOF. */
 
3804
                if ( (yy_c_buf_p) - (yytext_ptr) - YY_MORE_ADJ == 1 )
 
3805
                        {
 
3806
                        /* We matched a single character, the EOB, so
 
3807
                         * treat this as a final EOF.
 
3808
                         */
 
3809
                        return EOB_ACT_END_OF_FILE;
 
3810
                        }
 
3811
 
 
3812
                else
 
3813
                        {
 
3814
                        /* We matched some text prior to the EOB, first
 
3815
                         * process it.
 
3816
                         */
 
3817
                        return EOB_ACT_LAST_MATCH;
 
3818
                        }
 
3819
                }
 
3820
 
 
3821
        /* Try to read more data. */
 
3822
 
 
3823
        /* First move last chars to start of buffer. */
 
3824
        number_to_move = (int) ((yy_c_buf_p) - (yytext_ptr)) - 1;
 
3825
 
 
3826
        for ( i = 0; i < number_to_move; ++i )
 
3827
                *(dest++) = *(source++);
 
3828
 
 
3829
        if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_EOF_PENDING )
 
3830
                /* don't do the read, it's not guaranteed to return an EOF,
 
3831
                 * just force an EOF
 
3832
                 */
 
3833
                YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars) = 0;
 
3834
 
 
3835
        else
 
3836
                {
 
3837
                        int num_to_read =
 
3838
                        YY_CURRENT_BUFFER_LVALUE->yy_buf_size - number_to_move - 1;
 
3839
 
 
3840
                while ( num_to_read <= 0 )
 
3841
                        { /* Not enough room in the buffer - grow it. */
 
3842
 
 
3843
                        /* just a shorter name for the current buffer */
 
3844
                        YY_BUFFER_STATE b = YY_CURRENT_BUFFER;
 
3845
 
 
3846
                        int yy_c_buf_p_offset =
 
3847
                                (int) ((yy_c_buf_p) - b->yy_ch_buf);
 
3848
 
 
3849
                        if ( b->yy_is_our_buffer )
 
3850
                                {
 
3851
                                int new_size = b->yy_buf_size * 2;
 
3852
 
 
3853
                                if ( new_size <= 0 )
 
3854
                                        b->yy_buf_size += b->yy_buf_size / 8;
 
3855
                                else
 
3856
                                        b->yy_buf_size *= 2;
 
3857
 
 
3858
                                b->yy_ch_buf = (char *)
 
3859
                                        /* Include room in for 2 EOB chars. */
 
3860
                                        Kmlrealloc((void *) b->yy_ch_buf,b->yy_buf_size + 2  );
 
3861
                                }
 
3862
                        else
 
3863
                                /* Can't grow it, we don't own it. */
 
3864
                                b->yy_ch_buf = 0;
 
3865
 
 
3866
                        if ( ! b->yy_ch_buf )
 
3867
                                YY_FATAL_ERROR(
 
3868
                                "fatal error - scanner input buffer overflow" );
 
3869
 
 
3870
                        (yy_c_buf_p) = &b->yy_ch_buf[yy_c_buf_p_offset];
 
3871
 
 
3872
                        num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size -
 
3873
                                                number_to_move - 1;
 
3874
 
 
3875
                        }
 
3876
 
 
3877
                if ( num_to_read > YY_READ_BUF_SIZE )
 
3878
                        num_to_read = YY_READ_BUF_SIZE;
 
3879
 
 
3880
                /* Read in more data. */
 
3881
                YY_INPUT( (&YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[number_to_move]),
 
3882
                        (yy_n_chars), (size_t) num_to_read );
 
3883
 
 
3884
                YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars);
 
3885
                }
 
3886
 
 
3887
        if ( (yy_n_chars) == 0 )
 
3888
                {
 
3889
                if ( number_to_move == YY_MORE_ADJ )
 
3890
                        {
 
3891
                        ret_val = EOB_ACT_END_OF_FILE;
 
3892
                        Kmlrestart(Kmlin  );
 
3893
                        }
 
3894
 
 
3895
                else
 
3896
                        {
 
3897
                        ret_val = EOB_ACT_LAST_MATCH;
 
3898
                        YY_CURRENT_BUFFER_LVALUE->yy_buffer_status =
 
3899
                                YY_BUFFER_EOF_PENDING;
 
3900
                        }
 
3901
                }
 
3902
 
 
3903
        else
 
3904
                ret_val = EOB_ACT_CONTINUE_SCAN;
 
3905
 
 
3906
        if ((yy_size_t) ((yy_n_chars) + number_to_move) > YY_CURRENT_BUFFER_LVALUE->yy_buf_size) {
 
3907
                /* Extend the array by 50%, plus the number we really need. */
 
3908
                yy_size_t new_size = (yy_n_chars) + number_to_move + ((yy_n_chars) >> 1);
 
3909
                YY_CURRENT_BUFFER_LVALUE->yy_ch_buf = (char *) Kmlrealloc((void *) YY_CURRENT_BUFFER_LVALUE->yy_ch_buf,new_size  );
 
3910
                if ( ! YY_CURRENT_BUFFER_LVALUE->yy_ch_buf )
 
3911
                        YY_FATAL_ERROR( "out of dynamic memory in yy_get_next_buffer()" );
 
3912
        }
 
3913
 
 
3914
        (yy_n_chars) += number_to_move;
 
3915
        YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] = YY_END_OF_BUFFER_CHAR;
 
3916
        YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] = YY_END_OF_BUFFER_CHAR;
 
3917
 
 
3918
        (yytext_ptr) = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[0];
 
3919
 
 
3920
        return ret_val;
 
3921
}
 
3922
 
 
3923
/* yy_get_previous_state - get the state just before the EOB char was reached */
 
3924
 
 
3925
    static yy_state_type yy_get_previous_state (void)
 
3926
{
 
3927
        register yy_state_type yy_current_state;
 
3928
        register char *yy_cp;
 
3929
    
 
3930
        yy_current_state = (yy_start);
 
3931
 
 
3932
        for ( yy_cp = (yytext_ptr) + YY_MORE_ADJ; yy_cp < (yy_c_buf_p); ++yy_cp )
 
3933
                {
 
3934
                register YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 1);
 
3935
                if ( yy_accept[yy_current_state] )
 
3936
                        {
 
3937
                        (yy_last_accepting_state) = yy_current_state;
 
3938
                        (yy_last_accepting_cpos) = yy_cp;
 
3939
                        }
 
3940
                while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
 
3941
                        {
 
3942
                        yy_current_state = (int) yy_def[yy_current_state];
 
3943
                        if ( yy_current_state >= 19 )
 
3944
                                yy_c = yy_meta[(unsigned int) yy_c];
 
3945
                        }
 
3946
                yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
 
3947
                }
 
3948
 
 
3949
        return yy_current_state;
 
3950
}
 
3951
 
 
3952
/* yy_try_NUL_trans - try to make a transition on the NUL character
 
3953
 *
 
3954
 * synopsis
 
3955
 *      next_state = yy_try_NUL_trans( current_state );
 
3956
 */
 
3957
    static yy_state_type yy_try_NUL_trans  (yy_state_type yy_current_state )
 
3958
{
 
3959
        register int yy_is_jam;
 
3960
        register char *yy_cp = (yy_c_buf_p);
 
3961
 
 
3962
        register YY_CHAR yy_c = 1;
 
3963
        if ( yy_accept[yy_current_state] )
 
3964
                {
 
3965
                (yy_last_accepting_state) = yy_current_state;
 
3966
                (yy_last_accepting_cpos) = yy_cp;
 
3967
                }
 
3968
        while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
 
3969
                {
 
3970
                yy_current_state = (int) yy_def[yy_current_state];
 
3971
                if ( yy_current_state >= 19 )
 
3972
                        yy_c = yy_meta[(unsigned int) yy_c];
 
3973
                }
 
3974
        yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
 
3975
        yy_is_jam = (yy_current_state == 18);
 
3976
 
 
3977
        return yy_is_jam ? 0 : yy_current_state;
 
3978
}
 
3979
 
 
3980
    static void yyunput (int c, register char * yy_bp )
 
3981
{
 
3982
        register char *yy_cp;
 
3983
    
 
3984
    yy_cp = (yy_c_buf_p);
 
3985
 
 
3986
        /* undo effects of setting up Kmltext */
 
3987
        *yy_cp = (yy_hold_char);
 
3988
 
 
3989
        if ( yy_cp < YY_CURRENT_BUFFER_LVALUE->yy_ch_buf + 2 )
 
3990
                { /* need to shift things up to make room */
 
3991
                /* +2 for EOB chars. */
 
3992
                register int number_to_move = (yy_n_chars) + 2;
 
3993
                register char *dest = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[
 
3994
                                        YY_CURRENT_BUFFER_LVALUE->yy_buf_size + 2];
 
3995
                register char *source =
 
3996
                                &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[number_to_move];
 
3997
 
 
3998
                while ( source > YY_CURRENT_BUFFER_LVALUE->yy_ch_buf )
 
3999
                        *--dest = *--source;
 
4000
 
 
4001
                yy_cp += (int) (dest - source);
 
4002
                yy_bp += (int) (dest - source);
 
4003
                YY_CURRENT_BUFFER_LVALUE->yy_n_chars =
 
4004
                        (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_buf_size;
 
4005
 
 
4006
                if ( yy_cp < YY_CURRENT_BUFFER_LVALUE->yy_ch_buf + 2 )
 
4007
                        YY_FATAL_ERROR( "flex scanner push-back overflow" );
 
4008
                }
 
4009
 
 
4010
        *--yy_cp = (char) c;
 
4011
 
 
4012
        (yytext_ptr) = yy_bp;
 
4013
        (yy_hold_char) = *yy_cp;
 
4014
        (yy_c_buf_p) = yy_cp;
 
4015
}
 
4016
 
 
4017
#ifndef YY_NO_INPUT
 
4018
#ifdef __cplusplus
 
4019
    static int yyinput (void)
 
4020
#else
 
4021
    static int input  (void)
 
4022
#endif
 
4023
 
 
4024
{
 
4025
        int c;
 
4026
    
 
4027
        *(yy_c_buf_p) = (yy_hold_char);
 
4028
 
 
4029
        if ( *(yy_c_buf_p) == YY_END_OF_BUFFER_CHAR )
 
4030
                {
 
4031
                /* yy_c_buf_p now points to the character we want to return.
 
4032
                 * If this occurs *before* the EOB characters, then it's a
 
4033
                 * valid NUL; if not, then we've hit the end of the buffer.
 
4034
                 */
 
4035
                if ( (yy_c_buf_p) < &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] )
 
4036
                        /* This was really a NUL. */
 
4037
                        *(yy_c_buf_p) = '\0';
 
4038
 
 
4039
                else
 
4040
                        { /* need more input */
 
4041
                        int offset = (yy_c_buf_p) - (yytext_ptr);
 
4042
                        ++(yy_c_buf_p);
 
4043
 
 
4044
                        switch ( yy_get_next_buffer(  ) )
 
4045
                                {
 
4046
                                case EOB_ACT_LAST_MATCH:
 
4047
                                        /* This happens because yy_g_n_b()
 
4048
                                         * sees that we've accumulated a
 
4049
                                         * token and flags that we need to
 
4050
                                         * try matching the token before
 
4051
                                         * proceeding.  But for input(),
 
4052
                                         * there's no matching to consider.
 
4053
                                         * So convert the EOB_ACT_LAST_MATCH
 
4054
                                         * to EOB_ACT_END_OF_FILE.
 
4055
                                         */
 
4056
 
 
4057
                                        /* Reset buffer status. */
 
4058
                                        Kmlrestart(Kmlin );
 
4059
 
 
4060
                                        /*FALLTHROUGH*/
 
4061
 
 
4062
                                case EOB_ACT_END_OF_FILE:
 
4063
                                        {
 
4064
                                        if ( Kmlwrap( ) )
 
4065
                                                return EOF;
 
4066
 
 
4067
                                        if ( ! (yy_did_buffer_switch_on_eof) )
 
4068
                                                YY_NEW_FILE;
 
4069
#ifdef __cplusplus
 
4070
                                        return yyinput();
 
4071
#else
 
4072
                                        return input();
 
4073
#endif
 
4074
                                        }
 
4075
 
 
4076
                                case EOB_ACT_CONTINUE_SCAN:
 
4077
                                        (yy_c_buf_p) = (yytext_ptr) + offset;
 
4078
                                        break;
 
4079
                                }
 
4080
                        }
 
4081
                }
 
4082
 
 
4083
        c = *(unsigned char *) (yy_c_buf_p);    /* cast for 8-bit char's */
 
4084
        *(yy_c_buf_p) = '\0';   /* preserve Kmltext */
 
4085
        (yy_hold_char) = *++(yy_c_buf_p);
 
4086
 
 
4087
        return c;
 
4088
}
 
4089
#endif  /* ifndef YY_NO_INPUT */
 
4090
 
 
4091
/** Immediately switch to a different input stream.
 
4092
 * @param input_file A readable stream.
 
4093
 * 
 
4094
 * @note This function does not reset the start condition to @c INITIAL .
 
4095
 */
 
4096
    void Kmlrestart  (FILE * input_file )
 
4097
{
 
4098
    
 
4099
        if ( ! YY_CURRENT_BUFFER ){
 
4100
        Kmlensure_buffer_stack ();
 
4101
                YY_CURRENT_BUFFER_LVALUE =
 
4102
            Kml_create_buffer(Kmlin,YY_BUF_SIZE );
 
4103
        }
 
4104
 
 
4105
        Kml_init_buffer(YY_CURRENT_BUFFER,input_file );
 
4106
        Kml_load_buffer_state( );
 
4107
}
 
4108
 
 
4109
/** Switch to a different input buffer.
 
4110
 * @param new_buffer The new input buffer.
 
4111
 * 
 
4112
 */
 
4113
    void Kml_switch_to_buffer  (YY_BUFFER_STATE  new_buffer )
 
4114
{
 
4115
    
 
4116
        /* TODO. We should be able to replace this entire function body
 
4117
         * with
 
4118
         *              Kmlpop_buffer_state();
 
4119
         *              Kmlpush_buffer_state(new_buffer);
 
4120
     */
 
4121
        Kmlensure_buffer_stack ();
 
4122
        if ( YY_CURRENT_BUFFER == new_buffer )
 
4123
                return;
 
4124
 
 
4125
        if ( YY_CURRENT_BUFFER )
 
4126
                {
 
4127
                /* Flush out information for old buffer. */
 
4128
                *(yy_c_buf_p) = (yy_hold_char);
 
4129
                YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p);
 
4130
                YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars);
 
4131
                }
 
4132
 
 
4133
        YY_CURRENT_BUFFER_LVALUE = new_buffer;
 
4134
        Kml_load_buffer_state( );
 
4135
 
 
4136
        /* We don't actually know whether we did this switch during
 
4137
         * EOF (Kmlwrap()) processing, but the only time this flag
 
4138
         * is looked at is after Kmlwrap() is called, so it's safe
 
4139
         * to go ahead and always set it.
 
4140
         */
 
4141
        (yy_did_buffer_switch_on_eof) = 1;
 
4142
}
 
4143
 
 
4144
static void Kml_load_buffer_state  (void)
 
4145
{
 
4146
        (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars;
 
4147
        (yytext_ptr) = (yy_c_buf_p) = YY_CURRENT_BUFFER_LVALUE->yy_buf_pos;
 
4148
        Kmlin = YY_CURRENT_BUFFER_LVALUE->yy_input_file;
 
4149
        (yy_hold_char) = *(yy_c_buf_p);
 
4150
}
 
4151
 
 
4152
/** Allocate and initialize an input buffer state.
 
4153
 * @param file A readable stream.
 
4154
 * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE.
 
4155
 * 
 
4156
 * @return the allocated buffer state.
 
4157
 */
 
4158
    YY_BUFFER_STATE Kml_create_buffer  (FILE * file, int  size )
 
4159
{
 
4160
        YY_BUFFER_STATE b;
 
4161
    
 
4162
        b = (YY_BUFFER_STATE) Kmlalloc(sizeof( struct yy_buffer_state )  );
 
4163
        if ( ! b )
 
4164
                YY_FATAL_ERROR( "out of dynamic memory in Kml_create_buffer()" );
 
4165
 
 
4166
        b->yy_buf_size = size;
 
4167
 
 
4168
        /* yy_ch_buf has to be 2 characters longer than the size given because
 
4169
         * we need to put in 2 end-of-buffer characters.
 
4170
         */
 
4171
        b->yy_ch_buf = (char *) Kmlalloc(b->yy_buf_size + 2  );
 
4172
        if ( ! b->yy_ch_buf )
 
4173
                YY_FATAL_ERROR( "out of dynamic memory in Kml_create_buffer()" );
 
4174
 
 
4175
        b->yy_is_our_buffer = 1;
 
4176
 
 
4177
        Kml_init_buffer(b,file );
 
4178
 
 
4179
        return b;
 
4180
}
 
4181
 
 
4182
/** Destroy the buffer.
 
4183
 * @param b a buffer created with Kml_create_buffer()
 
4184
 * 
 
4185
 */
 
4186
    void Kml_delete_buffer (YY_BUFFER_STATE  b )
 
4187
{
 
4188
    
 
4189
        if ( ! b )
 
4190
                return;
 
4191
 
 
4192
        if ( b == YY_CURRENT_BUFFER ) /* Not sure if we should pop here. */
 
4193
                YY_CURRENT_BUFFER_LVALUE = (YY_BUFFER_STATE) 0;
 
4194
 
 
4195
        if ( b->yy_is_our_buffer )
 
4196
                Kmlfree((void *) b->yy_ch_buf  );
 
4197
 
 
4198
        Kmlfree((void *) b  );
 
4199
}
 
4200
 
 
4201
#ifndef __cplusplus
 
4202
extern int isatty (int );
 
4203
#endif /* __cplusplus */
 
4204
    
 
4205
/* Initializes or reinitializes a buffer.
 
4206
 * This function is sometimes called more than once on the same buffer,
 
4207
 * such as during a Kmlrestart() or at EOF.
 
4208
 */
 
4209
    static void Kml_init_buffer  (YY_BUFFER_STATE  b, FILE * file )
 
4210
 
 
4211
{
 
4212
        int oerrno = errno;
 
4213
    
 
4214
        Kml_flush_buffer(b );
 
4215
 
 
4216
        b->yy_input_file = file;
 
4217
        b->yy_fill_buffer = 1;
 
4218
 
 
4219
    /* If b is the current buffer, then Kml_init_buffer was _probably_
 
4220
     * called from Kmlrestart() or through yy_get_next_buffer.
 
4221
     * In that case, we don't want to reset the lineno or column.
 
4222
     */
 
4223
    if (b != YY_CURRENT_BUFFER){
 
4224
        b->yy_bs_lineno = 1;
 
4225
        b->yy_bs_column = 0;
 
4226
    }
 
4227
 
 
4228
        b->yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0;
 
4229
    
 
4230
        errno = oerrno;
 
4231
}
 
4232
 
 
4233
/** Discard all buffered characters. On the next scan, YY_INPUT will be called.
 
4234
 * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER.
 
4235
 * 
 
4236
 */
 
4237
    void Kml_flush_buffer (YY_BUFFER_STATE  b )
 
4238
{
 
4239
        if ( ! b )
 
4240
                return;
 
4241
 
 
4242
        b->yy_n_chars = 0;
 
4243
 
 
4244
        /* We always need two end-of-buffer characters.  The first causes
 
4245
         * a transition to the end-of-buffer state.  The second causes
 
4246
         * a jam in that state.
 
4247
         */
 
4248
        b->yy_ch_buf[0] = YY_END_OF_BUFFER_CHAR;
 
4249
        b->yy_ch_buf[1] = YY_END_OF_BUFFER_CHAR;
 
4250
 
 
4251
        b->yy_buf_pos = &b->yy_ch_buf[0];
 
4252
 
 
4253
        b->yy_at_bol = 1;
 
4254
        b->yy_buffer_status = YY_BUFFER_NEW;
 
4255
 
 
4256
        if ( b == YY_CURRENT_BUFFER )
 
4257
                Kml_load_buffer_state( );
 
4258
}
 
4259
 
 
4260
/** Pushes the new state onto the stack. The new state becomes
 
4261
 *  the current state. This function will allocate the stack
 
4262
 *  if necessary.
 
4263
 *  @param new_buffer The new state.
 
4264
 *  
 
4265
 */
 
4266
void Kmlpush_buffer_state (YY_BUFFER_STATE new_buffer )
 
4267
{
 
4268
        if (new_buffer == NULL)
 
4269
                return;
 
4270
 
 
4271
        Kmlensure_buffer_stack();
 
4272
 
 
4273
        /* This block is copied from Kml_switch_to_buffer. */
 
4274
        if ( YY_CURRENT_BUFFER )
 
4275
                {
 
4276
                /* Flush out information for old buffer. */
 
4277
                *(yy_c_buf_p) = (yy_hold_char);
 
4278
                YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p);
 
4279
                YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars);
 
4280
                }
 
4281
 
 
4282
        /* Only push if top exists. Otherwise, replace top. */
 
4283
        if (YY_CURRENT_BUFFER)
 
4284
                (yy_buffer_stack_top)++;
 
4285
        YY_CURRENT_BUFFER_LVALUE = new_buffer;
 
4286
 
 
4287
        /* copied from Kml_switch_to_buffer. */
 
4288
        Kml_load_buffer_state( );
 
4289
        (yy_did_buffer_switch_on_eof) = 1;
 
4290
}
 
4291
 
 
4292
/** Removes and deletes the top of the stack, if present.
 
4293
 *  The next element becomes the new top.
 
4294
 *  
 
4295
 */
 
4296
void Kmlpop_buffer_state (void)
 
4297
{
 
4298
        if (!YY_CURRENT_BUFFER)
 
4299
                return;
 
4300
 
 
4301
        Kml_delete_buffer(YY_CURRENT_BUFFER );
 
4302
        YY_CURRENT_BUFFER_LVALUE = NULL;
 
4303
        if ((yy_buffer_stack_top) > 0)
 
4304
                --(yy_buffer_stack_top);
 
4305
 
 
4306
        if (YY_CURRENT_BUFFER) {
 
4307
                Kml_load_buffer_state( );
 
4308
                (yy_did_buffer_switch_on_eof) = 1;
 
4309
        }
 
4310
}
 
4311
 
 
4312
/* Allocates the stack if it does not exist.
 
4313
 *  Guarantees space for at least one push.
 
4314
 */
 
4315
static void Kmlensure_buffer_stack (void)
 
4316
{
 
4317
        int num_to_alloc;
 
4318
    
 
4319
        if (!(yy_buffer_stack)) {
 
4320
 
 
4321
                /* First allocation is just for 2 elements, since we don't know if this
 
4322
                 * scanner will even need a stack. We use 2 instead of 1 to avoid an
 
4323
                 * immediate realloc on the next call.
 
4324
         */
 
4325
                num_to_alloc = 1;
 
4326
                (yy_buffer_stack) = (struct yy_buffer_state**)Kmlalloc
 
4327
                                                                (num_to_alloc * sizeof(struct yy_buffer_state*)
 
4328
                                                                );
 
4329
                if ( ! (yy_buffer_stack) )
 
4330
                        YY_FATAL_ERROR( "out of dynamic memory in Kmlensure_buffer_stack()" );
 
4331
                                                                  
 
4332
                memset((yy_buffer_stack), 0, num_to_alloc * sizeof(struct yy_buffer_state*));
 
4333
                                
 
4334
                (yy_buffer_stack_max) = num_to_alloc;
 
4335
                (yy_buffer_stack_top) = 0;
 
4336
                return;
 
4337
        }
 
4338
 
 
4339
        if ((yy_buffer_stack_top) >= ((yy_buffer_stack_max)) - 1){
 
4340
 
 
4341
                /* Increase the buffer to prepare for a possible push. */
 
4342
                int grow_size = 8 /* arbitrary grow size */;
 
4343
 
 
4344
                num_to_alloc = (yy_buffer_stack_max) + grow_size;
 
4345
                (yy_buffer_stack) = (struct yy_buffer_state**)Kmlrealloc
 
4346
                                                                ((yy_buffer_stack),
 
4347
                                                                num_to_alloc * sizeof(struct yy_buffer_state*)
 
4348
                                                                );
 
4349
                if ( ! (yy_buffer_stack) )
 
4350
                        YY_FATAL_ERROR( "out of dynamic memory in Kmlensure_buffer_stack()" );
 
4351
 
 
4352
                /* zero only the new slots.*/
 
4353
                memset((yy_buffer_stack) + (yy_buffer_stack_max), 0, grow_size * sizeof(struct yy_buffer_state*));
 
4354
                (yy_buffer_stack_max) = num_to_alloc;
 
4355
        }
 
4356
}
 
4357
 
 
4358
/** Setup the input buffer state to scan directly from a user-specified character buffer.
 
4359
 * @param base the character buffer
 
4360
 * @param size the size in bytes of the character buffer
 
4361
 * 
 
4362
 * @return the newly allocated buffer state object. 
 
4363
 */
 
4364
YY_BUFFER_STATE Kml_scan_buffer  (char * base, yy_size_t  size )
 
4365
{
 
4366
        YY_BUFFER_STATE b;
 
4367
    
 
4368
        if ( size < 2 ||
 
4369
             base[size-2] != YY_END_OF_BUFFER_CHAR ||
 
4370
             base[size-1] != YY_END_OF_BUFFER_CHAR )
 
4371
                /* They forgot to leave room for the EOB's. */
 
4372
                return 0;
 
4373
 
 
4374
        b = (YY_BUFFER_STATE) Kmlalloc(sizeof( struct yy_buffer_state )  );
 
4375
        if ( ! b )
 
4376
                YY_FATAL_ERROR( "out of dynamic memory in Kml_scan_buffer()" );
 
4377
 
 
4378
        b->yy_buf_size = size - 2;      /* "- 2" to take care of EOB's */
 
4379
        b->yy_buf_pos = b->yy_ch_buf = base;
 
4380
        b->yy_is_our_buffer = 0;
 
4381
        b->yy_input_file = 0;
 
4382
        b->yy_n_chars = b->yy_buf_size;
 
4383
        b->yy_is_interactive = 0;
 
4384
        b->yy_at_bol = 1;
 
4385
        b->yy_fill_buffer = 0;
 
4386
        b->yy_buffer_status = YY_BUFFER_NEW;
 
4387
 
 
4388
        Kml_switch_to_buffer(b  );
 
4389
 
 
4390
        return b;
 
4391
}
 
4392
 
 
4393
/** Setup the input buffer state to scan a string. The next call to Kmllex() will
 
4394
 * scan from a @e copy of @a str.
 
4395
 * @param yystr a NUL-terminated string to scan
 
4396
 * 
 
4397
 * @return the newly allocated buffer state object.
 
4398
 * @note If you want to scan bytes that may contain NUL values, then use
 
4399
 *       Kml_scan_bytes() instead.
 
4400
 */
 
4401
YY_BUFFER_STATE Kml_scan_string (yyconst char * yystr )
 
4402
{
 
4403
    
 
4404
        return Kml_scan_bytes(yystr,strlen(yystr) );
 
4405
}
 
4406
 
 
4407
/** Setup the input buffer state to scan the given bytes. The next call to Kmllex() will
 
4408
 * scan from a @e copy of @a bytes.
 
4409
 * @param yybytes the byte buffer to scan
 
4410
 * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes.
 
4411
 * 
 
4412
 * @return the newly allocated buffer state object.
 
4413
 */
 
4414
YY_BUFFER_STATE Kml_scan_bytes  (yyconst char * yybytes, int  _yybytes_len )
 
4415
{
 
4416
        YY_BUFFER_STATE b;
 
4417
        char *buf;
 
4418
        yy_size_t n;
 
4419
        int i;
 
4420
    
 
4421
        /* Get memory for full buffer, including space for trailing EOB's. */
 
4422
        n = _yybytes_len + 2;
 
4423
        buf = (char *) Kmlalloc(n  );
 
4424
        if ( ! buf )
 
4425
                YY_FATAL_ERROR( "out of dynamic memory in Kml_scan_bytes()" );
 
4426
 
 
4427
        for ( i = 0; i < _yybytes_len; ++i )
 
4428
                buf[i] = yybytes[i];
 
4429
 
 
4430
        buf[_yybytes_len] = buf[_yybytes_len+1] = YY_END_OF_BUFFER_CHAR;
 
4431
 
 
4432
        b = Kml_scan_buffer(buf,n );
 
4433
        if ( ! b )
 
4434
                YY_FATAL_ERROR( "bad buffer in Kml_scan_bytes()" );
 
4435
 
 
4436
        /* It's okay to grow etc. this buffer, and we should throw it
 
4437
         * away when we're done.
 
4438
         */
 
4439
        b->yy_is_our_buffer = 1;
 
4440
 
 
4441
        return b;
 
4442
}
 
4443
 
 
4444
#ifndef YY_EXIT_FAILURE
 
4445
#define YY_EXIT_FAILURE 2
 
4446
#endif
 
4447
 
 
4448
static void yy_fatal_error (yyconst char* msg )
 
4449
{
 
4450
        (void) fprintf( stderr, "%s\n", msg );
 
4451
        exit( YY_EXIT_FAILURE );
 
4452
}
 
4453
 
 
4454
/* Redefine yyless() so it works in section 3 code. */
 
4455
 
 
4456
#undef yyless
 
4457
#define yyless(n) \
 
4458
        do \
 
4459
                { \
 
4460
                /* Undo effects of setting up Kmltext. */ \
 
4461
        int yyless_macro_arg = (n); \
 
4462
        YY_LESS_LINENO(yyless_macro_arg);\
 
4463
                Kmltext[Kmlleng] = (yy_hold_char); \
 
4464
                (yy_c_buf_p) = Kmltext + yyless_macro_arg; \
 
4465
                (yy_hold_char) = *(yy_c_buf_p); \
 
4466
                *(yy_c_buf_p) = '\0'; \
 
4467
                Kmlleng = yyless_macro_arg; \
 
4468
                } \
 
4469
        while ( 0 )
 
4470
 
 
4471
/* Accessor  methods (get/set functions) to struct members. */
 
4472
 
 
4473
/** Get the current line number.
 
4474
 * 
 
4475
 */
 
4476
int Kmlget_lineno  (void)
 
4477
{
 
4478
        
 
4479
    return Kmllineno;
 
4480
}
 
4481
 
 
4482
/** Get the input stream.
 
4483
 * 
 
4484
 */
 
4485
FILE *Kmlget_in  (void)
 
4486
{
 
4487
        return Kmlin;
 
4488
}
 
4489
 
 
4490
/** Get the output stream.
 
4491
 * 
 
4492
 */
 
4493
FILE *Kmlget_out  (void)
 
4494
{
 
4495
        return Kmlout;
 
4496
}
 
4497
 
 
4498
/** Get the length of the current token.
 
4499
 * 
 
4500
 */
 
4501
int Kmlget_leng  (void)
 
4502
{
 
4503
        return Kmlleng;
 
4504
}
 
4505
 
 
4506
/** Get the current token.
 
4507
 * 
 
4508
 */
 
4509
 
 
4510
char *Kmlget_text  (void)
 
4511
{
 
4512
        return Kmltext;
 
4513
}
 
4514
 
 
4515
/** Set the current line number.
 
4516
 * @param line_number
 
4517
 * 
 
4518
 */
 
4519
void Kmlset_lineno (int  line_number )
 
4520
{
 
4521
    
 
4522
    Kmllineno = line_number;
 
4523
}
 
4524
 
 
4525
/** Set the input stream. This does not discard the current
 
4526
 * input buffer.
 
4527
 * @param in_str A readable stream.
 
4528
 * 
 
4529
 * @see Kml_switch_to_buffer
 
4530
 */
 
4531
void Kmlset_in (FILE *  in_str )
 
4532
{
 
4533
        Kmlin = in_str ;
 
4534
}
 
4535
 
 
4536
void Kmlset_out (FILE *  out_str )
 
4537
{
 
4538
        Kmlout = out_str ;
 
4539
}
 
4540
 
 
4541
int Kmlget_debug  (void)
 
4542
{
 
4543
        return Kml_flex_debug;
 
4544
}
 
4545
 
 
4546
void Kmlset_debug (int  bdebug )
 
4547
{
 
4548
        Kml_flex_debug = bdebug ;
 
4549
}
 
4550
 
 
4551
static int yy_init_globals (void)
 
4552
{
 
4553
        /* Initialization is the same as for the non-reentrant scanner.
 
4554
     * This function is called from Kmllex_destroy(), so don't allocate here.
 
4555
     */
 
4556
 
 
4557
    (yy_buffer_stack) = 0;
 
4558
    (yy_buffer_stack_top) = 0;
 
4559
    (yy_buffer_stack_max) = 0;
 
4560
    (yy_c_buf_p) = (char *) 0;
 
4561
    (yy_init) = 0;
 
4562
    (yy_start) = 0;
 
4563
 
 
4564
/* Defined in main.c */
 
4565
#ifdef YY_STDINIT
 
4566
    Kmlin = stdin;
 
4567
    Kmlout = stdout;
 
4568
#else
 
4569
    Kmlin = (FILE *) 0;
 
4570
    Kmlout = (FILE *) 0;
 
4571
#endif
 
4572
 
 
4573
    /* For future reference: Set errno on error, since we are called by
 
4574
     * Kmllex_init()
 
4575
     */
 
4576
    return 0;
 
4577
}
 
4578
 
 
4579
/* Kmllex_destroy is for both reentrant and non-reentrant scanners. */
 
4580
int Kmllex_destroy  (void)
 
4581
{
 
4582
    
 
4583
    /* Pop the buffer stack, destroying each element. */
 
4584
        while(YY_CURRENT_BUFFER){
 
4585
                Kml_delete_buffer(YY_CURRENT_BUFFER  );
 
4586
                YY_CURRENT_BUFFER_LVALUE = NULL;
 
4587
                Kmlpop_buffer_state();
 
4588
        }
 
4589
 
 
4590
        /* Destroy the stack itself. */
 
4591
        Kmlfree((yy_buffer_stack) );
 
4592
        (yy_buffer_stack) = NULL;
 
4593
 
 
4594
    /* Reset the globals. This is important in a non-reentrant scanner so the next time
 
4595
     * Kmllex() is called, initialization will occur. */
 
4596
    yy_init_globals( );
 
4597
 
 
4598
    return 0;
 
4599
}
 
4600
 
 
4601
/*
 
4602
 * Internal utility routines.
 
4603
 */
 
4604
 
 
4605
#ifndef yytext_ptr
 
4606
static void yy_flex_strncpy (char* s1, yyconst char * s2, int n )
 
4607
{
 
4608
        register int i;
 
4609
        for ( i = 0; i < n; ++i )
 
4610
                s1[i] = s2[i];
 
4611
}
 
4612
#endif
 
4613
 
 
4614
#ifdef YY_NEED_STRLEN
 
4615
static int yy_flex_strlen (yyconst char * s )
 
4616
{
 
4617
        register int n;
 
4618
        for ( n = 0; s[n]; ++n )
 
4619
                ;
 
4620
 
 
4621
        return n;
 
4622
}
 
4623
#endif
 
4624
 
 
4625
void *Kmlalloc (yy_size_t  size )
 
4626
{
 
4627
        return (void *) malloc( size );
 
4628
}
 
4629
 
 
4630
void *Kmlrealloc  (void * ptr, yy_size_t  size )
 
4631
{
 
4632
        /* The cast to (char *) in the following accommodates both
 
4633
         * implementations that use char* generic pointers, and those
 
4634
         * that use void* generic pointers.  It works with the latter
 
4635
         * because both ANSI C and C++ allow castless assignment from
 
4636
         * any pointer type to void*, and deal with argument conversions
 
4637
         * as though doing an assignment.
 
4638
         */
 
4639
        return (void *) realloc( (char *) ptr, size );
 
4640
}
 
4641
 
 
4642
void Kmlfree (void * ptr )
 
4643
{
 
4644
        free( (char *) ptr );   /* see Kmlrealloc() for (char *) cast */
 
4645
}
 
4646
 
 
4647
#define YYTABLES_NAME "yytables"
 
4648
 
 
4649
/**
 
4650
 * reset the line and column count
 
4651
 *
 
4652
 *
 
4653
 */
 
4654
void kml_reset_lexer(void)
 
4655
{
 
4656
 
 
4657
  kml_line = 1;
 
4658
  kml_col  = 1;
 
4659
 
 
4660
}
 
4661
 
 
4662
/**
 
4663
 * kmlError() is invoked when the lexer or the parser encounter
 
4664
 * an error. The error message is passed via *s
 
4665
 *
 
4666
 *
 
4667
 */
 
4668
void KmlError(char *s)
 
4669
{
 
4670
  printf("error: %s at line: %d col: %d\n",s,kml_line,kml_col);
 
4671
 
 
4672
}
 
4673
 
 
4674
int Kmlwrap(void)
 
4675
{
 
4676
  return 1;
 
4677
}
 
4678
 
 
4679
 
 
4680
/* 
 
4681
 KML_FLEX_END - FLEX generated code ends here 
 
4682
*/
 
4683
 
 
4684
 
 
4685
 
 
4686
gaiaGeomCollPtr
 
4687
gaiaParseKml (const unsigned char *dirty_buffer)
 
4688
{
 
4689
    void *pParser = ParseAlloc (malloc);
 
4690
    /* Linked-list of token values */
 
4691
    kmlFlexToken *tokens = malloc (sizeof (kmlFlexToken));
 
4692
    /* Pointer to the head of the list */
 
4693
    kmlFlexToken *head = tokens;
 
4694
    int yv;
 
4695
    kmlNodePtr result = NULL;
 
4696
    gaiaGeomCollPtr geom = NULL;
 
4697
 
 
4698
    KmlLval.pval = NULL;
 
4699
    tokens->value = NULL;
 
4700
    tokens->Next = NULL;
 
4701
    kml_parse_error = 0;
 
4702
    Kml_scan_string ((char *) dirty_buffer);
 
4703
 
 
4704
    /*
 
4705
       / Keep tokenizing until we reach the end
 
4706
       / yylex() will return the next matching Token for us.
 
4707
     */
 
4708
    while ((yv = yylex ()) != 0)
 
4709
      {
 
4710
          if (yv == -1)
 
4711
            {
 
4712
                kml_parse_error = 1;
 
4713
                break;
 
4714
            }
 
4715
          tokens->Next = malloc (sizeof (kmlFlexToken));
 
4716
          tokens->Next->Next = NULL;
 
4717
          /*
 
4718
             /KmlLval is a global variable from FLEX.
 
4719
             /KmlLval is defined in kmlLexglobal.h
 
4720
           */
 
4721
          kml_xferString (&(tokens->Next->value), KmlLval.pval);
 
4722
          /* Pass the token to the wkt parser created from lemon */
 
4723
          Parse (pParser, yv, &(tokens->Next->value), &result);
 
4724
          tokens = tokens->Next;
 
4725
      }
 
4726
    /* This denotes the end of a line as well as the end of the parser */
 
4727
    Parse (pParser, KML_NEWLINE, 0, &result);
 
4728
    ParseFree (pParser, free);
 
4729
    Kmllex_destroy ();
 
4730
 
 
4731
    /* Assigning the token as the end to avoid seg faults while cleaning */
 
4732
    tokens->Next = NULL;
 
4733
    kml_cleanup (head);
 
4734
    kml_freeString (&(KmlLval.pval));
 
4735
 
 
4736
    if (kml_parse_error)
 
4737
      {
 
4738
          if (result)
 
4739
              kml_freeTree (result);
 
4740
          return NULL;
 
4741
      }
 
4742
 
 
4743
    /* attempting to build a geometry from KML */
 
4744
    geom = kml_build_geometry (result);
 
4745
    geom->Srid = 4326;
 
4746
    kml_freeTree (result);
 
4747
    return geom;
 
4748
}
 
4749
 
 
4750
 
 
4751
/*
 
4752
** CAVEAT: we must now undefine any Lemon/Flex own macro
 
4753
*/
 
4754
#undef YYNOCODE
 
4755
#undef YYNSTATE
 
4756
#undef YYNRULE
 
4757
#undef YY_SHIFT_MAX
 
4758
#undef YY_REDUCE_USE_DFLT
 
4759
#undef YY_REDUCE_MAX
 
4760
#undef YY_FLUSH_BUFFER
 
4761
#undef YY_DO_BEFORE_ACTION
 
4762
#undef YY_NUM_RULES
 
4763
#undef YY_END_OF_BUFFER
 
4764
#undef YY_END_FILE
 
4765
#undef YYACTIONTYPE
 
4766
#undef YY_SZ_ACTTAB
 
4767
#undef YY_NEW_FILE
 
4768
#undef BEGIN
 
4769
#undef YY_START
 
4770
#undef YY_CURRENT_BUFFER
 
4771
#undef YY_CURRENT_BUFFER_LVALUE
 
4772
#undef YY_STATE_BUF_SIZE
 
4773
#undef YY_DECL
 
4774
#undef YY_FATAL_ERROR
 
4775
#undef YYMINORTYPE
 
4776
#undef YY_CHAR
 
4777
#undef YYSTYPE
 
4778
#undef input
 
4779
#undef ParseAlloc
 
4780
#undef ParseFree
 
4781
#undef ParseStackPeak
 
4782
#undef Parse
 
4783
#undef yyalloc
 
4784
#undef yyfree
 
4785
#undef yyin
 
4786
#undef yyleng
 
4787
#undef yyless
 
4788
#undef yylex
 
4789
#undef yylineno
 
4790
#undef yyout
 
4791
#undef yyrealloc
 
4792
#undef yyrestart
 
4793
#undef yyStackEntry
 
4794
#undef yytext
 
4795
#undef yywrap
 
4796
#undef yyzerominor
 
4797
#undef yy_accept
 
4798
#undef yy_action
 
4799
#undef yy_base
 
4800
#undef yy_buffer_stack
 
4801
#undef yy_buffer_stack_max
 
4802
#undef yy_buffer_stack_top
 
4803
#undef yy_c_buf_p
 
4804
#undef yy_chk
 
4805
#undef yy_create_buffer
 
4806
#undef yy_def
 
4807
#undef yy_default
 
4808
#undef yy_delete_buffer
 
4809
#undef yy_destructor
 
4810
#undef yy_ec
 
4811
#undef yy_fatal_error
 
4812
#undef yy_find_reduce_action
 
4813
#undef yy_find_shift_action
 
4814
#undef yy_flex_debug
 
4815
#undef yy_flush_buffer
 
4816
#undef yy_get_next_buffer
 
4817
#undef yy_get_previous_state
 
4818
#undef yy_init
 
4819
#undef yy_init_buffer
 
4820
#undef yy_init_globals
 
4821
#undef yy_load_buffer
 
4822
#undef yy_load_buffer_state
 
4823
#undef yy_lookahead
 
4824
#undef yy_meta
 
4825
#undef yy_new_buffer
 
4826
#undef yy_nxt
 
4827
#undef yy_parse_failed
 
4828
#undef yy_pop_parser_stack
 
4829
#undef yy_reduce
 
4830
#undef yy_reduce_ofst
 
4831
#undef yy_set_bol
 
4832
#undef yy_set_interactive
 
4833
#undef yy_shift
 
4834
#undef yy_shift_ofst
 
4835
#undef yy_start
 
4836
#undef yy_state_type
 
4837
#undef yy_switch_to_buffer
 
4838
#undef yy_syntax_error
 
4839
#undef yy_trans_info
 
4840
#undef yy_try_NUL_trans
 
4841
#undef yyParser
 
4842
#undef yyStackEntry
 
4843
#undef yyStackOverflow
 
4844
#undef yyRuleInfo
 
4845
#undef yytext_ptr
 
4846
#undef yyunput
 
4847
#undef yyzerominor
 
4848
#undef ParseARG_SDECL
 
4849
#undef ParseARG_PDECL
 
4850
#undef ParseARG_FETCH
 
4851
#undef ParseARG_STORE
 
4852
#undef REJECT
 
4853
#undef yymore
 
4854
#undef YY_MORE_ADJ
 
4855
#undef YY_RESTORE_YY_MORE_OFFSET
 
4856
#undef YY_LESS_LINENO
 
4857
#undef yyTracePrompt
 
4858
#undef yyTraceFILE
 
4859
#undef yyTokenName
 
4860
#undef yyRuleName
 
4861
#undef ParseTrace