Routino SVN Repository Browser

Check out the latest version of Routino: svn co http://routino.org/svn/trunk routino

ViewVC logotype

Annotation of /trunk/src/waysx.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1135 - (hide annotations) (download) (as text)
Sat Nov 10 14:38:28 2012 UTC (12 years, 4 months ago) by amb
File MIME type: text/x-csrc
File size: 17971 byte(s)
Don't index the ways in the first sorting, but wait until after de-duplicating.

1 amb 110 /***************************************
2     Extended Way data type functions.
3 amb 151
4     Part of the Routino routing software.
5 amb 110 ******************/ /******************
6 amb 948 This file Copyright 2008-2012 Andrew M. Bishop
7 amb 110
8 amb 151 This program is free software: you can redistribute it and/or modify
9     it under the terms of the GNU Affero General Public License as published by
10     the Free Software Foundation, either version 3 of the License, or
11     (at your option) any later version.
12    
13     This program is distributed in the hope that it will be useful,
14     but WITHOUT ANY WARRANTY; without even the implied warranty of
15     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16     GNU Affero General Public License for more details.
17    
18     You should have received a copy of the GNU Affero General Public License
19     along with this program. If not, see <http://www.gnu.org/licenses/>.
20 amb 110 ***************************************/
21    
22    
23     #include <assert.h>
24     #include <stdlib.h>
25     #include <string.h>
26    
27 amb 955 #include "types.h"
28 amb 228 #include "ways.h"
29 amb 110
30 amb 955 #include "typesx.h"
31 amb 1092 #include "segmentsx.h"
32 amb 449 #include "waysx.h"
33 amb 110
34 amb 449 #include "files.h"
35 amb 519 #include "logging.h"
36 amb 532 #include "sorting.h"
37 amb 449
38    
39 amb 680 /* Global variables */
40 amb 110
41 amb 289 /*+ The command line '--tmpdir' option or its default value. +*/
42 amb 284 extern char *option_tmpdirname;
43 amb 110
44 amb 680 /* Local variables */
45    
46 amb 1094 /*+ Temporary file-local variables for use by the sort functions. +*/
47 amb 284 static WaysX *sortwaysx;
48 amb 1100 static SegmentsX *sortsegmentsx;
49 amb 284
50 amb 1100 /* Local functions */
51 amb 680
52 amb 499 static int sort_by_id(WayX *a,WayX *b);
53 amb 1129 static int sort_by_name(WayX *a,WayX *b);
54 amb 310 static int sort_by_name_and_prop_and_id(WayX *a,WayX *b);
55    
56 amb 1114 static int delete_unused(WayX *wayx,index_t index);
57 amb 1135 static int deduplicate_by_id(WayX *wayx,index_t index);
58     static int index_by_id(WayX *wayx,index_t index);
59 amb 1094 static int deduplicate_and_index_by_compact_id(WayX *wayx,index_t index);
60 amb 272
61 amb 110
62     /*++++++++++++++++++++++++++++++++++++++
63 amb 326 Allocate a new way list (create a new file or open an existing one).
64 amb 110
65     WaysX *NewWayList Returns the way list.
66 amb 326
67 amb 1123 int append Set to 1 if the file is to be opened for appending.
68    
69     int readonly Set to 1 if the file is not to be opened.
70 amb 110 ++++++++++++++++++++++++++++++++++++++*/
71    
72 amb 1123 WaysX *NewWayList(int append,int readonly)
73 amb 110 {
74     WaysX *waysx;
75    
76 amb 213 waysx=(WaysX*)calloc(1,sizeof(WaysX));
77 amb 110
78 amb 243 assert(waysx); /* Check calloc() worked */
79    
80 amb 1120 waysx->filename =(char*)malloc(strlen(option_tmpdirname)+32);
81     waysx->filename_tmp=(char*)malloc(strlen(option_tmpdirname)+32);
82 amb 216
83 amb 1120 sprintf(waysx->filename ,"%s/waysx.parsed.mem",option_tmpdirname);
84     sprintf(waysx->filename_tmp,"%s/waysx.%p.tmp" ,option_tmpdirname,(void*)waysx);
85 amb 262
86 amb 1123 if(append || readonly)
87     if(ExistsFile(waysx->filename))
88     {
89     off_t size,position=0;
90     int fd;
91 amb 326
92 amb 1123 size=SizeFile(waysx->filename);
93 amb 326
94 amb 1123 fd=ReOpenFile(waysx->filename);
95 amb 326
96 amb 1123 while(position<size)
97     {
98     FILESORT_VARINT waysize;
99 amb 326
100 amb 1123 SeekReadFile(fd,&waysize,FILESORT_VARSIZE,position);
101 amb 326
102 amb 1123 waysx->number++;
103     position+=waysize+FILESORT_VARSIZE;
104     }
105    
106     CloseFile(fd);
107 amb 326 }
108    
109 amb 1123 if(append)
110     waysx->fd=OpenFileAppend(waysx->filename);
111     else if(!readonly)
112     waysx->fd=OpenFileNew(waysx->filename);
113 amb 326 else
114 amb 1123 waysx->fd=-1;
115 amb 326
116 amb 262
117 amb 1120 waysx->nfilename_tmp=(char*)malloc(strlen(option_tmpdirname)+32);
118    
119     sprintf(waysx->nfilename_tmp,"%s/waynames.%p.tmp",option_tmpdirname,(void*)waysx);
120    
121 amb 110 return(waysx);
122     }
123    
124    
125     /*++++++++++++++++++++++++++++++++++++++
126 amb 226 Free a way list.
127    
128 amb 681 WaysX *waysx The set of ways to be freed.
129 amb 326
130 amb 680 int keep Set to 1 if the file is to be kept (for appending later).
131 amb 226 ++++++++++++++++++++++++++++++++++++++*/
132    
133 amb 326 void FreeWayList(WaysX *waysx,int keep)
134 amb 226 {
135 amb 326 if(!keep)
136     DeleteFile(waysx->filename);
137    
138 amb 1120 DeleteFile(waysx->filename_tmp);
139    
140 amb 283 free(waysx->filename);
141 amb 1120 free(waysx->filename_tmp);
142 amb 262
143 amb 226 if(waysx->idata)
144     free(waysx->idata);
145    
146 amb 1093 if(waysx->cdata)
147     free(waysx->cdata);
148    
149 amb 1120 DeleteFile(waysx->nfilename_tmp);
150 amb 326
151 amb 1120 free(waysx->nfilename_tmp);
152 amb 226
153     free(waysx);
154     }
155    
156    
157     /*++++++++++++++++++++++++++++++++++++++
158 amb 493 Append a single way to an unsorted way list.
159 amb 203
160 amb 682 WaysX *waysx The set of ways to process.
161 amb 110
162 amb 262 way_t id The ID of the way.
163 amb 110
164 amb 262 Way *way The way data itself.
165 amb 110
166 amb 262 const char *name The name or reference of the way.
167     ++++++++++++++++++++++++++++++++++++++*/
168 amb 110
169 amb 682 void AppendWay(WaysX *waysx,way_t id,Way *way,const char *name)
170 amb 262 {
171     WayX wayx;
172 amb 311 FILESORT_VARINT size;
173 amb 110
174 amb 262 wayx.id=id;
175     wayx.way=*way;
176    
177 amb 310 size=sizeof(WayX)+strlen(name)+1;
178    
179 amb 311 WriteFile(waysx->fd,&size,FILESORT_VARSIZE);
180 amb 262 WriteFile(waysx->fd,&wayx,sizeof(WayX));
181 amb 310 WriteFile(waysx->fd,name,strlen(name)+1);
182 amb 262
183 amb 650 waysx->number++;
184 amb 466
185 amb 1065 assert(waysx->number!=0); /* Zero marks the high-water mark for ways. */
186 amb 110 }
187    
188    
189     /*++++++++++++++++++++++++++++++++++++++
190 amb 1120 Finish appending ways and change the filename over.
191    
192     WaysX *waysx The ways that have been appended.
193     ++++++++++++++++++++++++++++++++++++++*/
194    
195     void FinishWayList(WaysX *waysx)
196     {
197     /* Close the file (finished appending) */
198    
199     waysx->fd=CloseFile(waysx->fd);
200    
201     /* Rename the file to the temporary name (used everywhere else) */
202    
203     RenameFile(waysx->filename,waysx->filename_tmp);
204     }
205    
206    
207     /*++++++++++++++++++++++++++++++++++++++
208 amb 224 Sort the list of ways.
209 amb 110
210 amb 682 WaysX *waysx The set of ways to process.
211 amb 110 ++++++++++++++++++++++++++++++++++++++*/
212    
213 amb 682 void SortWayList(WaysX *waysx)
214 amb 110 {
215 amb 1129 index_t xnumber;
216 amb 555 int fd;
217 amb 1129
218     /* Print the start message */
219    
220     printf_first("Sorting Ways");
221    
222     /* Re-open the file read-only and a new file writeable */
223    
224     waysx->fd=ReOpenFile(waysx->filename_tmp);
225    
226     DeleteFile(waysx->filename_tmp);
227    
228     fd=OpenFileNew(waysx->filename_tmp);
229    
230     /* Sort the ways by ID and index them */
231    
232     xnumber=waysx->number;
233    
234     waysx->number=filesort_vary(waysx->fd,fd,NULL,
235     (int (*)(const void*,const void*))sort_by_id,
236 amb 1135 (int (*)(void*,index_t))deduplicate_by_id);
237 amb 1129
238     /* Close the files */
239    
240     waysx->fd=CloseFile(waysx->fd);
241     CloseFile(fd);
242    
243     /* Print the final message */
244    
245     printf_last("Sorted Ways: Ways=%"Pindex_t" Duplicates=%"Pindex_t,xnumber,xnumber-waysx->number);
246     }
247    
248    
249     /*++++++++++++++++++++++++++++++++++++++
250     Extract the way names from the ways and reference the list of names from the ways.
251    
252     WaysX *waysx The set of ways to process.
253     ++++++++++++++++++++++++++++++++++++++*/
254    
255     void ExtractWayNames(WaysX *waysx)
256     {
257     index_t i;
258     int fd;
259 amb 310 char *names[2]={NULL,NULL};
260     int namelen[2]={0,0};
261 amb 499 int nnames=0;
262 amb 310 uint32_t lastlength=0;
263 amb 110
264 amb 266 /* Print the start message */
265    
266 amb 519 printf_first("Sorting Ways by Name");
267 amb 110
268 amb 555 /* Re-open the file read-only and a new file writeable */
269    
270 amb 1120 waysx->fd=ReOpenFile(waysx->filename_tmp);
271 amb 216
272 amb 1120 DeleteFile(waysx->filename_tmp);
273 amb 262
274 amb 1120 fd=OpenFileNew(waysx->filename_tmp);
275 amb 310
276 amb 499 /* Sort the ways to allow separating the names */
277 amb 310
278 amb 1106 filesort_vary(waysx->fd,fd,NULL,
279 amb 1129 (int (*)(const void*,const void*))sort_by_name,
280 amb 1106 NULL);
281 amb 310
282     /* Close the files */
283    
284 amb 612 waysx->fd=CloseFile(waysx->fd);
285 amb 310 CloseFile(fd);
286    
287     /* Print the final message */
288    
289 amb 790 printf_last("Sorted Ways by Name: Ways=%"Pindex_t,waysx->number);
290 amb 310
291    
292     /* Print the start message */
293    
294 amb 519 printf_first("Separating Way Names: Ways=0 Names=0");
295 amb 310
296 amb 555 /* Re-open the file read-only and new files writeable */
297 amb 310
298 amb 1120 waysx->fd=ReOpenFile(waysx->filename_tmp);
299 amb 310
300 amb 1120 DeleteFile(waysx->filename_tmp);
301 amb 262
302 amb 1120 fd=OpenFileNew(waysx->filename_tmp);
303 amb 272
304 amb 1120 waysx->nfd=OpenFileNew(waysx->nfilename_tmp);
305 amb 555
306 amb 499 /* Copy from the single file into two files */
307 amb 310
308 amb 650 for(i=0;i<waysx->number;i++)
309 amb 310 {
310     WayX wayx;
311 amb 311 FILESORT_VARINT size;
312 amb 310
313 amb 311 ReadFile(waysx->fd,&size,FILESORT_VARSIZE);
314 amb 310
315     if(namelen[nnames%2]<size)
316     names[nnames%2]=(char*)realloc((void*)names[nnames%2],namelen[nnames%2]=size);
317    
318     ReadFile(waysx->fd,&wayx,sizeof(WayX));
319     ReadFile(waysx->fd,names[nnames%2],size-sizeof(WayX));
320    
321     if(nnames==0 || strcmp(names[0],names[1]))
322     {
323 amb 555 WriteFile(waysx->nfd,names[nnames%2],size-sizeof(WayX));
324 amb 310
325     lastlength=waysx->nlength;
326     waysx->nlength+=size-sizeof(WayX);
327    
328     nnames++;
329     }
330    
331     wayx.way.name=lastlength;
332    
333     WriteFile(fd,&wayx,sizeof(WayX));
334    
335 amb 757 if(!((i+1)%1000))
336 amb 790 printf_middle("Separating Way Names: Ways=%"Pindex_t" Names=%"Pindex_t,i+1,nnames);
337 amb 310 }
338    
339     if(names[0]) free(names[0]);
340     if(names[1]) free(names[1]);
341    
342     /* Close the files */
343    
344 amb 612 waysx->fd=CloseFile(waysx->fd);
345 amb 310 CloseFile(fd);
346    
347 amb 612 waysx->nfd=CloseFile(waysx->nfd);
348 amb 310
349     /* Print the final message */
350    
351 amb 1092 printf_last("Separated Way Names: Ways=%"Pindex_t" Names=%"Pindex_t,waysx->number,nnames);
352 amb 310
353    
354     /* Print the start message */
355    
356 amb 519 printf_first("Sorting Ways");
357 amb 310
358 amb 555 /* Re-open the file read-only and a new file writeable */
359 amb 310
360 amb 1120 waysx->fd=ReOpenFile(waysx->filename_tmp);
361 amb 310
362 amb 1120 DeleteFile(waysx->filename_tmp);
363 amb 310
364 amb 1120 fd=OpenFileNew(waysx->filename_tmp);
365 amb 310
366 amb 1135 /* Allocate the array of indexes */
367    
368     waysx->idata=(way_t*)malloc(waysx->number*sizeof(way_t));
369    
370     assert(waysx->idata); /* Check malloc() worked */
371    
372 amb 1129 /* Sort the ways by ID */
373 amb 272
374 amb 1135 sortwaysx=waysx;
375    
376 amb 1129 filesort_fixed(waysx->fd,fd,sizeof(WayX),NULL,
377     (int (*)(const void*,const void*))sort_by_id,
378 amb 1135 (int (*)(void*,index_t))index_by_id);
379 amb 262
380 amb 555 /* Close the files */
381 amb 262
382 amb 612 waysx->fd=CloseFile(waysx->fd);
383 amb 262 CloseFile(fd);
384    
385 amb 266 /* Print the final message */
386    
387 amb 1129 printf_last("Sorted Ways: Ways=%"Pindex_t,waysx->number);
388 amb 499 }
389    
390    
391     /*++++++++++++++++++++++++++++++++++++++
392 amb 1100 Compact the way list, removing duplicated ways and unused ways.
393 amb 499
394 amb 1100 WaysX *waysx The set of ways to process.
395 amb 1092
396 amb 1100 SegmentsX *segmentsx The set of segments to check.
397 amb 499 ++++++++++++++++++++++++++++++++++++++*/
398    
399 amb 1100 void CompactWayList(WaysX *waysx,SegmentsX *segmentsx)
400 amb 499 {
401 amb 1100 int fd;
402     index_t cnumber;
403 amb 499
404     /* Print the start message */
405    
406 amb 1094 printf_first("Sorting Ways and Compacting");
407 amb 1092
408 amb 1093 /* Allocate the array of indexes */
409 amb 499
410 amb 1093 waysx->cdata=(index_t*)malloc(waysx->number*sizeof(index_t));
411 amb 499
412 amb 1093 assert(waysx->cdata); /* Check malloc() worked */
413 amb 499
414 amb 1100 /* Re-open the file read-only and a new file writeable */
415 amb 499
416 amb 1120 waysx->fd=ReOpenFile(waysx->filename_tmp);
417 amb 1093
418 amb 1120 DeleteFile(waysx->filename_tmp);
419 amb 1100
420 amb 1120 fd=OpenFileNew(waysx->filename_tmp);
421 amb 1100
422 amb 1094 /* Sort the ways to allow compacting according to the properties */
423 amb 499
424 amb 1094 sortwaysx=waysx;
425 amb 1100 sortsegmentsx=segmentsx;
426 amb 499
427 amb 1114 cnumber=filesort_fixed(waysx->fd,fd,sizeof(WayX),(int (*)(void*,index_t))delete_unused,
428 amb 1106 (int (*)(const void*,const void*))sort_by_name_and_prop_and_id,
429     (int (*)(void*,index_t))deduplicate_and_index_by_compact_id);
430 amb 499
431 amb 1100 /* Close the files */
432 amb 499
433 amb 1094 waysx->fd=CloseFile(waysx->fd);
434 amb 1100 CloseFile(fd);
435 amb 499
436     /* Print the final message */
437    
438 amb 1100 printf_last("Sorted and Compacted Ways: Ways=%"Pindex_t" Unique=%"Pindex_t,waysx->number,cnumber);
439     waysx->number=cnumber;
440 amb 499
441 amb 1100 free(segmentsx->usedway);
442     segmentsx->usedway=NULL;
443 amb 224 }
444    
445    
446     /*++++++++++++++++++++++++++++++++++++++
447 amb 262 Sort the ways into id order.
448 amb 224
449 amb 262 int sort_by_id Returns the comparison of the id fields.
450    
451 amb 272 WayX *a The first extended way.
452 amb 262
453 amb 272 WayX *b The second extended way.
454 amb 262 ++++++++++++++++++++++++++++++++++++++*/
455    
456 amb 272 static int sort_by_id(WayX *a,WayX *b)
457 amb 262 {
458 amb 272 way_t a_id=a->id;
459     way_t b_id=b->id;
460 amb 262
461     if(a_id<b_id)
462     return(-1);
463     else if(a_id>b_id)
464     return(1);
465     else
466 amb 1118 return(FILESORT_PRESERVE_ORDER(a,b));
467 amb 262 }
468    
469    
470     /*++++++++++++++++++++++++++++++++++++++
471 amb 680 Sort the ways into name order and then id order.
472 amb 272
473 amb 1129 int sort_by_name Returns the comparison of the name fields.
474 amb 272
475 amb 310 WayX *a The first extended Way.
476    
477     WayX *b The second extended Way.
478     ++++++++++++++++++++++++++++++++++++++*/
479    
480 amb 1129 static int sort_by_name(WayX *a,WayX *b)
481 amb 310 {
482     int compare;
483     char *a_name=(char*)a+sizeof(WayX);
484     char *b_name=(char*)b+sizeof(WayX);
485    
486     compare=strcmp(a_name,b_name);
487    
488     if(compare)
489     return(compare);
490 amb 1129 else
491     return(FILESORT_PRESERVE_ORDER(a,b));
492 amb 499 }
493    
494    
495     /*++++++++++++++++++++++++++++++++++++++
496     Sort the ways into name, properties and id order.
497    
498     int sort_by_name_and_prop_and_id Returns the comparison of the name, properties and id fields.
499    
500     WayX *a The first extended Way.
501    
502     WayX *b The second extended Way.
503     ++++++++++++++++++++++++++++++++++++++*/
504    
505     static int sort_by_name_and_prop_and_id(WayX *a,WayX *b)
506     {
507     int compare;
508     index_t a_name=a->way.name;
509     index_t b_name=b->way.name;
510    
511     if(a_name<b_name)
512     return(-1);
513     else if(a_name>b_name)
514     return(1);
515    
516 amb 310 compare=WaysCompare(&a->way,&b->way);
517    
518     if(compare)
519     return(compare);
520    
521     return(sort_by_id(a,b));
522     }
523    
524    
525     /*++++++++++++++++++++++++++++++++++++++
526 amb 1135 Discard duplicate ways.
527 amb 310
528 amb 1135 int deduplicate_by_id Return 1 if the value is to be kept, otherwise 0.
529 amb 310
530 amb 272 WayX *wayx The extended way.
531    
532 amb 1106 index_t index The number of sorted ways that have already been written to the output file.
533 amb 272 ++++++++++++++++++++++++++++++++++++++*/
534    
535 amb 1135 static int deduplicate_by_id(WayX *wayx,index_t index)
536 amb 272 {
537 amb 310 static way_t previd;
538    
539     if(index==0 || wayx->id!=previd)
540 amb 272 {
541 amb 310 previd=wayx->id;
542 amb 272
543     return(1);
544     }
545 amb 812 else
546     {
547     logerror("Way %"Pway_t" is duplicated.\n",wayx->id);
548 amb 272
549 amb 812 return(0);
550     }
551 amb 272 }
552    
553    
554     /*++++++++++++++++++++++++++++++++++++++
555 amb 1135 Create the index of identifiers.
556    
557     int index_by_id Return 1 if the value is to be kept, otherwise 0.
558    
559     WayX *wayx The extended way.
560    
561     index_t index The number of sorted ways that have already been written to the output file.
562     ++++++++++++++++++++++++++++++++++++++*/
563    
564     static int index_by_id(WayX *wayx,index_t index)
565     {
566     sortwaysx->idata[index]=wayx->id;
567    
568     return(1);
569     }
570    
571    
572     /*++++++++++++++++++++++++++++++++++++++
573 amb 1113 Delete the ways that are no longer being used.
574 amb 1094
575 amb 1114 int delete_unused Return 1 if the value is to be kept, otherwise 0.
576 amb 1094
577     WayX *wayx The extended way.
578    
579 amb 1113 index_t index The number of unsorted ways that have been read from the input file.
580 amb 1094 ++++++++++++++++++++++++++++++++++++++*/
581    
582 amb 1114 static int delete_unused(WayX *wayx,index_t index)
583 amb 1094 {
584 amb 1114 if(sortsegmentsx && !IsBitSet(sortsegmentsx->usedway,index))
585 amb 1094 {
586 amb 1114 sortwaysx->cdata[index]=NO_WAY;
587 amb 1094
588 amb 1100 return(0);
589 amb 1094 }
590 amb 1114 else
591     {
592     wayx->id=index;
593 amb 1100
594 amb 1114 return(1);
595     }
596 amb 1113 }
597    
598    
599     /*++++++++++++++++++++++++++++++++++++++
600     Create the index of compacted Way identifiers and ignore Ways with duplicated properties.
601    
602     int deduplicate_and_index_by_compact_id Return 1 if the value is to be kept, otherwise 0.
603    
604     WayX *wayx The extended way.
605    
606     index_t index The number of sorted ways that have already been written to the output file.
607     ++++++++++++++++++++++++++++++++++++++*/
608    
609     static int deduplicate_and_index_by_compact_id(WayX *wayx,index_t index)
610     {
611     static Way lastway;
612    
613 amb 1100 if(index==0 || wayx->way.name!=lastway.name || WaysCompare(&lastway,&wayx->way))
614 amb 1094 {
615 amb 1100 lastway=wayx->way;
616 amb 1094
617 amb 1100 sortwaysx->cdata[wayx->id]=index;
618 amb 1094
619 amb 1100 wayx->id=index;
620    
621     return(1);
622 amb 1094 }
623 amb 1100 else
624     {
625     sortwaysx->cdata[wayx->id]=index-1;
626 amb 1094
627 amb 1100 return(0);
628     }
629 amb 1094 }
630    
631    
632     /*++++++++++++++++++++++++++++++++++++++
633 amb 285 Find a particular way index.
634    
635     index_t IndexWayX Returns the index of the extended way with the specified id.
636    
637 amb 682 WaysX *waysx The set of ways to process.
638 amb 285
639     way_t id The way id to look for.
640     ++++++++++++++++++++++++++++++++++++++*/
641    
642 amb 682 index_t IndexWayX(WaysX *waysx,way_t id)
643 amb 285 {
644 amb 780 index_t start=0;
645     index_t end=waysx->number-1;
646     index_t mid;
647 amb 285
648     /* Binary search - search key exact match only is required.
649     *
650     * # <- start | Check mid and move start or end if it doesn't match
651     * # |
652     * # | Since an exact match is wanted we can set end=mid-1
653     * # <- mid | or start=mid+1 because we know that mid doesn't match.
654     * # |
655     * # | Eventually either end=start or end=start+1 and one of
656     * # <- end | start or end is the wanted one.
657     */
658    
659     if(end<start) /* There are no ways */
660     return(NO_WAY);
661     else if(id<waysx->idata[start]) /* Check key is not before start */
662     return(NO_WAY);
663     else if(id>waysx->idata[end]) /* Check key is not after end */
664     return(NO_WAY);
665     else
666     {
667     do
668     {
669     mid=(start+end)/2; /* Choose mid point */
670    
671     if(waysx->idata[mid]<id) /* Mid point is too low */
672     start=mid+1;
673     else if(waysx->idata[mid]>id) /* Mid point is too high */
674 amb 843 end=mid?(mid-1):mid;
675 amb 285 else /* Mid point is correct */
676     return(mid);
677     }
678     while((end-start)>1);
679    
680     if(waysx->idata[start]==id) /* Start is correct */
681     return(start);
682    
683     if(waysx->idata[end]==id) /* End is correct */
684     return(end);
685     }
686    
687     return(NO_WAY);
688     }
689    
690    
691     /*++++++++++++++++++++++++++++++++++++++
692     Save the way list to a file.
693    
694 amb 682 WaysX *waysx The set of ways to save.
695 amb 285
696     const char *filename The name of the file to save.
697     ++++++++++++++++++++++++++++++++++++++*/
698    
699 amb 682 void SaveWayList(WaysX *waysx,const char *filename)
700 amb 285 {
701     index_t i;
702 amb 555 int fd;
703 amb 310 int position=0;
704 amb 1104 WayX wayx;
705 amb 499 WaysFile waysfile={0};
706 amb 529 highways_t highways=0;
707     transports_t allow=0;
708 amb 530 properties_t props=0;
709 amb 285
710 amb 461 /* Print the start message */
711    
712 amb 519 printf_first("Writing Ways: Ways=0");
713 amb 285
714 amb 1104 /* Re-open the files */
715 amb 461
716 amb 1120 waysx->fd=ReOpenFile(waysx->filename_tmp);
717     waysx->nfd=ReOpenFile(waysx->nfilename_tmp);
718 amb 285
719 amb 461 /* Write out the ways data */
720 amb 285
721 amb 502 fd=OpenFileNew(filename);
722 amb 285
723 amb 461 SeekFile(fd,sizeof(WaysFile));
724 amb 285
725     for(i=0;i<waysx->number;i++)
726     {
727 amb 1104 ReadFile(waysx->fd,&wayx,sizeof(WayX));
728 amb 285
729 amb 1104 highways|=HIGHWAYS(wayx.way.type);
730     allow |=wayx.way.allow;
731     props |=wayx.way.props;
732 amb 398
733 amb 1104 WriteFile(fd,&wayx.way,sizeof(Way));
734 amb 309
735 amb 757 if(!((i+1)%1000))
736 amb 790 printf_middle("Writing Ways: Ways=%"Pindex_t,i+1);
737 amb 285 }
738    
739 amb 461 /* Write out the ways names */
740 amb 285
741 amb 1100 SeekFile(fd,sizeof(WaysFile)+(off_t)waysx->number*sizeof(Way));
742 amb 461
743 amb 309 while(position<waysx->nlength)
744     {
745     int len=1024;
746     char temp[1024];
747    
748     if((waysx->nlength-position)<1024)
749     len=waysx->nlength-position;
750    
751 amb 555 ReadFile(waysx->nfd,temp,len);
752 amb 1104
753 amb 309 WriteFile(fd,temp,len);
754    
755     position+=len;
756     }
757    
758 amb 1104 /* Close the files */
759 amb 309
760 amb 1104 waysx->fd=CloseFile(waysx->fd);
761 amb 612 waysx->nfd=CloseFile(waysx->nfd);
762 amb 555
763 amb 461 /* Write out the header structure */
764    
765 amb 1100 waysfile.number =waysx->number;
766 amb 461
767 amb 526 waysfile.highways=highways;
768     waysfile.allow =allow;
769     waysfile.props =props;
770 amb 461
771     SeekFile(fd,0);
772     WriteFile(fd,&waysfile,sizeof(WaysFile));
773    
774 amb 285 CloseFile(fd);
775    
776 amb 461 /* Print the final message */
777    
778 amb 1100 printf_last("Wrote Ways: Ways=%"Pindex_t,waysx->number);
779 amb 285 }

Properties

Name Value
cvs:description Extended ways functions.