public static void main(String[] args) throws IOException, NoSuchAlgorithmException {
        String baseDir = args[0];//"C:\\Users\\Playtech\\New Folder\\gc\\hl";
        String outFile = args[1];//"C:\\Users\\Playtech\\New Folder\\gc\\hl\\texts.dump";
        Path base = Paths.get(baseDir);
        List<HomelandString> strings = new ArrayList<>(25_000);
        Map<Key, List<HomelandString>> canonicalized = new LinkedHashMap<>(50_000);
        for (Rel rel : RELS) {
            try (FileChannel fc = FileChannel.open(base.resolve(rel.rel), READ)) {
                MappedByteBuffer map = fc.map(MapMode.READ_ONLY, 0, fc.size());
                if (DUMP) {
                    List<HomelandString> bds = new ArrayList<>(25_000);
                    RelSearcher.relStrings(rel.rel, map, rel.ranges, bds);
                    strings.addAll(bds);
                    try (FileOutputStream fos = new FileOutputStream("C:\\Users\\Playtech\\New Folder\\gc\\hl\\tmp\\" + rel.rel);
                            PrintWriter pw = new PrintWriter(new OutputStreamWriter(fos, HomelandString.SHIFT_JIS))) {
                        for (HomelandString hs : bds) {
                            pw.print("" + toHex(hs.offset) + " " + toHex(hs.length) + " ");
                            pw.flush();
                            fos.write(hs.strBytes);
                            pw.println();
                        }
                    }
                } else {
                    RelSearcher.relStrings(rel.rel, map, rel.ranges, strings);
                }
            }
        }
        try (FileChannel allbin = FileChannel.open(base.resolve("all.bin"), READ);
                FileChannel bootdol = FileChannel.open(base.resolve("boot.dol"), READ);) {
            AllBinSplitter.allBinStrings("all.bin",
                    allbin.map(MapMode.READ_ONLY, 0, allbin.size()),
                    bootdol.map(MapMode.READ_ONLY, 0, bootdol.size()),
                    strings);
        }
        System.gc();
        for (HomelandString str : strings) {
            Key key = new Key(str.strBytes);
            List<HomelandString> list = canonicalized.get(key);
            if (list == null) {
                list = new ArrayList<>(1);
                canonicalized.put(key, list);
            }
            list.add(str);
        }

        MessageDigest md = MessageDigest.getInstance("SHA-256");
        try (FileOutputStream fos = new FileOutputStream(outFile)) {
            int i = 0;
            final Set<String> ids = new TreeSet<>();
            for (Entry<Key, List<HomelandString>> e : canonicalized.entrySet()) {
//                String string = e.getKey();
                List<HomelandString> list = e.getValue();
                HomelandString hs = list.get(0);
                md.reset();
                byte[] digest = md.digest(hs.strBytes);
                String sha = toHex(digest);
                String id = sha.substring(0, 8);
                if (!ids.add(id)) {
                    throw new RuntimeException("duplicate id " + id);
                }
                id = "hl-string-" + id;
                fos.write(id.getBytes(HomelandString.SHIFT_JIS));
                fos.write("\n".getBytes(HomelandString.SHIFT_JIS));
                for (HomelandString h : list) {
                    fos.write(h.file.getBytes(HomelandString.SHIFT_JIS));
                    fos.write("\t".getBytes(HomelandString.SHIFT_JIS));
                    fos.write(toHex(h.offset).getBytes(HomelandString.SHIFT_JIS));
                    fos.write("\n".getBytes(HomelandString.SHIFT_JIS));
                }
                fos.write("\n".getBytes(HomelandString.SHIFT_JIS));
                fos.write(toHex(hs.length).getBytes(HomelandString.SHIFT_JIS));
                fos.write("\n".getBytes(HomelandString.SHIFT_JIS));
                fos.write(hs.strBytes);
//                fos.write("\r\n".getBytes(HomelandString.SHIFT_JIS));
//                byte[] strNumberBytes = sha.getBytes(HomelandString.SHIFT_JIS);
//                fos.write(strNumberBytes, 0, Math.min(strNumberBytes.length, hs.length));
//                for (int j = strNumberBytes.length; j < hs.strBytes.length; j++) {
//                    fos.write(0x3F);
//                }
                fos.write("\n".getBytes(HomelandString.SHIFT_JIS));
                i++;
            }
            System.out.println(i + " strings");
        }
    }