Codebase list mkgmap / 38342b4
New upstream version 0.0.0+svn4810 Bas Couwenberg 2 years ago
9 changed file(s) with 105 addition(s) and 21 deletion(s). Raw diff Collapse all Expand all
7070 into {user}\AppData\Roaming\Garmin\Maps or \ProgramData\Garmin\Maps
7171 and the map will be available to Garmin PC programs.
7272 The directory name is --family-name with extension .gmap.
73
74 ;--gmapi-minimal[=<include-pattern>]
75 : Special option for map providers to reduce disk writes when updating. Works like
76 --gmapi but does not write Product data for input files which are provided as
77 *.img. It is assumed that the content of those files wasn't changed and thus
78 doesn't need a rewrite. The optional include-pattern is a regular expression
79 which can be used to specify *.img files for which a write should be forced. The
80 pattern is used on the full path to the input file. The global index files and
81 the *.tdb file will still contain all needed references.
82 : Example usage with pattern:
83 :: --gmapi-minimal=.*4711[0-9]{4}\.img
84 :: This pattern matches file names between 47110000.img and 47119999.img
85 :: and ignores the path.
7386
7487 ;-c filename
7588 ;--read-config=filename
6969 into {user}\AppData\Roaming\Garmin\Maps or \ProgramData\Garmin\Maps and the
7070 map will be available to Garmin PC programs. The directory name is
7171 --family-name with extension .gmap.
72
73 --gmapi-minimal[=<include-pattern>]
74 Special option for map providers to reduce disk writes when updating. Works
75 like --gmapi but does not write Product data for input files which are
76 provided as *.img. It is assumed that the content of those files wasn't
77 changed and thus doesn't need a rewrite. The optional include-pattern is a
78 regular expression which can be used to specify *.img files for which a
79 write should be forced. The pattern is used on the full path to the input
80 file. The global index files and the *.tdb file will still contain all
81 needed references.
82 Example usage with pattern:
83 --gmapi-minimal=.*4711[0-9]{4}\.img
84 This pattern matches file names between 47110000.img and 47119999.img
85 and ignores the path.
7286
7387 -c filename
7488 --read-config=filename
0 svn.version: 4807
1 build.timestamp: 2021-09-14T09:45:24+0100
0 svn.version: 4810
1 build.timestamp: 2021-10-25T08:27:43+0100
2626 for (String listOpt : Arrays.asList("mdr7-excl", "mdr7-del", "poi-excl-index", "location-autofill",
2727 "overview-levels", "levels", "name-tag-list", "polygon-size-limits", "dem", "dem-dists", "drive-on",
2828 "dead-ends", "add-pois-to-lines", "coastlinefile", "generate-sea", "nearby-poi-rules",
29 "line-types-with-direction")) {
29 "line-types-with-direction", "gmapi-minimal")) {
3030 stringToList(get(listOpt, null), listOpt);
3131 }
3232 }
3131 import uk.me.parabola.imgfmt.app.Area;
3232 import uk.me.parabola.imgfmt.app.BufferedImgFileReader;
3333 import uk.me.parabola.imgfmt.app.lbl.LBLFileReader;
34 import uk.me.parabola.imgfmt.app.map.MapReader;
3435 import uk.me.parabola.imgfmt.app.srt.Sort;
3536 import uk.me.parabola.imgfmt.app.trergn.TREFileReader;
3637 import uk.me.parabola.imgfmt.app.trergn.TREHeader;
8485 private int codePage;
8586 private int sortOrderId;
8687 private int demsize;
88 private MapReader mapReader;
8789
8890 private FileInfo(String filename, FileKind kind) {
8991 this.filename = filename;
474476 public void setDemsize(int demsize) {
475477 this.demsize = demsize;
476478 }
479
480 public MapReader getMapReader() throws FileNotFoundException {
481 if (mapReader == null)
482 mapReader = new MapReader(filename);
483 return mapReader;
484 }
485
486 public void closeMapReader() {
487 if (mapReader != null) {
488 Utils.closeFile(mapReader);
489 mapReader = null;
490 }
491 }
477492 }
3333 import uk.me.parabola.imgfmt.fs.FileSystem;
3434 import uk.me.parabola.imgfmt.fs.ImgChannel;
3535 import uk.me.parabola.imgfmt.sys.ImgFS;
36 import uk.me.parabola.log.Logger;
3637 import uk.me.parabola.mkgmap.CommandArgs;
3738
3839 import static java.nio.file.StandardOpenOption.*;
4445 * each .img file.
4546 */
4647 public class GmapiBuilder implements Combiner {
48 private static final Logger log = Logger.getLogger(GmapiBuilder.class);
4749 private static final String NS = "http://www.garmin.com/xmlschemas/MapProduct/v1";
4850
4951 private final Map<String, Combiner> combinerMap;
52 private final Map<String, String> sourceMap;
5053
5154 private Path gmapDir;
5255 private final Map<Integer, ProductInfo> productMap = new HashMap<>();
5760
5861 private String typFile;
5962
60 public GmapiBuilder(Map<String, Combiner> combinerMap) {
63 private boolean forceWrite;
64 private String mustWritePattern;
65
66
67 public GmapiBuilder(Map<String, Combiner> combinerMap, Map<String, String> sourceMap) {
6168 this.combinerMap = combinerMap;
69 this.sourceMap = sourceMap;
6270 }
6371
6472 /**
7482 productVersion = (short) args.get("product-version", 100);
7583
7684 gmapDir = Paths.get(args.getOutputDir(), String.format("%s.gmap", familyName));
85 forceWrite = args.exists("gmapi");
86
87 mustWritePattern = args.get("gmapi-minimal", null);
7788 }
7889
7990 /**
92103
93104 // Unzip the image into the product tile directory.
94105 try {
95 if (info.isImg())
96 unzipImg(fn, mapname, productId);
106 if (info.isImg()) {
107 if (forceWrite || shouldWrite(info))
108 unzipImg(fn, mapname, productId);
109 }
97110 else if (info.getKind() == FileKind.TYP_KIND)
98111 typFile = info.getFilename();
99112
100113 } catch (IOException e) {
101114 throw new ExitException("Error saving gmapi data", e);
102115 }
116 }
117
118 private boolean shouldWrite(FileInfo info) {
119 String fn = info.getFilename();
120 String source = sourceMap.get(fn);
121 if (!source.equals(fn)) {
122 log.diagnostic("gmapi-minimal: Writing freshly compiled file " + fn);
123 return true;
124 }
125 if (mustWritePattern != null) {
126 if (fn.matches(mustWritePattern)) {
127 log.diagnostic("gmapi-minimal: Writing old file " + fn + " because it matches pattern " + mustWritePattern);
128 return true;
129 }
130 }
131 log.diagnostic("gmapi-minimal: Skipping file " + fn);
132 return false;
103133 }
104134
105135 /**
156186 unzipImg(srcImgName, destDir);
157187 }
158188
159 private static void unzipImg(String srcImgName, Path destDir) throws IOException {
189 private void unzipImg(String srcImgName, Path destDir) throws IOException {
160190 FileSystem fs = ImgFS.openFs(srcImgName);
161191 for (DirectoryEntry ent : fs.list()) {
162192 String fullname = ent.getFullName();
167197 continue;
168198
169199 Files.createDirectories(destDir);
170 copyToFile(f, destDir.resolve(name));
200 Path out = destDir.resolve(name);
201 copyToFile(f, out);
171202 }
172203 }
173204 }
154154 mdrFile.addMap(info.getHexname(), info.getCodePage());
155155
156156 String filename = info.getFilename();
157 MapReader mr = null;
158157 try {
159 mr = new MapReader(filename);
158 MapReader mr = info.getMapReader();
160159
161160 AreaMaps maps = new AreaMaps();
162161
171170 addZips(mr);
172171 } catch (FileNotFoundException e) {
173172 throw new ExitException("Could not open " + filename + " when creating mdr file");
174 } finally {
175 Utils.closeFile(mr);
176173 }
177174 }
178175
134134 for (String m : msgs)
135135 tdb.addCopyright(m);
136136
137 MapReader mapReader = null;
138137 String filename = finfo.getFilename();
139138 try{
140 mapReader = new MapReader(filename);
139 MapReader mapReader = finfo.getMapReader();
141140
142141 msgs = mapReader.getCopyrights();
143142 boolean found = false;
156155
157156 } catch (FileNotFoundException e) {
158157 throw new ExitException("Could not open " + filename + " when creating tdb file");
159 } finally {
160 Utils.closeFile(mapReader);
161158 }
162159
163160
103103 private volatile int programRC = 0;
104104
105105 private final Map<String, Combiner> combinerMap = new HashMap<>();
106 private final Map<String, String> sourceMap = new HashMap<>();
106107 private boolean informationDisplayed = false;
107108
108109 /**
296297 }
297298 });
298299 task.setArgs(args);
300 task.setSource(filename);
299301 futures.add(task);
300302 }
301303
617619 final Map<String, Integer> nameToHex = new HashMap<>();
618620 for (FilenameTask f : filenames) {
619621 if (f.getFilename().endsWith(".img")) {
622 sourceMap.put(f.getFilename(), f.getSource());
620623 int hex;
621624 try {
622625 hex = FileInfo.getFileInfo(f.getFilename() ).getHexname();
674677 continue;
675678 c.onMapEnd(fileInfo);
676679 }
680 fileInfo.closeMapReader();
677681 } catch (FileNotFoundException e) {
678682 throw new MapFailedException("could not open file " + e.getMessage());
679683 }
705709 boolean indexOpt = args.exists("index");
706710 boolean gmapsuppOpt = args.exists("gmapsupp");
707711 boolean tdbOpt = args.exists("tdbfile");
708 boolean gmapiOpt = args.exists("gmapi");
712 boolean gmapiOpt = args.exists("gmapi") || args.exists("gmapi-minimal");
709713 boolean nsisOpt = args.exists("nsis");
710714
711 for (String opt : Arrays.asList("gmapi", "nsis")) {
715 if (args.exists("gmapi") && args.exists("gmapi-minimal")) {
716 throw new ExitException("Options --gmapi and --gmapi-minimal are mutually exclusive");
717 }
718 for (String opt : Arrays.asList("gmapi", "nsis", "gmapi-minimal")) {
712719 if (!createTdbFiles && args.exists(opt)) {
713720 throw new ExitException("Options --" + opt + " and --no-tdbfiles are mutually exclusive");
714721 }
728735 addCombiner("mdx", new MdxBuilder());
729736 }
730737 if (gmapiOpt) {
731 addCombiner("gmapi", new GmapiBuilder(combinerMap));
738 addCombiner("gmapi", new GmapiBuilder(combinerMap, sourceMap));
732739 }
733740 if (nsisOpt) {
734741 addCombiner("nsis", new NsisBuilder(combinerMap));
771778 private static class FilenameTask extends FutureTask<String> {
772779 private CommandArgs args;
773780 private String filename;
781 private String source;
774782
775783 private FilenameTask(Callable<String> callable) {
776784 super(callable);
793801 }
794802
795803 public String toString() {
796 return filename;
797 }
804 return source + " -> " + filename;
805 }
806
807 public void setSource(String source) {
808 this.source = source;
809 }
810
811 public String getSource() {
812 return source;
813 }
814
798815 }
799816 }